Как вы структурируете конфигурационные данные в базе данных?

StackOverflow https://stackoverflow.com/questions/240428

Вопрос

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

  1. Вы можете создать таблицу, в которой хранятся пары ключ / значение, где key - это имя параметра конфигурации, а value - его значение.Плюсы этого в том, что добавлять новые значения легко, и вы можете использовать те же процедуры для установки / получения данных.Недостатками являются то, что у вас есть нетипизированные данные в качестве значения.
  2. В качестве альтернативы вы можете жестко запрограммировать таблицу конфигурации, в которой каждый столбец будет именем значения и его типом данных.Недостатком этого является дополнительное обслуживание при настройке новых значений, но это позволяет вам иметь введенные данные.

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

Обновить

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

Это было полезно?

Решение

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

Но да, я бы выбрал вариант 1, если конфигурационные файлы не подходят.Еще одно преимущество варианта 1 заключается в том, что вы можете очень легко преобразовать его в объект Dictionary (или эквивалент) для использования в вашем приложении.

Другие советы

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

Что еще более важно, учитывайте эти моменты при настройке:

  • Иерархия:Очевидно, что конфигурация выиграет от иерархии
  • Управление версиями:Подумайте о преимуществе возможности отката к конфигурации, действовавшей на определенную дату.
  • Распределение:В какой-то момент было бы неплохо иметь возможность объединять приложения в кластеры.Некоторые свойства, вероятно, должны быть локальными для каждого узла в кластере.
  • Документация:В зависимости от того, есть ли у вас веб-инструмент или что-то в этом роде, вероятно, неплохо хранить документацию о свойстве рядом с кодом, который его использует.(Аннотации кода очень хороши для этого.)
  • Уведомление:Как код узнает, что где-то в репозитории конфигурации было внесено изменение?

Лично мне нравится перевернутый способ обработки конфигурации, при котором свойства конфигурации вводятся в модули, которые не знают, откуда взялись значения.Таким образом, система управления конфигурацией может быть очень сложной или очень простой в зависимости от ваших (текущих) потребностей.

Я использую вариант 1.

Использование базы данных для конфигурационных данных кажется излишним.

РЕДАКТИРОВАТЬ (извините за слишком длинное поле для комментариев):Конечно, не существует строгих правил относительно того, как вы реализуете какую-либо часть своей программы.Например, отвертки с прорезями подходят для некоторых винтов Philips!Наверное, я судил слишком рано, еще не зная, каков ваш сценарий.

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

Другой сценарий, в котором db может иметь смысл, - это когда у вас есть ферма серверов, где вы хотите, чтобы ваша база данных хранила вашу центральную конфигурацию, но тогда вы можете сделать то же самое с общим сетевым диском, который указывает на файл конфигурации xml.

XML-файл лучше, когда ваша конфигурация иерархически структурирована.Вы можете легко организовать, найти и обновить то, что вам нужно, а в качестве бонуса вы можете управлять версиями конфигурационного файла вместе с вашим исходным кодом!

В общем, все зависит от того, как используются конфигурационные данные.

На этом мое мнение заканчивается ограниченностью знаний о вашем приложении.Я уверен, что вы сможете принять правильное решение.

Я предполагаю, что это больше похоже на опрос, поэтому я скажу о колонковом подходе (вариант 2).Однако это будет зависеть от того, как часто меняется ваша конфигурация, насколько она динамична, сколько в ней данных и т.д.

Я бы, конечно, использовал этот подход для пользовательских конфигураций / предпочтений и т.д.

Мой проект использует таблицу базы данных с четырьмя столбцами:

  1. Идентификатор [pk]
  2. Область применения (по умолчанию "Приложение")
  3. Настройка
  4. Значение

Настройки с областью действия "Приложение" - это глобальные настройки, такие как Максимальное количество одновременных пользователей.

Каждый модуль имеет свою собственную область действия, основанную;таким образом, наши ResultsLoader и UserLoader имеют разные области видимости, но оба имеют параметр с именем 'InputPath'.

Значения по умолчанию либо указаны в исходном коде, либо вводятся через наш контейнер IoC.Если значение не введено или не предоставлено в базе данных, используется значение по умолчанию из кода (если таковое существует).Поэтому значения по умолчанию никогда не сохраняются в базе данных.

У нас это получается довольно хорошо.Каждый раз, когда мы создаем резервную копию базы данных, мы получаем копию конфигурации, что весьма удобно.Эти два фактора всегда синхронизированы.

Выбирайте вариант 2.Вариант 1 - это действительно способ внедрения базы данных поверх базы данных, и это хорошо известный антипаттерн, который просто доставит вам неприятности в долгосрочной перспективе.

Я могу придумать по крайней мере еще два способа:

(a) Создайте таблицу со столбцами key, string-value, date-value, int-value, real-value.Оставьте неиспользуемые типы NULL.

(b) Используйте формат сериализации, такой как XML, YAML или JSON, и сохраните все это в большом двоичном объекте.

Где вы храните параметры конфигурации, необходимые вашему приложению для подключения к базе данных?

Почему бы не сохранить там и другую информацию о конфигурации?

Я бы выбрал вариант 1, если только количество параметров конфигурации не было ОЧЕНЬ маленьким (семь или меньше).

В моей компании мы работаем над использованием первого варианта (простой таблицы, похожей на словарь) с изюминкой.Мы разрешаем замену строк с использованием токенов, которые содержат имя переменной конфигурации, подлежащей замене.

Например, таблица может содержать строки ('строка подключения к базе данных', 'jdbc://%host%...') и ('host', 'foobar').Инкапсуляция этого с помощью простого сервиса или уровня хранимых процедур обеспечивает чрезвычайно простую, но гибкую рекурсивную конфигурацию.Это поддерживает нашу потребность в нескольких изолированных средах (dev, test, prod и т.д.).

В прошлом я использовал как 1, так и 2, и я думаю, что они оба являются ужасными решениями.Я думаю, вариант 2 лучше, потому что он позволяет печатать, но он намного более уродливый, чем вариант 1.Самая большая проблема, с которой я сталкиваюсь, - это управление версиями конфигурационного файла.Вы можете достаточно хорошо версифицировать SQL, используя стандартные системы контроля версий, но объединение изменений обычно проблематично.Если бы у меня была возможность сделать это "правильно", я бы, вероятно, создал кучу таблиц, по одной для каждого типа параметра конфигурации (не обязательно для каждого самого параметра), тем самым получив преимущество ввода и преимущество парадигмы ключ / значение, где это уместно.Таким образом, вы также можете реализовать более продвинутые структуры, такие как списки и иерархии, которые затем будут доступны для прямого запроса приложением вместо того, чтобы загружать конфигурацию и затем каким-то образом преобразовывать ее в памяти.

Я голосую за вариант 2.Прост в понимании и обслуживании.

Вариант 1 хорош для легко расширяемого центрального хранилища.В дополнение к некоторым замечательным предложениям таких людей, как Р.Б., Хьюго и Эллиот, вы также можете рассмотреть:

Включите флаг Global / User setting с полем user или даже полем user / machine (для настроек типа пользовательского интерфейса для конкретной машины).

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

Я использую сочетание опции 2 и столбцов XML в SQL server.Возможно, вы также не захотите добавлять контрольное ограничение, чтобы сохранить таблицу в одной строке.

CREATE TABLE [dbo].[MyOption] (
  [GUID] uniqueidentifier CONSTRAINT [dfMyOptions_GUID] DEFAULT newsequentialid()  ROWGUIDCOL NOT NULL,
  [Logo] varbinary(max) NULL,
  [X] char(1)  CONSTRAINT [dfMyOptions_X] DEFAULT 'X' NOT NULL,
  CONSTRAINT [MyOptions_pk] PRIMARY KEY CLUSTERED ([GUID]),
  CONSTRAINT [MyOptions_ck] CHECK ([X]='X')
)

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

но как насчет формата для одного поля для хранения нескольких параметров конфигурации, которые будут использоваться базой данных?

например, одно поле для каждого пользователя, содержащее все их настройки, связанные с их представлением на доске объявлений (например, порядок сортировки по умолчанию, заблокированные темы и т.д.), и, возможно, другое со всеми их настройками для их темы (например, цвет текста, цвет bg и т.д.)

Хранение иерархии и документов в реляционной базе данных - это безумие.Сначала вы должны либо измельчить их, только для того, чтобы рекомбинировать на более позднем этапе.Или там запихнутая внутрь КЛЯКСА, еще более глупая.

Не используйте реляционную базу данных для нереляционных данных, этот инструмент не подходит.Рассмотрим для этого что-то вроде MongoDB или CouchDB.Безсхемные, нереляционные хранилища данных.Сохраните его как JSON, если он каким-либо образом передается по проводам клиенту, используйте XML для серверной части.

CouchDB предоставляет вам управление версиями "из коробки".

Не храните данные конфигурации в базе данных, если у вас нет на то очень веских причин.Если у вас есть очень веская причина и вы абсолютно уверены, что собираетесь это сделать, вам, вероятно, следует сохранить ее в формате сериализации данных, таком как JSON или YAML (не XML, если только вам действительно не нужен язык разметки для настройки вашего приложения - поверьте мне, вам это не нужно) в виде строки.Затем вы можете просто прочитать строку и использовать инструменты на любом языке, на котором вы работаете, для ее чтения и изменения.Храните строки с временными метками, и у вас будет простая схема управления версиями с возможностью хранения иерархических данных в очень простой системе.Даже если вам не нужны иерархические конфигурационные данные, по крайней мере, сейчас, если они вам понадобятся в будущем, вам не придется менять свой конфигурационный интерфейс, чтобы получить их.Конечно, вы теряете возможность выполнять реляционные запросы к вашим конфигурационным данным, но если вы храните это если у вас много конфигурационных данных, то вы, вероятно, все равно делаете что-то очень неправильное.

Компании, как правило, хранят множество конфигурационных данных для своих систем в базе данных, я не уверен почему, я не думаю, что при принятии таких решений много задумываются.Я не слишком часто вижу, чтобы подобные вещи делались в мире OSS.Даже большим программам OSS, которым требуется множество настроек, таким как Apache, для работы не требуется подключение к базе данных, содержащей таблицу apache_config .Наличие огромного количества настроек, с которыми приходится иметь дело в ваших приложениях, - это неприятный запах кода, хранение этих данных в базе данных просто вызывает больше проблем (как показано в этом потоке).

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top