В моей базе данных две таблицы:
Wiki
WikiId
...
WikiUser
WikiUserId (PK)
WikiId
UserId
IsOwner
...
Эти таблицы имеют отношение один (Wiki) к многим (WikiUser).
Как мне реализовать следующее бизнес-правило в моих классах сущностей LINQ:
"У Вики должен быть ровно один владелец?"
Я попытался обновить таблицы следующим образом:
Wiki
WikiId (PK)
OwnerId (FK to WikiUser)
...
WikiUser
WikiUserId (PK)
WikiId
UserId
...
Это усиливает ограничение, но если я удаляю запись WikiUser владельца из коллекции WikiUser Wiki, я получаю уродливое SqlException. Кажется, что это было бы трудно поймать и обработать в интерфейсе.
Есть ли способ выполнить эту проверку перед генерацией SqlException? Лучший способ структурировать мою базу данных? Способ поймать и перевести SqlException во что-то более полезное?
Редактировать: Я бы предпочел сохранить правила валидации в классах сущностей LINQ, если это возможно.
Редактировать 2: Еще несколько подробностей о моей конкретной ситуации.
В моем приложении пользователь должен иметь возможность удалять пользователей из вики. Они должны иметь возможность удалить любого пользователя, кроме пользователя, который в настоящее время помечен как «владелец» вики (у вики всегда должен быть ровно один владелец).
В моей логике управления я хотел бы использовать что-то вроде этого:
wiki.WikiUsers.Remove(wikiUser);
mRepository.Save();
И перенести все нарушенные правила на уровень пользовательского интерфейса.
То, что я не хочу делать, это:
if(wikiUser.WikiUserId != wiki.OwnerId) {
wiki.WikiUsers.Remove(wikiUser);
mRepository.Save();
}
else {
//Handle errors.
}
Я также не особо хочу перемещать код в свой репозиторий (потому что нет ничего, что указывало бы на то, что он не использовал встроенные функции Remove), поэтому я также НЕ хочу, чтобы код был таким:
mRepository.RemoveWikiUser(wiki, wikiUser)
mRepository.Save();
Это было бы приемлемо:
try {
wiki.WikiUsers.Remove(wikiUser);
mRepository.Save();
}
catch(ValidationException ve) {
//Display ve.Message
}
Но это отлавливает слишком много ошибок:
try {
wiki.WikiUsers.Remove(wikiUser);
mRepository.Save();
}
catch(SqlException se) {
//Display se.Message
}
Я бы также НЕ ПРЕДПОЧЛЕНО, чтобы явно вызывать проверку бизнес-правил (хотя это может стать необходимым):
wiki.WIkiUsers.Remove(wikiUser);
if(wiki.CheckRules()) {
mRepository.Save();
}
else {
//Display broken rules
}