Предположим, что у меня есть данные о заказах клиентов, которые мне нужны, и я хотел бы сделать некоторые отчеты по этим данным. Все заказы клиентов сохраняются в таблице Кассандры, так что я могу получить все заказы данного клиента:Как сделать моделирование данных Cassandra для подсчета совокупности?
TABLE customer_orders
store_id uuid,
customer_id text,
order_id text,
order_amount int,
order_date timestamp,
PRIMARY: KEY (store_id, customer_id)
Но я также хотел бы, чтобы найти все клиент с определенным количеством заказов. В идеале я хотел бы иметь это в готовой к запросу таблице в Кассандре. Например, «получите всех клиентов, у которых есть 1 заказ».
Поэтому у меня есть таблица вроде этого:
TABLE order_count_to_customer
store_id uuid,
order_count int,
customer_id text
PRIMARY KEY ((store_id, order_count), customer_id)
Так идея, когда заказ поступает как из этих таблиц, которые будут обновлены.
Так создать третью таблицу:
TABLE customer_to_orders_count
store_id uuid,
customer_id text,
orders_count counter,
PRIMARY KEY (store_id, orders_count)
Когда заказ прибывает:
Я сохранить его в первой таблице
Затем обновляют счетчик в третьей таблице путем увеличения его на 1.
Затем я прочитал co unter в третьей таблице и вставьте новую запись во вторую таблицу.
Когда мне нужно найти всех клиентов с заданным количеством заказов, я просто запрашиваю вторую таблицу.
Проблема в том, что счетчики не являются атомарными и согласованными. Если я обновляю счетчик, скажем 3, нет гарантии, что когда я его прочитаю, чтобы обновить вторую таблицу, это будет 3. Это может быть 2. Даже если я прочитаю счетчик, прежде чем я сделаю обновление счетчика, может быть некоторое значение с нескольких шагов назад. Так что никаких гарантий тоже. Обратите внимание, что я знаю об ограничениях счетчиков в Кассандре, и я не спрашиваю, как решить проблему с помощью счетчиков.
Я скорее даю этот пример, чтобы попросить дать общий совет относительно того, как моделировать данные, чтобы иметь возможность делать подсчет совокупности. Я могу, конечно, использовать Spark для выполнения агрегированных запросов непосредственно в первой таблице в моем примере. Но мне кажется, что может быть и более умный способ сделать это, а также Spark будет включать в себя сбор всех данных таблицы в памяти.