SlideShare a Scribd company logo
Cassandra. Patterns.
Для кого доклад
Для разработчиков, которые уже знают что
такое Cassandra, для чего она нужна и
попробовали ее использовать.
Cassandra. Internals.
Cassandra имеет внутри структуру хранения,
похожую на lsm tree + wal.
Верхний уровень - memtable (sorted by row
key, btree-like).
Нижний уровень - disk (sstable + bloom filter).
Cassandra. Java point of view.
SortedMap<RowKey, SortedMap<ColumnKey, ColumnValue>>
Cassandra. Internals. Write path.
Cassandra. Internals. Read path.
Cassandra. Сильные стороны.
Почти линейная масштабируемость
записи и чтения
Не нужно backup, все
восстанавливается на лету
Есть поддержка нескольких ДЦ
Настраиваемая модель (в терминах CAP)
Стабильный продукт с первоклассным community
Нет ACID транзакций
Частое удаление данных это проблема
Нет хороших secondary index*
* Индексы сейчас улучшаются:
https://github.com/xedin/sasi и CASSANDRA-
10661)
Cassandra. Слабые стороны.
Лайки
CREATE TABLE LikedByObject(
user_id bigint,
object_id bigint,
created bigint,
PRIMARY KEY (object_id, user_id)
);
CREATE TABLE LikedByUser(
user_id bigint,
object_id bigint,
created bigint,
type_id int,
PRIMARY KEY ((user_id, type_id), object_id)
);
Лайки
Выбрать всех кто лайкал объект
select * from LikedByObject where object_id = 42
Выбрать все что лайкал пользователь
select * from LikedByUser where user_id = 42 and type_id in (1, 2, 3)
Лайки
Нет secondary index, используем materialized view. Почти всегда
копирование данных более предпочтительно, так как самое
затратное при чтении данных с диска это seek. Прочитать чуть
больше данных, но из одного место быстрее, чем из двух.
Уведомления
Уведомления
CREATE TABLE NotificationByUser (
user_id bigint,
shard_part text,
id timeuuid,
type_id int,
.....
PRIMARY KEY ((user_id, shard_part), id)
) WITH CLUSTERING ORDER BY (id DESC);
CREATE TABLE NotificationByUserAndType (
.....
PRIMARY KEY ((user_id, type_id, shard_part), id)
) WITH CLUSTERING ORDER BY (id DESC);
CREATE TABLE NotificationSeen (
user_id bigint,
id timeuuid,
value boolean,
PRIMARY KEY (user_id, id)
) WITH CLUSTERING ORDER BY (id DESC);
Уведомления
Уведомления всегда отсортированы по времени события, к
которому они относятся. Используем clustering order, чтобы данные
физически хранились в нужном порядке.
Уведомления могут быть непросмотренные и просмотренные.
Выделим мутабельную часть данных в отдельную cf. Это
упрощает процесс обновления данных и API.
Уведомления
CREATE TABLE NotificationByUser (
user_id bigint,
shard_part text,
id timeuuid,
type_id int,
.....
PRIMARY KEY ((user_id, shard_part), id)
) WITH CLUSTERING ORDER BY (id DESC);
У одного пользователя может быть очень много уведомлений.
Таким образом у нас могут появится wide rows. Их нужно избегать
(OOM, additional seeks, вот это вот все). Добавим в partition key
дату.
Partition keys
Как правильно выбрать partition key?
Распределение колонок внутри строки должно быть равномерным
в идеале. В одной строке не должно быть слишком много данных
(wide rows).
Варианты:
Сам ключ
Ключ + timebased часть
Ключ + partition (n of partitions fixed or any)
Partition keys
Лайки. У одного объекта очень редко бывает слишком много
лайков. Object id хороший partition key.
Уведомления. У одного пользователя может быть очень много
уведомлений, так как они накапливаются со временем. User id
плохой partition key. Нужно добавить что-то еще. User id + date.
Можно также сделать предположение, что уведомления более-
менее распределены по дням равномерно, поэтому date подходит.
Partition keys
Лента постов по тегу.
CREATE TABLE TagPosts (
tag text,
partition int,
post_id bigint,
PRIMARY KEY((tag, partition), post_id)
) WITH CLUSTERING ORDER BY (post_id DESC);
Просто tag взять нельзя, потому что распределение имеет
выбросы (тренды) и длинный хвост. Date плохая идея, так как
хвост и тренды не зависят от даты.
Partition keys
Неестественное разбиение данных на любое количество partitions
сложнее. При вставке нужно вычислять partition.
CREATE TABLE TagPostsPartitions (
tag text,
partition int,
post_count counter,
PRIMARY KEY (tag, partition)
) WITH CLUSTERING ORDER BY (partition DESC);
Partition keys
Если вы уверены, что кол-во данных по каждому ключу примерно
одинаково, то вычисление partition может быть простым:
key % n partitions
Partition keys
Вопрос: можно ли делать skinny partitions*?
*skinny partition - в одной партиции одна строка
Ответ: да, если паттерн доступа random и
нет range queries.
CREATE TABLE BlackList (
login text,
created bigint,
PRIMARY KEY (login)
);
Вставка
Используйте batches, только если вам
действительно нужна атомарность
Для производительности используйте
асинхронные операции (в драйвере) с
одиночными запросами*
*http://lostechies.com/ryansvihla/2014/08/28/cassandra-batch-loading-
without-the-batch-keyword/
Удаление
CREATE TABLE Queues (
queue_id bigint,
enqueued timeuuid,
PRIMARY KEY (queue_id, enqueued)
);
Классический anti-pattern!
Удаление
Как и в любом log-structure engine, данные физически сразу не
удаляются. Удаленные данные будут помечены, как tombstone, и
через некоторое время (настраивается) будут физически удалены
при очередном compaction.
Операция DELETE по ключу ввполняется за O(1).
Операция выборки вида:
select * from Queues where queue_id = 42 order by enqueued limit 1
может выполняться за O(n).
Удаление
Думайте про удаление заранее
Старайтесь удалять партиции целиком
Избегайте RMW
Делайте операции идемпотентными и
переписывайте данные
Используйте counter columns
Используйте транзакции осторожно, они
замедляют производительность и все
равно не ACID
Вопросы
https://facebook.com/denis.gabaydulin
(messanger)
gabaden@gmail.com

More Related Content

What's hot (11)

PPTX
Apache Cassandra. Ещё одно NoSQL хранилище (Владимир Климонтович)
Ontico
 
PDF
DF1 - BD - Baranov - Mining Large Datasets with Apache Spark
MoscowDataFest
 
PPTX
Cassandra db
Andrei Poliakov
 
PDF
Блеск и нищета распределённых кэшей
aragozin
 
PDF
Apache spark
Anton Anokhin
 
PPTX
Azure for IT pro - TechDays Armenia
Alexey Bokov
 
PDF
Архитектура бесконечного хранилища для пользовательского контента — Артём Сок...
Yandex
 
PDF
IBM Cloudant и Apache CouchDB: NoSQL базы данных эпохи облаков
Maxim Zinal
 
PPTX
презентация
Andrey Arbuzov
 
PDF
HappyDev'15 Keynote: Когда все данные станут большими...
Alexey Zinoviev
 
PDF
BaaS - резервное копирование в облако
Vadim Gabel
 
Apache Cassandra. Ещё одно NoSQL хранилище (Владимир Климонтович)
Ontico
 
DF1 - BD - Baranov - Mining Large Datasets with Apache Spark
MoscowDataFest
 
Cassandra db
Andrei Poliakov
 
Блеск и нищета распределённых кэшей
aragozin
 
Apache spark
Anton Anokhin
 
Azure for IT pro - TechDays Armenia
Alexey Bokov
 
Архитектура бесконечного хранилища для пользовательского контента — Артём Сок...
Yandex
 
IBM Cloudant и Apache CouchDB: NoSQL базы данных эпохи облаков
Maxim Zinal
 
презентация
Andrey Arbuzov
 
HappyDev'15 Keynote: Когда все данные станут большими...
Alexey Zinoviev
 
BaaS - резервное копирование в облако
Vadim Gabel
 

Viewers also liked (6)

PPTX
Cassandra database design best practises
Sandeep Sharma IIMK Smart City,IoT,Bigdata,Cloud,BI,DW
 
PPTX
Presentation of Apache Cassandra
Nikiforos Botis
 
PDF
C* Summit 2013: How Not to Use Cassandra by Axel Liljencrantz
DataStax Academy
 
PDF
Cassandra at NoSql Matters 2012
jbellis
 
PPTX
Learning Cassandra
Dave Gardner
 
PDF
Value Proposition Design
Yves Pigneur
 
Cassandra database design best practises
Sandeep Sharma IIMK Smart City,IoT,Bigdata,Cloud,BI,DW
 
Presentation of Apache Cassandra
Nikiforos Botis
 
C* Summit 2013: How Not to Use Cassandra by Axel Liljencrantz
DataStax Academy
 
Cassandra at NoSql Matters 2012
jbellis
 
Learning Cassandra
Dave Gardner
 
Value Proposition Design
Yves Pigneur
 
Ad

Similar to Cassandra design patterns (20)

PDF
Олег Анастасьев "Ближе к Cassandra". Выступление на Cassandra Conf 2013
it-people
 
PPT
Алексей Чумаков. Apache Cassandra на реальном проекте
Volha Banadyseva
 
PDF
За гранью NoSQL: NewSQL на Cassandra
odnoklassniki.ru
 
PDF
Cassandra
Vadim Tsesko
 
PPTX
apache cassandra и подруга её scylla
Daniel Podolsky
 
PDF
Базы данных. Cassandra
Vadim Tsesko
 
PDF
Technopolis.NoSQL 03 Cassandra
Vadim Tsesko
 
PDF
Aleksey Yeschenko "Моделирование данных с помощью CQL3". Выступление на Cassa...
it-people
 
PDF
Cравнительный анализ хранилищ данных (Олег Царев, Кирилл Коринский)
Ontico
 
PDF
Кеширование данных в БД
Александр Ежов
 
PPTX
Cassandra:Курс молодого бойца
Igor Khokhryakov
 
PPTX
Cassandra
Ilya Medvedev
 
PDF
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Строим N...
IT-Portfolio
 
PDF
Велосипедостраительство в NoSQL, строим собственное NoSQL хранилище
Alexandre Kalendarev
 
PPTX
Безболезненный Fallback cache на Scala / Олег Нижников (Tinkoff.ru)
Ontico
 
PDF
Сравнительный анализ хранилищ данных, Олег Царев, Кирилл Коринский
Fuenteovejuna
 
PPTX
Apache cassandra (rus)
Dmitriy Gutman
 
PPT
Как устроен NoSQL, Андрей Аксенов (Sphinx)
Ontico
 
PPT
phpConf 2010 Классификация систем хранения
Slach
 
PDF
Обзор перспективных баз данных для highload / Юрий Насретдинов
Ontico
 
Олег Анастасьев "Ближе к Cassandra". Выступление на Cassandra Conf 2013
it-people
 
Алексей Чумаков. Apache Cassandra на реальном проекте
Volha Banadyseva
 
За гранью NoSQL: NewSQL на Cassandra
odnoklassniki.ru
 
Cassandra
Vadim Tsesko
 
apache cassandra и подруга её scylla
Daniel Podolsky
 
Базы данных. Cassandra
Vadim Tsesko
 
Technopolis.NoSQL 03 Cassandra
Vadim Tsesko
 
Aleksey Yeschenko "Моделирование данных с помощью CQL3". Выступление на Cassa...
it-people
 
Cравнительный анализ хранилищ данных (Олег Царев, Кирилл Коринский)
Ontico
 
Кеширование данных в БД
Александр Ежов
 
Cassandra:Курс молодого бойца
Igor Khokhryakov
 
Cassandra
Ilya Medvedev
 
16 декабря, DEV {highload} - конференция о Highload веб-разработке, "Строим N...
IT-Portfolio
 
Велосипедостраительство в NoSQL, строим собственное NoSQL хранилище
Alexandre Kalendarev
 
Безболезненный Fallback cache на Scala / Олег Нижников (Tinkoff.ru)
Ontico
 
Сравнительный анализ хранилищ данных, Олег Царев, Кирилл Коринский
Fuenteovejuna
 
Apache cassandra (rus)
Dmitriy Gutman
 
Как устроен NoSQL, Андрей Аксенов (Sphinx)
Ontico
 
phpConf 2010 Классификация систем хранения
Slach
 
Обзор перспективных баз данных для highload / Юрий Насретдинов
Ontico
 
Ad

Cassandra design patterns

  • 2. Для кого доклад Для разработчиков, которые уже знают что такое Cassandra, для чего она нужна и попробовали ее использовать.
  • 3. Cassandra. Internals. Cassandra имеет внутри структуру хранения, похожую на lsm tree + wal. Верхний уровень - memtable (sorted by row key, btree-like). Нижний уровень - disk (sstable + bloom filter).
  • 4. Cassandra. Java point of view. SortedMap<RowKey, SortedMap<ColumnKey, ColumnValue>>
  • 7. Cassandra. Сильные стороны. Почти линейная масштабируемость записи и чтения Не нужно backup, все восстанавливается на лету Есть поддержка нескольких ДЦ Настраиваемая модель (в терминах CAP) Стабильный продукт с первоклассным community
  • 8. Нет ACID транзакций Частое удаление данных это проблема Нет хороших secondary index* * Индексы сейчас улучшаются: https://github.com/xedin/sasi и CASSANDRA- 10661) Cassandra. Слабые стороны.
  • 9. Лайки CREATE TABLE LikedByObject( user_id bigint, object_id bigint, created bigint, PRIMARY KEY (object_id, user_id) ); CREATE TABLE LikedByUser( user_id bigint, object_id bigint, created bigint, type_id int, PRIMARY KEY ((user_id, type_id), object_id) );
  • 10. Лайки Выбрать всех кто лайкал объект select * from LikedByObject where object_id = 42 Выбрать все что лайкал пользователь select * from LikedByUser where user_id = 42 and type_id in (1, 2, 3)
  • 11. Лайки Нет secondary index, используем materialized view. Почти всегда копирование данных более предпочтительно, так как самое затратное при чтении данных с диска это seek. Прочитать чуть больше данных, но из одного место быстрее, чем из двух.
  • 13. Уведомления CREATE TABLE NotificationByUser ( user_id bigint, shard_part text, id timeuuid, type_id int, ..... PRIMARY KEY ((user_id, shard_part), id) ) WITH CLUSTERING ORDER BY (id DESC); CREATE TABLE NotificationByUserAndType ( ..... PRIMARY KEY ((user_id, type_id, shard_part), id) ) WITH CLUSTERING ORDER BY (id DESC); CREATE TABLE NotificationSeen ( user_id bigint, id timeuuid, value boolean, PRIMARY KEY (user_id, id) ) WITH CLUSTERING ORDER BY (id DESC);
  • 14. Уведомления Уведомления всегда отсортированы по времени события, к которому они относятся. Используем clustering order, чтобы данные физически хранились в нужном порядке. Уведомления могут быть непросмотренные и просмотренные. Выделим мутабельную часть данных в отдельную cf. Это упрощает процесс обновления данных и API.
  • 15. Уведомления CREATE TABLE NotificationByUser ( user_id bigint, shard_part text, id timeuuid, type_id int, ..... PRIMARY KEY ((user_id, shard_part), id) ) WITH CLUSTERING ORDER BY (id DESC); У одного пользователя может быть очень много уведомлений. Таким образом у нас могут появится wide rows. Их нужно избегать (OOM, additional seeks, вот это вот все). Добавим в partition key дату.
  • 16. Partition keys Как правильно выбрать partition key? Распределение колонок внутри строки должно быть равномерным в идеале. В одной строке не должно быть слишком много данных (wide rows). Варианты: Сам ключ Ключ + timebased часть Ключ + partition (n of partitions fixed or any)
  • 17. Partition keys Лайки. У одного объекта очень редко бывает слишком много лайков. Object id хороший partition key. Уведомления. У одного пользователя может быть очень много уведомлений, так как они накапливаются со временем. User id плохой partition key. Нужно добавить что-то еще. User id + date. Можно также сделать предположение, что уведомления более- менее распределены по дням равномерно, поэтому date подходит.
  • 18. Partition keys Лента постов по тегу. CREATE TABLE TagPosts ( tag text, partition int, post_id bigint, PRIMARY KEY((tag, partition), post_id) ) WITH CLUSTERING ORDER BY (post_id DESC); Просто tag взять нельзя, потому что распределение имеет выбросы (тренды) и длинный хвост. Date плохая идея, так как хвост и тренды не зависят от даты.
  • 19. Partition keys Неестественное разбиение данных на любое количество partitions сложнее. При вставке нужно вычислять partition. CREATE TABLE TagPostsPartitions ( tag text, partition int, post_count counter, PRIMARY KEY (tag, partition) ) WITH CLUSTERING ORDER BY (partition DESC);
  • 20. Partition keys Если вы уверены, что кол-во данных по каждому ключу примерно одинаково, то вычисление partition может быть простым: key % n partitions
  • 21. Partition keys Вопрос: можно ли делать skinny partitions*? *skinny partition - в одной партиции одна строка Ответ: да, если паттерн доступа random и нет range queries. CREATE TABLE BlackList ( login text, created bigint, PRIMARY KEY (login) );
  • 22. Вставка Используйте batches, только если вам действительно нужна атомарность Для производительности используйте асинхронные операции (в драйвере) с одиночными запросами* *http://lostechies.com/ryansvihla/2014/08/28/cassandra-batch-loading- without-the-batch-keyword/
  • 23. Удаление CREATE TABLE Queues ( queue_id bigint, enqueued timeuuid, PRIMARY KEY (queue_id, enqueued) ); Классический anti-pattern!
  • 24. Удаление Как и в любом log-structure engine, данные физически сразу не удаляются. Удаленные данные будут помечены, как tombstone, и через некоторое время (настраивается) будут физически удалены при очередном compaction. Операция DELETE по ключу ввполняется за O(1). Операция выборки вида: select * from Queues where queue_id = 42 order by enqueued limit 1 может выполняться за O(n).
  • 25. Удаление Думайте про удаление заранее Старайтесь удалять партиции целиком
  • 26. Избегайте RMW Делайте операции идемпотентными и переписывайте данные Используйте counter columns Используйте транзакции осторожно, они замедляют производительность и все равно не ACID