/chat

simple chat

Primary LanguageJavaScript

Simple chat

Создание чата в целях практики новых инструментов/языков/технологий.

Архитектура

Архитектуру любого проекта описываем в 4 секциях:

Доменная модель

Чат

Чат содержит в себе все сообщения(в отсортированном по времени виде), отправленные в него. Основная функция чата(и всего приложения на данный момент) возможность принять в себя сообщение, и увидомить всех участников чата об этом событии путем показа сообщения.

Пользователь

Пользователь на данный имеет только имя. В будущем:

  • Разная мета инфа(ава, возраст, пол, вера и т.д)
  • acces policy
  • роль в чате(админ, модер, молчун)

Сообщение

Сообщение имеет свой текст, дату отправки и ссылку на пользователя, отправившего его. В будущем:

  • может быть отредактировано
  • может быть удалено
  • может быть переслано
  • может быть получен ответ на сообщение(reply)

Компоненты

Серверное API

Набор endpoints для взаимодействия с основной системой. Обычное api, которое предоставляет клиентам доступ к функционалу приложения

Комет сервер(доставщик сообщений)

Должен уметь пушить сообщения в каналы, без запроса пользователя, для real time оставки

Клиенты к api

Любое ПО способное дергать методы серверного API. Также нужно подписываться на каналы для доставки realTime сообщений

Курсор в чате

Нужно хранить id последнего прочитанного сообщения для каждого из чатов, где есть пользователь, для того чтобы делить в интерфейсе прочитанные и непрочиатнные сообщения

Персистентное хранилище

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

Кэш

Кэш будет нужен как минимум для хранения списка чатов пользователя, и последнего сообщения для каждого из чатов(чтобы получить левую колонку в формате как вк или телеграм) Также в кэше можно будет хранить курсор

Взаимодействие компонентов

Клиент <=> Сервер

  • Получить список чатов для юзера
  • Получить определенное число сообщений из чата, начиная с определенного
  • Отправить сообщение
  • Прочитать все сообщения из чата до определенного

Над форматом API особо заморачиватсья не буду, т.е цели достигнуть RestFull или каноничного соовтетствия определенной версии jRpc не ставлю.

Клиент <=> Comet

Тут нужна просто возомжность подписываться на определенные каналы. Будет свой канал для каждого из чатов.

Конкретные технологии

  • persistenceDB - Mysql Здесь просто буду юзать то что знаю
  • messageDelivery - Centrifugo? firebase? С firebase был опыт а centrifugo давно хотел попробовать + много положительных отзывов в плане perfomance и high availibility
  • server language - golang Просто давно хотел попробовать его с каким то проектом с существующим ТЗ, а не с упражнениями в интерактивных обучалках
  • inMemoryDb - Redis Идеально подойдет для задачи хранения списка чатов с последним сообщением(id и текск)
  • client - vue C фронтом у меня все печально, слышал что vue довольно простой, его и опробую.

RoadMap

Пороект ОЧЕНЬ сырой и кривой. Нужно много улучшений:

  • Серверная часть:

    • Нормальный JWT и авторизация
    • Погуглить хорошие практики конфига приложений Golang(ENV ??)
    • Подумать когда закрывать коннекшны к бд(посе каждого запроса, или в фазе завершения обработки http запроса)
    • Развертка в 1 команду(docker compose? cubernetes?)
    • проверить везде, что все ошибки корректно обрабатываеются, подумать чем заменить err != nil
    • аудит безопасности
    • написать тесты
    • дб резолвер(шарды чатов и юзеров)
    • прикрутить модный сбор логов(кибана)
  • Клиентская часть:

    • разобраться с нормальными асинхронными запрсоами к api ибо вызывать команды с async = false это печаль
    • отказаться от джквери(юза по сути только для аякса)
    • не подгружать старые сообщения 10 раз в случае когда они кончились
    • нормально детектить прочитанные, сейчас прочианными сообщениями считаются те, которые были в откытом чате, а нужно делать те, которые попали в поле зрения пользователя
    • помечать непрочитанные в окне чата(сейчас помечается только напротив названия чата)
    • удостовериться что vue защищает от xss
    • имя автора
    • прорисовывать отправленное сообщение до того как оно ушло на сервер, и обрабатывать успех/ошибку
    • выровнять дату в правой колонке

Как развернуть

  1. Копируем репу к себе
  2. Восстанавливаем БД из chat.sql
  3. Запускаем centrifugo на сервере
  4. Настраиваем nginx на папку web()
  5. Переименовываем example-conf.json в conf.json и корректно заполняем
  6. go run main.go
  7. Если нужно меняем захардкоженные параметры в js code

Надеюсь я успею подготовить compose файл и все это делать не придется...