Какая самая зрелая BDD Framework для .NET?

Мы используем BDD – Behavior Driven Development (с точки зрения Дэна Севера) в качестве механизма регистрации пользовательских тестов приёма и разработки дисков на нескольких проектах с достойным успехом. На сегодняшний день, хотя мы фактически не автоматизировали сами тесты.

Теперь я ищу автоматизацию тестов, но я не уверен, какова структура поведения для поддержки. До сих пор NBehave кажется предвестником, но есть ли другие, над которыми я должен смотреть? Есть ли явный «победитель» на данный момент?

Быстрый ответ

Одним из очень важных моментов для воспитания является то, что есть два варианта развития, управляемого поведением. Эти два варианта: xBehave и xSpec .

xBehave BDD: SpecFlow

SpecFlow (очень похож на огурец из стека Ruby) отлично подходит для облегчения тестов xBehave BDD в качестве критериев приема. Однако он не обеспечивает хороший способ написания поведенческих тестов на уровне единицы. Есть еще несколько инфраструктур тестирования xBehave, но SpecFlow получил много тяги.

xSpec BDD: MSpec

Объективно. Учитывая доступные контекстные спецификации, MSpec был самым длинным и является наиболее широко используемой инфраструктурой контекста / спецификации в сообществе .Net.

Другая инфраструктура xSpec BDD: NSpec

Я лично рекомендовал NSpec (вдохновленный напрямую RSpec для Ruby). Полное раскрытие информации, я являюсь одним из авторов NSpec. Вы можете выполнить BDD, просто используя NUnit или MSTest … но они кажутся короткими (очень сложно создавать контексты постепенно). MSpec также является опцией и является самой зрелой структурой контекста / спецификации для .Net. Но в NSpec есть несколько вещей, которые проще.

Длительный ответ

Два аромата BDD в основном существуют из-за ортогональных преимуществ, которые они обеспечивают.

За и против xBehave (синтаксис GWT)

Pros

  • помогает облегчить разговоры с бизнесом через общий диалект, называемый (например, «Дано ….», «Дано …», «Когда ……, И когда …..», «Тогда …», А потом)
  • общий диалект может быть сопоставлен с исполняемым кодом, который доказывает бизнесу, что вы на самом деле закончили то, что вы сказали, что закончите
  • диалект сжимается, поэтому бизнес должен устранить требования и вписаться в предложения.

Cons

  • В то время как подход xBehave хорош для управления критериями приемлемости высокого уровня, циклы, необходимые для сопоставления английского языка с исполняемым кодом с помощью атрибутов, делают невозможным вытеснение домена на уровне единицы.
  • Отображение общего диалекта в тестах PAINFUL (увеличение вашего регулярного выражения). Каждое предложение, созданное бизнесом, должно быть сопоставлено с исполняемым методом через атрибуты.
  • Общий диалект должен быть жестко контролирован, так что управление картированием не выходит из-под контроля. Каждый раз, когда вы меняете предложение, вы должны найти метод, который непосредственно относится к этому предложению, и исправить соответствие регулярных выражений.

Плюсы и минусы xSpec (Контекст / Спецификация)

Pros

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

Cons

  • Не такой ansible для бизнеса. Давайте посмотрим правде в глаза, бизнес не любит, чтобы устранить то, что они хотят. Если бы мы предоставили им подход, основанный на контекстах к BDD, тогда предложение просто прочитало бы «Just make it work».
  • Все в коде. Контекстная документация переплетается внутри кода (поэтому нам не нужно беспокоиться о привязке английского к коду)
  • Не так читается, учитывая менее ограничительные формулировки.

образцы

Боулинг-Ката – довольно хороший пример.

SpecFlow Sample

Вот что спецификация будет выглядеть в SpecFlow (опять же, это замечательно как тест приемочного испытания, потому что он напрямую связывается с бизнесом):

Функциональный файл

Файл функции является общим диалектом для теста.

 Характеристика: Расчет результатов 
   Чтобы узнать мою работу
   Как игрок
   Я хочу, чтобы система вычислила мой общий балл

 Игра Сценарий: игра Водосточные
   Учитывая новую игру в боулинг
   Когда все мои яйца приземляются в желобе
   Тогда мой общий балл должен быть 0

 Сценарий: одиночный контакт
   Учитывая новую игру в боулинг
   Когда я ударил ровно 1 контакт
   Тогда мой общий балл должен быть 1

Файл определения шага

Файл определения шага – это фактическое выполнение теста, этот файл содержит сопоставления для SpecFlow

[Binding] public class BowlingSteps { private Game _game; [Given(@"a new bowling game")] public void GivenANewBowlingGame() { _game = new Game(); } [When(@"all of my balls are landing in the gutter")] public void WhenAllOfMyBallsAreLandingInTheGutter() { _game.Frames = "00000000000000000000"; } [When(@"I've hit exactly 1 pin")] public void When1PinIsHit() { _game.Frames = "10000000000000000000"; } [Then(@"my total score should be (\d+)")] public void ThenMyTotalScoreShouldBe(int score) { Assert.AreEqual(score, _game.Score); } } 

Пример MSpec, xSpec, Контекст / Спецификация

public class describe_BowlingKata { public static Game game; public class when_all_balls_land_in_the_gutter : describe_BowlingKata { Establish ctx = () => game = new Game(); Because of = () => game.Frames = "00000000000000000000"; It should_have_a_score_of_0 = () => game.Score.ShouldBe(0); } public class when_a_single_pin_is_hit : describe_BowlingKata { Establish ctx = () => game = new Game(); Because of = () => game.Frames = "10000000000000000000"; It should_have_a_score_of_1 = () => game.Score.ShouldBe(1); } }
public class describe_BowlingKata { public static Game game; public class when_all_balls_land_in_the_gutter : describe_BowlingKata { Establish ctx = () => game = new Game(); Because of = () => game.Frames = "00000000000000000000"; It should_have_a_score_of_0 = () => game.Score.ShouldBe(0); } public class when_a_single_pin_is_hit : describe_BowlingKata { Establish ctx = () => game = new Game(); Because of = () => game.Frames = "10000000000000000000"; It should_have_a_score_of_1 = () => game.Score.ShouldBe(1); } } 

NSpec Sample, xSpec, Контекст / Спецификация

Вот пример NSpec одного и того же боулинг-ката:

class describe_BowlingGame : nspec { Game game; void before_each() { game = new Game(); } void when_all_my_balls_land_in_the_gutter() { before = () => game.Frames = "00000000000000000000"; it["should have a score of 0"] = () => game.Score.should_be(0); } void when_a_single_pin_is_it() { before = () => game.Frames = "10000000000000000000"; it["should have a score of 1"] = () => game.Score.should_be(1); } }
class describe_BowlingGame : nspec { Game game; void before_each() { game = new Game(); } void when_all_my_balls_land_in_the_gutter() { before = () => game.Frames = "00000000000000000000"; it["should have a score of 0"] = () => game.Score.should_be(0); } void when_a_single_pin_is_it() { before = () => game.Frames = "10000000000000000000"; it["should have a score of 1"] = () => game.Score.should_be(1); } } 

Поскольку вы делаете все больше и больше BDD, вы обнаружите, что необходимы как xBehave, так и xSpec-ароматы BDD. xBehave больше подходит для тестов Acceptance, xSpec больше подходит для модульных тестов и разработки, ориентированных на домен.

MSpec vs NSpec

Важным фактором должны быть такие объективные показатели, как возраст и стабильность, и я хотел бы призвать всех учитывать это. Но, пожалуйста, также учтите, что более новые frameworks могут обеспечить более сжатые api, лучшее использование языковых конструкций и основываться на уроках, извлеченных для прошлых структур . MSpec предоставляет конструкторы Given, Because, It и Cleanup .. но они стоят за счет: статической инициализации для всех участников, взрыва classа и синтаксически жесткой из-за ее уникального использования делегатов. Вы обнаружите, что простейшие тесты MSpec проще в NSpec. Вот более сложный набор тестов, написанный как в MSpec, так и в NSpec.

Сравнение xUnit, MSpec и NSpec: https://gist.github.com/amirrajan/6701522

Связанные ссылки

RSpec против огурца (рассказы RSpec)

BDD с огурцом и rspec – когда это избыточно?

Проверьте SpecFlow .

Это инструмент, вдохновленный Cucumber, который нацелен на предоставление прагматичного и без трения подхода к разработке, основанному на приемочных испытаниях, и разработке поведенческих разработок для .NET-проектов.

Интеграция VisualStudio кажется особенно перспективной.

StoryQ выглядит как хорошая альтернатива NBehave с его свободным интерфейсом. Я определенно проверил бы это.

Я не думаю, что есть «победитель». Другие frameworks include проект SpecUnit.NET, и MSpec также демонстрирует promise с началом адаптера Gallio . Технически, поскольку IronRuby находится на горизонте, rSpec может быть вариантом для тех, кто готов к кровотечению. NBehave + NSpec может быть старшим фреймворком с лучшей автоматизацией, хотя я обнаружил, что борюсь с чрезмерно подробным синтаксисом.

Я бы проверить их все и выбрать frameworks, которые лучше всего подходят для вашего проекта. Все они OSS, поэтому его трудно потерять, реальная выгода – просто переходить на BDD.

Я лично порекомендовал бы BDDfy что здорово, на мой взгляд! Это с открытым исходным кодом, поддерживает условное и свободно основанное описание сценария, отлично подходит как для принятия, так и для модульных тестов. Вы можете найти его на GitHub .

Robot Framework также можно использовать с IronPython для выполнения ATDD или BDD в .Net. Я думаю, что возможности выражения Robot Framework лучше, чем, например. SpecFlow или NSpec . Это не заставляет вас использовать определенный синтаксис, но вместо этого использует подход, управляемый ключевыми словами. Если вы тестируете веб-приложения, у него есть Selenium2Library, который обеспечивает привязки к Selenium WebDriver.

Существует также Spectre , который определяет DSL в Boo, чтобы сделать его более естественным.

Я вообще соглашался на NBehave, в сочетании с MbUnit и любыми DI / mocking frameworks, в которых вы нуждаетесь. Это замечательный комментарий Джима Бургера о том, что NBehave очень многословный, и я иногда использую cut-and-paste. Тем не менее, он отлично работает – я использую плагин Gallio’s ReSharper, поэтому я просто получаю дополнительное окно. Однако не пробовал это с помощью ccnet.

Проверьте это сообщение в блоге и его комментарии для вдохновляющих идей: http://haacked.com/archive/2008/08/23/introducing-subspec.aspx/

Concordion.NET не только поддерживает BDD, но и ATDD: http://assertselenium.com/2012/11/05/difference-between-tdd-bdd-atdd/ Технические характеристики написаны на простом английском языке с использованием HTML. ИМХО это одно из преимуществ Concordion.NET. HTML-документы могут быть организованы в судоходную структуру для создания живой документации . И, поскольку тесты проходят против системы, вы можете быть уверены, что документация всегда актуальна.

Я начинаю свой первый выход в BDD с небольшого приложения с моей командой. Инструменты, которые мы выбираем для выполнения этой задачи, – это: Specflow с Selenium Webdriver для xBehave-историй и MSpec с Machine.Fakes.Moq для контейнера-автомата для наших модульных тестов xSpec. С помощью Resharper мы будем как лидером по истории, так и спецификатором, благодаря интеграции, поддерживаемой Specflow и MSpec. Наличие собственной интеграции в визуальную студию с R # является ключевой особенностью для нас.

Поскольку наш дизайн – это все MVC3, мы также будем применять шаблон разделения оркестров к нашим controllerам MVC . Это позволит нам писать спецификации непосредственно против оркестра. Затем мы можем писать истории непосредственно против использования нашего приложения.

Также проверьте UBADDAS, специфичный для UAT, найденный в

https://github.com/KernowCode/UBADDAS

с объяснением здесь

http://kernowcode.wordpress.com/ (в июне 2014 года)

Вы можете написать тест, подобный этому

 [Test] public void IWantToRegisterANewUser() { var user = new User(); ICustomer customer = new Customer(); SoThat(MyBusinessValue.IncreaseCustomerBase) .As(user) .Given(customer.Register) .When(customer.Confirm_Registration) .Then(customer.Login); } 

и производит это

 I want to register a new user so that Increase customer base as user given Register customer when Confirm customer registration then Login customer 

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

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

Я бы никоим образом не избегал теста, написанного на языке программирования, такого как примеры MSpec выше. Если я появлюсь с таким испытанием в офисе менеджера, он вышвырнет меня. Но он заинтересован в чтении тестов на основе Gherkin-Syntax. Чем больше ребят могут читать и модифицировать тесты, тем лучше.

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

Опять же, ответ еще раз:

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

Я могу порекомендовать использовать SpecFlow. У вас есть полный доступ к полной библиотеке .Net и всем ее функциям, ваши тесты остаются переносимыми. Это может дать вам преимущество перед совершенно портативными решениями, такими как Robot Framework, если вы не против переносимости. Тем не менее, вы всегда можете улучшить стабильность и мобильность системы, используя различные инструменты для разработки и тестирования. Поэтому тестирование программного обеспечения .Net с использованием подхода BDD на основе python может быть хорошей (или даже лучшей) идеей в некоторых случаях.

Тем не менее, SpecFlow проявлял стабильную и пуленепробиваемость при ежедневном тестировании, включая тесты на ночную сборку и т. Д. В проектах среднего размера. Кроме того, он хорошо интегрируется в тестовую среду Microsoft Unit.

  • HttpWebRequest URL с точкой в ​​конце
  • Неактивность и активность WPF
  • Как получить список зарегистрированных пользователей / подключенных пользователей в .NET?
  • Введите символ «&» в текстовую метку в Windows Forms?
  • C #: Поиск алгоритма / библиотеки сжатия PNG
  • Как захватить экран для видео с помощью C # .Net?
  • Серийный объект Json.NET с корневым именем
  • Общий список - перемещение элемента в списке
  • Как я могу запросить нулевые значения в структуре сущностей?
  • Как можно получить абсолютный или нормализованный путь к файлу в .NET?
  • Удаление десериализации JSON в объект с помощью Json.NET
  • Давайте будем гением компьютера.