Skip to content
enrive2020Public

About

CRM для музыкальных школ: расписание, абонементы со списанием и заморозкой, зарплаты преподавателей. Мультитенантный SaaS на PostgreSQL.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Latest commit

 

History

42 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

RockCRM

CRM для музыкальных школ. Мультитенантный SaaS: одна установка обслуживает много школ, каждая видит только свои данные.

PostgreSQL 17 · FastAPI · React + TypeScript


Зачем

Существующие CRM для учебных центров делятся на две группы, и обе промахиваются мимо музыкальной школы.

Универсальные (Битрикс24, amoCRM) умеют воронку и бронирование ресурсов, но не знают, что такое абонемент: списание за занятие, заморозку на каникулы, отработку пропуска и зарплату преподавателя там либо считают в Excel, либо заказывают у интегратора. Платформы для онлайн-школ (Antitreningi и подобные) умеют уроки и тесты, но у них нет ни расписания, ни кабинетов, ни посещаемости — офлайн-центру они не подходят вовсе.

В итоге администратор музыкальной школы ведёт расписание в одном месте, остатки абонементов в другом, а зарплату преподавателей в третьем — и сводит это руками.

RockCRM закрывает именно эту работу. Отметка посещаемости — одно действие, которое само двигает остаток абонемента, начисление преподавателю и напоминание о продлении.

Что уже есть

Спецификация Домен, роли, правила абонемента, границы v1
Контракты этапов расписание · абонементы · воронка
Схема БД 6 миграций, изоляция тенантов, ограничения целостности
Бэкенд FastAPI на голом SQL, без ORM
Фронтенд React и TypeScript, две рантайм-зависимости
Прототип Кликабельный интерфейс, открывается файлом без сборки
Тесты схемы Проверки гарантий базы на живом PostgreSQL

Каждый этап начинается с контракта между бэкендом и фронтендом: он фиксирует форму данных до того, как написана первая строка кода, поэтому обе стороны пишутся параллельно и не ждут друг друга. Расхождения между контрактом и реальностью попадают в задачи с меткой пробел-контракта — их набралось достаточно, чтобы считать этот приём окупившимся.

Три решения, на которых всё держится

Абонемент — журнал, а не счётчик. Остаток занятий не хранится изменяемым числом: есть журнал операций, остаток — их сумма. Спор с родителем «куда делось занятие» разрешается открытием журнала, ошибочная отметка гасится компенсирующей записью, а не правкой задним числом.

Правила копируются в абонемент при продаже. Если школа завтра решит, что прогул больше не сгорает, вчерашние абонементы не пересчитаются: проданный абонемент — договор на условиях, действовавших при покупке.

Двойную бронь запрещает база, а не код. Ограничения исключения по кабинету и преподавателю: два администратора, сохраняющие занятие одновременно, оба увидели бы свободный слот, и проверка в приложении здесь бесполезна.

Дорожная карта

  • Спецификация и схема БД
  • Прототип интерфейса
  • Расписание и посещаемость
  • Абонементы: списание и отработки при отметке
  • Зарплаты: начисление от проведённого занятия
  • Карточка ученика, продажа и продление абонементов, заморозки
  • Воронка заявок, приём по вебхуку, отчёт по источникам
  • Кабинет родителя
  • Мультитенантный онбординг и биллинг

Закрыты три этапа. Расписание и отметка: одно действие списывает занятие, начисляет преподавателю и предупреждает о продлении. Карточка ученика и абонемент: поиск по родителю, история движений, продажа с предпросмотром итога, заморозка со сдвигом срока. Воронка заявок: приём из Telegram-бота и LeadHub, пробный урок в расписании, конверсия в ученика, отчёт по источникам.

Общий принцип экранов — администратор видит последствия прежде, чем нажать: сколько спишется, сколько начислится, до какого числа продлится, сколько занятий отменится.

Текущее состояние проверок: 165 тестов бэкенда и 22 теста схемы против настоящего PostgreSQL. Схема проверяется на том, что она запрещает, а не на том, что таблицы создались.

Разработка

docker run -d --name rockcrm-pg \
  -e POSTGRES_PASSWORD=dev -e POSTGRES_DB=rockcrm \
  -p 5432:5432 postgres:17-alpine

for f in db/00*.sql; do psql "$DATABASE_URL" -v ON_ERROR_STOP=1 -f "$f"; done

Схеме нужно расширение btree_gist — оно есть в официальном образе postgres, но отсутствует в урезанных сборках. Подробности и порядок подключения приложения — в db/README.md.

About

CRM для музыкальных школ: расписание, абонементы со списанием и заморозкой, зарплаты преподавателей. Мультитенантный SaaS на PostgreSQL.

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages