MySQL раздел по внешнему ключу - PullRequest
0 голосов
/ 05 января 2020

У меня есть база данных чата в MySQL.

таблица пользователей

идентификатор_пользователя (PK), имя_пользователя

таблица чатов

chat_id (PK), user1_id (FK), user2_id (FK)

таблица 'сообщений'

message_id (PK), chat_id (FK), user_from (FK), message_text, message_date

Поскольку я ожидаю, что в таблице сообщений будут миллионы записей, я подумал о ее разбиении. Это хороший подход? И какой тип раздела должен использоваться здесь? Я думал, что если я разделю по chat_id, то для каждого чата между двумя пользователями я получу раздел. На практике в результате каждый раз все записи из раздела будут извлекаться, так как все они принадлежат одному чату. Но это означает, что если у меня 1 миллион чатов, у меня 1 миллион разделов. Однако, поскольку chat_id является внешним ключом, MySQL не разрешает разбиение по chat_id.

Ответы [ 2 ]

1 голос
/ 06 января 2020

Главное, что нужно понять о PARTITIONing, это то, что он не по сути обеспечивает какое-либо преимущество в производительности.

Есть несколько исключений. Единственное, что может применяться, это:

Если вы намереваетесь удалить «старые» чаты, скажем, через 30 дней, тогда DELETE можно сделать более эффективным с помощью DROP PARTITION.

* 1011. * Больше обсуждений: http://mysql.rjweb.org/doc.php/partitionmaint

Возвращаясь к вашим конкретным c вопросам:

"В каждом чате между двумя пользователями я получаю раздел" - НЕТ! Разметка плохо масштабируется. В целом, механизмы баз данных спроектированы так, чтобы быть эффективными при выполнении вещей DML: выбрать / вставить / удалить / обновить, но за счет вещей DDL: создать / изменить / удалить.

"все они принадлежат «Тот же чат» - звучит как попытка помочь с «кешированием». Большая часть этого может быть достигнута путем тщательного выбора индексов. messages для данного chat может быть «кластеризован» вместе с этой техникой в ​​таблице messages:

CREATE TABLE Messages (
    message_id BIGINT NOT NULL AUTO_INCREMENT,
    chat_id INT UNSIGNED NOT NULL,
    ...
    PRIMARY KEY(chat_id, message_id),  -- to cluster by chat
    INDEX(message_id)   -- to keep auto_increment happy
) ENGINE=InnoDB;

Почти во всех ситуациях «цель» разделения может быть эмулирована Подходящая схема индексации. (Следствие: нужно пересмотреть индексы при переключении на / из разбиения.)

«1 миллион разделов» - ограничение 8 КБ. И есть, по крайней мере, один диск файл на раздел; Операционные системы не любят иметь миллион файлов, особенно в одном каталоге. Даже 8К растягивает вещи.

0 голосов
/ 05 января 2020

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

Вы думаете, что там будет миллион сообщений, так что вы подумали I can split the tables so it will be easier, но я думаю, что такое управление сложно и не оптимизировано!

Я использую таблицу чата с room_id, sender_id, receive_id, message_text, message_date, видимыми полями. И им легче управлять ...

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

...