Наилучший метод для сопоставления произвольных пар ключ / значение со строкой таблицы в БД Postgres? - PullRequest
4 голосов
/ 20 января 2011

Для моей базы данных Postgres 8.4 у меня есть совершенно реляционная схема данных, но мне нужна возможность связать произвольные пары ключ / значение с несколькими моими таблицами, причем назначенные ключи меняются в зависимости от строки.Пары ключ / значение генерируются пользователем, поэтому у меня нет возможности заранее их прогнозировать или обсуждать упорядоченные изменения схемы.

У меня есть следующие требования:

  • Ключ / значениепары будут часто читаться, записываться время от времени.Чтение должно быть достаточно быстрым.
  • Нет необходимости (присутствует) запрашивать ключи или значения.(Но это может пригодиться когда-нибудь.)

Я вижу следующие возможные решения:

  1. Атрибут-значение-значение рисунок / антипаттерн . Раздражает, но раздражение обычно компенсируется моим ORM.
  2. Хранение пар ключ / значение в виде сериализованных данных JSON в текстовом столбце. Простое решение, и снова ORM пригодится, но я могу попрощаться с потребностями моего будущего себя в запросах.
  3. Хранение пар ключ / значение в некоторых других NoSQL db--вероятно, ключ / значение или хранилище документов. ORM здесь не поможет.Мне придется самостоятельно управлять отдельными запросами (и надвигающимися проблемами целостности данных?).

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

Ответы [ 3 ]

7 голосов
/ 20 января 2011

Именно для этого и предназначен тип данных hstore в PostgreSQL.
http://www.postgresql.org/docs/current/static/hstore.html

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

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

А с 9.0 стало еще лучше, потому что некоторые ограничения по размеру были сняты.

1 голос
/ 28 апреля 2011

hstore, как правило, является хорошим решением для этого, но лично я предпочитаю использовать простой ключ: таблицы значений.Одна таблица с определениями, другая таблица со значениями и отношение для привязки значений к определению и отношение для привязки значений к определенной записи в другой таблице.

Почему я против hstore?Потому что это как шаблон реестра.Часто упоминается как пример анти-паттерна.Вы можете поместить туда все, что трудно проверить, если это все еще необходимо, при загрузке целой строки (особенно в ORM) загружается весь hstore, что может иметь много мусора и очень мало смысла.Не говоря уже о том, что необходимо преобразовать тип данных hstore в ваш языковой тип и преобразовать обратно при сохранении.Таким образом, вы получаете некоторые издержки при преобразовании типов.

Итак, на самом деле я пытаюсь преобразовать все hstores в компании, на которую я работаю, в простые таблицы ключ-значение.Это не такая сложная задача, потому что структуры, хранящиеся здесь в hstore, огромны (или, по крайней мере, велики), а чтение / запись объекта тратит огромные накладные расходы на вызовы функций.Таким образом, выполняя простую задачу, такую ​​как «select * from base_product, где id = 1;»заставляет сервер потеть и сильно ухудшает производительность.Хочу отметить, что проблема производительности не в том, что db, а в том, что python должен несколько раз преобразовывать результаты, полученные от postgres.Пока ключ: значение не требует такого преобразования.

0 голосов
/ 20 января 2011

Поскольку вы не управляете данными, не пытайтесь их переусердствовать.

Для скорости вы должны периодически делать «кластеризовать sometable_attributes с использованием sometable_attributes_idx», чтобы все атрибуты для одной строки были физически близки.

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