Візьмемо ще один приклад, який менш загрожує концепціями та очікуваннями. У мене тут перерахунок, і це набір пріоритетів для помилки.
Яке значення ви зберігаєте в базі даних?
Таким чином, я міг би зберігати 'C'
, 'H'
, 'M'
і 'L'
в базі даних. Або 'HIGH'
тощо. У цьому виникає проблема строго типізованих даних. Існує відомий набір допустимих значень, і якщо ви не зберігаєте цей набір у базі даних, це може бути важко працювати.
Чому ви зберігаєте дані в коді?
У вас є List<String> priorities = {'CRITICAL', 'HIGH', 'MEDIUM', 'LOW'};
чи щось для цього в коді. Це означає, що у вас є різні відображення цих даних у відповідному форматі (ви вставляєте всі шапки в базу даних, але ви їх відображаєте як Critical
). Ваш код також важко локалізувати. Ви прив'язали представлення бази даних ідеї до рядка, який зберігається в коді.
Де б ви не мали доступу до цього списку, вам потрібно мати копію коду або клас із купою констант. Жоден з них не є хорошими варіантами. Не слід також забувати, що є й інші програми, які можуть використовувати ці дані (які можуть бути написані іншими мовами - у веб-додатку Java використовується система звітності Crystal Reports та дані, що містять пакетне завдання Perl ). Двигун звітів повинен знати дійсний перелік даних (що відбувається, якщо в 'LOW'
пріоритеті нічого не позначено, і вам потрібно знати, що це дійсний пріоритет для звіту?), А пакетне завдання матиме інформацію про те, що є дійсним значення є.
Гіпотетично, ви могли б сказати : «ми єдина мова магазин - все написано в Java» і є один .jar, що містить цю інформацію , - але тепер це означає , що ваші додатки тісно пов'язані один з одним і що .jar , що містить дані. Вам потрібно буде випустити звітну частину та частину пакетного оновлення разом із веб-додатком щоразу, коли відбудеться зміна - і сподіваємось, що цей випуск пройде гладко для всіх частин.
Що відбувається, коли ваш начальник хоче іншого пріоритету?
Ваш начальник сьогодні прийшов. Новий пріоритет - CEO
. Тепер вам потрібно перейти і змінити весь код і зробити перекомпіляцію та повторне розміщення.
За допомогою підходу "перерахування таблиці" ви оновлюєте список перерахунків, щоб мати новий пріоритет. Весь код, який отримує список, витягує його з бази даних.
Дані рідко стоять окремо
З пріоритетами клавіші даних в інші таблиці, які можуть містити інформацію про робочі процеси, або які можуть встановлювати цей пріоритет чи що.
Повернувшись до гендеру, про який ми згадували у запитанні: Стать має посилання на використовувані займенники: he/his/him
і she/hers/her
..., і ви хочете уникнути жорсткого кодування цього коду. І тоді ваш бос приходить, і вам потрібно додати, що ви отримали 'OTHER'
гендерну групу (щоб це було просто), і вам потрібно пов’язати цю стать з they/their/them
... і ваш начальник бачить, що має Facebook і ... ну так.
Обмежуючи себе строко типізованим бітом даних, а не таблицею перерахувань, вам тепер потрібно було повторити цю рядок у купі інших таблиць, щоб підтримувати цей зв'язок між даними та іншими його бітами.
Що з іншими сховищами даних?
Незалежно від того, де ви зберігаєте це, існує той самий принцип.
- Ви можете мати файл
priorities.prop
, у якому є список пріоритетів. Ви читаєте цей список у файлі властивостей.
Ви можете мати базу даних сховища документів (наприклад, CouchDB ), в якій є запис enums
(а потім написати функцію перевірки в JavaScript ):
{
"_id": "c18b0756c3c08d8fceb5bcddd60006f4",
"_rev": "1-c89f76e36b740e9b899a4bffab44e1c2",
"priorities": [ "critical", "high", "medium", "low" ],
"severities": [ "blocker", "bad", "annoying", "cosmetic" ]
}
У вас може бути XML-файл з трохи схемою:
<xs:element name="priority" type="priorityType"/>
<xs:simpleType name="priorityType">
<xs:restriction base="xs:string">
<xs:enumeration value="critical"/>
<xs:enumeration value="high"/>
<xs:enumeration value="medium"/>
<xs:enumeration value="low"/>
</xs:restriction>
</xs:simpleType>
Основна ідея така ж. Сам сховище даних - це те, де список дійсних значень потрібно зберігати та застосовувати. Розмістивши його тут, простіше міркувати про код і дані. Вам не потрібно турбуватися про те, щоб захисно перевіряти, що ви маєте кожен раз (це верхній регістр? Чи нижній? Чому chritical
в цьому стовпці є тип? Тощо ...), оскільки ви знаєте, що ви повертаєтесь із сховища даних саме те, що в сховищі даних очікує, що ви надішлете інакше - і ви можете запитати у сховищі даних щодо списку дійсних значень.
Винос
Набір допустимих значень - це дані , а не код. Ви дійсно повинні прагнути до DRY коду - але проблема дублювання в тому , що ви дублювати дані в коді, а не поважаючи своє місце в якості даних і зберігання в базі даних.
Це спрощує написання декількох додатків проти сховища даних і уникає випадків, коли вам потрібно буде розгорнути все, що щільно пов'язане з самими даними - адже ви не зв'язали свій код із даними.
Це полегшує тестування програм, тому що вам не доведеться повторно перевіряти всю програму, коли CEO
додається пріоритет - тому що у вас немає коду, який би дбав про фактичне значення пріоритету.
Можливість міркувати про код і дані незалежно один від одного полегшує пошук та виправлення помилок під час обслуговування.