познаниях)
Подскажите пожалуйста в некоторых вопросах:
1. Primary Index, удобная штука для выборки, этот индекс может содержать несколько полей, на сколько будет хардкорно, если у меня будет 5-6 полей, вставка происходит с частотой 3000 записей в сек . Не возникнут ли у меня проблемы?
2. Партиционирование думаю сделать под дням, норма ли это? В основном выборка идет по суточно, реже за несколько суток, совсем редко за месяц.Не будет ли большой проблемой?
Можно ли партиционирование сделать к примеру по несколько дней, к примеру 7....
Спасибо!
1. В целом длинный pk - это плохо: он будет помещаться в оперативку. 2. Партиционирование по дням делают, однако надо тестировать на данных, если вы поместите дату в начало pk, ch использует его на запросе. Также учитывайте, что партиционирование по дням это x30 файлов. По поводу партиционирования по некоторому количеству дней (например по 7) - да, можно. Нужно добавить в partition by не date, а toStartOfWeek или нечто подобное. Однако я не уверен, что без указания аналогичной функции в запросе не будут прочтены лишние данные.
Спасибо! Буду тестировать
ах да, самое важное вставка происходит с частотой 3000 записей в сек не надо лить в ch данные по 1 строке, заливайте батчами 3000 записей в секунду по 1 строке - ужас 1 запись в секунду по 3000 строк - легко
Ну да, читал об этом. Какой инструмент посоветуете, чтоб собирал эти батчи, перед вставкой?
мы используем kafka + заливка батчами по расписанию есть готовые инструменты, заточенные под ch: https://clickhouse.tech/docs/ru/interfaces/third-party/proxy/
вообще, надо понять что индексы в clickhouse это не B-Tree индексы как в остальных СУБД, когда мы методом половинного поиска по значению из индекса за o(log n) быстро находим где у нас в основном файле смещения по которому лежат данные с требуемым значением индекса в ClickHouse индексы это data skip индексы для PK это фактически min max индекс то есть мы читаем небольшой .mrk файл с кешированием в памяти .. видим в нем значения min \ max значения pk полей, для нескольких (по умолчанию 8192) строк в таблице и смещения в .bin файлах (начало compressed блока + смещение внутри uncompressed блока) и на этом основании принимаем решение как именно вычитывать этот .bin файл Партицирование по дням нужно только когда данных (размер .bin файлов) РЕАЛЬНО ОЧЕНЬ МНОГО... (размеры старых смерженых партов начинаются от нескольких сотен мегабайт) Партицирование это физическое разбиение на разные каталоги и оно позволяет очень быстро сразу определиться за какой период мы читаем, выборка из партиций идет паралельно, но для HDD много партиций в таком случае будет вредно, для SSD норм Партицирование по дням может мешать если вы всталяете данные в одном INSERT за большой промежуток времени и затрагиваете сразу несколько партиций, в которых будет создаваться куча мелких партов (system.parts) которые потом надо в бекграунде мержить с более старыми крупными партами > Вставка 3000 записей в секунду. в смысле 3000 INSERT по одной записи в секунду? НЕ ДЕЛАЙТЕ ТАК! или 3000 INSERT по 1 000 записей в секунду? так можно, лучше пусть будет 30 INSERT по 100 000 записей, или один INSERT в секунду на 3 000 000 записей
Спасибо за развернутый ответ и совет. Вопрос такой, стоит ли в индексе хранить UUID? Как он тогда вычислит min max? Или будет сортировать в алфавитном порядке?
нет не стоит вообще в PK индексе не стоит хранить поля с высокой кардинальностью (больше сотен тысяч) значений UUID вообще вредная штука, потому что значение рандомное и монотонно не возрастает соответсвенно размазывается по всем партам и трудно парты отбрасывать потому что не ясно есть ваш UUID в них или нет лучше замените на snowflake id какой нибудь который возрастает монотонно он похож на время и его кстати уже можно в PK хранить
Словари есть. Буду пробовать, спасибо. На что ориентироваться в результате?
а что такое snowflake id? Гугл говорит только что snowflake база данных
вот так гуглите =) snowflake да =) такая база есть twitter snowflakeid sonyflake id
Ваш гугл вам врет https://medium.com/nuances-of-programming/%D1%87%D1%82%D0%BE-%D1%82%D0%B0%D0%BA%D0%BE%D0%B5-snowflake-id-968dd6d21ca8
ну вы смотрите какой именно запрос генерирует на удаленных нодах ваш distributed запрос может быть там не передается dictGet условие... и вы там пытаетесь как то не потоково буферизировать результат вообще конечно запрос и структуры таблиц словарей нужны ... по памяти не обязательно именно ваш запрос отваливается, может быть там что-то другое отжирает
Обсуждают сегодня