Я новичок в TDD и ATDD и пытаюсь понять связь между пользовательской историей и ее критериями приемлемости. Для контекста я создаю трехуровневое приложение на C# с внешним интерфейсом MVC.
Скажем, например, что у меня есть следующая пользовательская история:
Чтобы обеспечить правильный ввод данных о емкости Как лицо, обновляющее эти данные, я хочу получать обратную связь, когда введенные данные не соответствуют нашей деятельности. правила.
Для меня имеет смысл разбить это на части и определить, что такое «данные о емкости», и бизнес-правила, которые регулируют это.
Например, может быть, у него есть свойство «Количество машин», которое должно быть больше нуля.
Чего я хочу избежать, так это тестирования фреймворка, и если я буду следовать ему правильно, я хочу проверить, правильно ли реализована эта бизнес-логика, т. е. что:
- Бизнес-правила («Количество машин должно быть больше нуля» и другие) корректно реализованы в кодовой базе.
- Если бизнес-правило нарушается, пользователь получает предупреждение об этой ошибке.
Я полагаю, что мог бы проверить правило № 2, проверив, что недопустимое состояние модели в контроллере перенаправляет, например, на ту же страницу - и есть МНОЖЕСТВО примеров этого.
Однако разве для этого не требуется украшать модель представления — и что в конечном итоге это реализует бизнес-правило с точки зрения пользователя? (таким образом удовлетворяя #1?)
Скажем, у меня есть следующий вид оператора/модуля-теста:
[Test]
public void GivenCapacityModelWhenNumMachinesZeroOrLessThenModelShouldBeInvalid()
{
// Given
IValidatorThing validator = new ValidatorThing(); //What enforces the rule? Should this be a controller service? Or a decorator such as [Range(0.000001,1000000)]? Doesn't each require different testing methods?
var invalidModel = new CapacityModel(); // Or the viewmodel?
double zeroValue = 0.000001;
invalidModel.NumMachines = zeroValue;
// When
var modelIsValid = ValidatorThing.validateModel(invalidModel);
// Then
Assert.IsFalse(modelIsValid);
}
Вышеупомянутое, конечно, не скомпилируется. Я пока не упомянул какой-либо конкретный фреймворк для имитации или исправления, чтобы не усложнять задачу. Итак, чтобы этот тест хотя бы скомпилировался (но все равно не прошел), мне нужно принять несколько решений:
- Должна ли CapacityModel быть моделью представления? Или DTO из сервисного уровня? Или класс метаданных на уровне DAL? Я могу реализовать любой из них и пройти тест... но что я действительно должен тестировать?
- Проверяет ли «валидатор» поведение службы, которая проверяет это свойство модели? Или аннотации данных в CapacityModel? Опять же, что я действительно должен тестировать в контексте трехуровневого приложения?
Некоторые вещи, которые следует учитывать: одна вещь, которую я буду знать, это то, что таблицы базы данных будут иметь ограничения, описывающие эти правила, поэтому может показаться, что цель этого правила на самом деле состоит в том, чтобы сообщить эти правила всем, кто с помощью приложения. В таком случае, могу ли я с уверенностью предположить, что это нарушит DRY, если правила появятся в трех местах: модель представления, объект данных и таблицы базы данных.
Причина, по которой у нас есть эти правила в базе данных, заключается в том, что мы хотим гарантировать, что если администратор базы данных должен возиться с записями, правила не будут случайно нарушены. Однако, насколько мне известно, нет хорошего способа перевести эти правила CONSTRAINT в DAL приложения... поэтому я полагаю, что их нужно будет повторить хотя бы еще раз в приложении, чтобы передать их Пользователь.
Итак, если бы мне нужно было написать модульный тест для выполнения бизнес-правила, разве я не писал бы только для того, чтобы убедиться, что правила отражают базу данных? И отдельно также написать модульный тест, который гарантирует, что пользователю отображается правильное сообщение?
Любое руководство, которое вы можете предложить, было бы замечательно. Я хочу чувствовать, что принятые мной решения были разумными, или, по крайней мере, иметь представление об альтернативных способах решения проблемы лучше.
Спасибо,
Лоуренс
РЕДАКТИРОВАТЬ:
Итак, в конечном счете, я пытался внедрить централизованный способ управления проверкой в приложении, чтобы иметь возможность разделения задач, т. е. чтобы контроллер заботился только о маршрутизации, модели представления заботились только об отображении данных, валидаторы заботились только о проверка и т. д., в отличие от проверки, например, в модели представления.
Я нашел очень полезную статью это помогло мне понять, как это сделать, используя существующую инфраструктуру MVC. Надеюсь, это поможет другим, изучающим такие типы сценариев.