Хранение сообщений чата в таблице MySql - PullRequest
5 голосов
/ 02 декабря 2011

Последние пару недель я работаю над клиентским веб-приложением для чата, и у меня есть вопрос относительно хранения сообщений чата в таблице MySql. Я создал таблицу под названием разговоры, и пока она состоит из 5 полей;

user1ID, user2ID, сообщения (средний текст), статус, метка времени.

Когда я тестирую приложение чата, все работает отлично, но проблема в том, что каждый раз, когда пользователь что-то отправляет, я добавляю это значение в поле «сообщения» в виде новой строки. И когда дело доходит до извлечения сообщения, мой SQL-код читает все это и показывает его соответствующему пользователю. Таким образом, объем данных линейно увеличивается на количество текста, добавляемого в поле сообщений. У меня вопрос, есть ли способ ВЫБРАТЬ только последнюю строку из текстового поля или, возможно, другое решение, которое уменьшит объем передаваемых данных.

Ответы [ 4 ]

14 голосов
/ 02 декабря 2011

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

Вот один вариант ERD для вашей базы данных.

enter image description here


5/6 / 2016 edit Добавление DDL с (надеюсь) улучшенными типами и именами полей

CREATE TABLE user
(
    user_id CHAR(32),
    user_login VARCHAR(255),
    user_password CHAR(64),
    user_email VARCHAR(400),
    PRIMARY KEY (user_id)
);

CREATE TABLE message
(
    message_id CHAR(32),
    message_datetime DATETIME,
    message_text TEXT,
    message_chat_id CHAR(32),
    message_user_id CHAR(32),
    PRIMARY KEY (message_id)
);

CREATE TABLE user_chat
(
    user_chat_chat_id CHAR(32),
    user_chat_user_id CHAR(32),
    PRIMARY KEY (user_chat_chat_id,user_chat_user_id)
);

CREATE TABLE chat
(
    chat_id CHAR(32),
    chat_topic VARCHAR(32),
    chat_password CHAR(64),
    user_chat_user_id CHAR(32),
    PRIMARY KEY (chat_id)
);

CREATE INDEX user_login_idx ON user (user_login);
ALTER TABLE message ADD FOREIGN KEY message_chat_id_idxfk (message_chat_id) REFERENCES chat (chat_id);

ALTER TABLE message ADD FOREIGN KEY message_user_id_idxfk (message_user_id) REFERENCES user (user_id);

ALTER TABLE user_chat ADD FOREIGN KEY user_chat_user_id_idxfk (user_chat_user_id) REFERENCES user (user_id);

ALTER TABLE chat ADD FOREIGN KEY chat_id_idxfk (chat_id,user_chat_user_id) REFERENCES user_chat (user_chat_chat_id,user_chat_user_id);
4 голосов
/ 02 декабря 2011

Почему бы не иметь такую ​​структуру таблицы:

чаты

  • chatID
  • user1ID
  • user2ID
  • startedDateTime
  • EndedDateTime

chatContent

  • chatContentID
  • chatID
  • сообщение
  • DATETIME
  • состояние

Таким образом, ваши данные гораздо проще искать и упорядочивать. Например, что, если вы хотите, чтобы определенное сообщение говорилось во время X? или вы хотите получать все сообщения чата со статусом X?

Разделение данных на 2 таблицы должно быть намного приятнее и аккуратнее.

0 голосов
/ 12 октября 2018

Итак, вот еще одна схема. Я бы описал цель следующим образом:

  • Ну как в фейсбуке. Пользователь может принадлежать ко многим группам, также группа может принадлежать многим пользователям.

enter image description here

  • В таблице user_group_chat я делаю столбец user_id, group_id и created_at как ПЕРВИЧНЫЙ КЛЮЧ. Столбец user_id также является FOREIGN KEY таблицы users, но для DELETE будет CASCADE, а group_id также FOREIGN KEY таблицы groups и для DELETE также будет CASCADE. И причина для того, чтобы сделать их как FOREIGN KEY проста. Если пользователь или группа не существует, их тоже не должно быть.
  • Также в таблице user_user_chat я делаю столбец from_user_id, to_user_id и created_at также как ПЕРВИЧНЫЙ КЛЮЧ. В двух словах, его поведение такое же, как и у таблицы user_group_chat. Просто эта таблица отвечает за хранение чата между пользователем и пользователем.
0 голосов
/ 02 декабря 2011

Рассмотрите возможность сохранения одного сообщения на строку в таблице:

id, user1id, user2id, сообщение, статус, отметка времени

где id - столбец автоинкремента.

...