Практически во всех случаях первичные ключи не являются частью вашего бизнеса. Конечно, у вас могут быть некоторые важные объекты, с которыми сталкиваются пользователи, с уникальными индексами ( UserName
для пользователей или OrderNumber
для заказов), но в большинстве случаев нет никакой необходимости явно идентифицировать доменные объекты по одному значению или набору значений кому-либо, кроме, возможно, административный пользователь. Даже в этих исключительных случаях, особенно если вы используете глобальные уникальные идентификаторы (GUID) , вам больше понравится или вы захотите использовать альтернативный ключ, чем раскрывать сам первичный ключ.
Таким образом, если мое понимание доменного дизайна является точным, первичные ключи не должны и, следовательно, не должны быть раскрыты, и хорошее избавление. Они безобразны и ограничивают мой стиль. Но если мы решим не включать первичные ключи в модель предметной области, это приведет к следующим последствиям:
- Наивно, объекты передачи данных (DTO), которые происходят исключительно из комбинаций моделей предметной области, не будут иметь первичных ключей
- Входящие DTO не будут иметь первичного ключа
Итак, можно ли с уверенностью сказать, что если вы действительно намерены сохранять чистоту и исключать первичные ключи в своей доменной модели, вы должны быть готовы обрабатывать каждый запрос с точки зрения уникальных индексов этого первичного ключа?
Иными словами, какое из следующих решений является правильным подходом к идентификации конкретных объектов после удаления PK в моделях доменов?
- Возможность идентифицировать объекты, с которыми вам нужно иметь дело, с помощью других атрибутов.
- Получение первичного ключа обратно в DTO; то есть, устранение PK при отображении из постоянства в домен, а затем рекомбинирование PK при отображении из домена в DTO?
РЕДАКТИРОВАТЬ: Давайте сделаем это конкретным.
Скажем , моя модель домена , VoIPProvider
который включает в себя такие области , как Name
, Description
, URL
, а также ссылки нравится ProviderType
, PhysicalAddress
и Transactions
.
Теперь предположим, что я хочу создать веб-сервис, который позволит привилегированным пользователям управлять VoIPProvider
s.
Возможно, в этом случае удобный идентификатор пользователя бесполезен; В конце концов, поставщики VoIP - это компании, чьи имена, как правило, различны в компьютерном смысле и даже достаточно различны в человеческом смысле по деловым причинам. Поэтому может быть достаточно сказать, что уникальность VoIPProvider
полностью определяется (Name, URL)
. Итак, теперь давайте скажем, что мне нужен метод, PUT api/providers/voip
чтобы привилегированные пользователи могли обновлять VoIP
поставщиков. Они отправляют VoIPProviderDTO
, который включает в себя многие, но не все поля из VoIPProvider
, в том числе потенциально некоторые. Тем не менее, я не могу читать их мысли, и они все еще должны сказать мне, о каком поставщике мы говорим.
Кажется, у меня есть 2 (возможно, 3) варианта:
- Включите первичный ключ или альтернативный ключ в мою модель домена и отправьте его в DTO, и наоборот
- Определите поставщика, о котором мы заботимся, с помощью уникального индекса, например:
(Name, Url)
- Представьте некоторый промежуточный объект, который всегда может отображаться между постоянным уровнем, доменом и DTO таким образом, который не раскрывает подробности реализации о постоянном уровне - скажем, путем введения временного идентификатора в памяти при переходе от домена к DTO и обратно,