Расширение xUnit.NET для использования пользовательского кода при обработке класса и поиске методов тестирования. - PullRequest
5 голосов
/ 28 января 2009

Я большой поклонник фреймворка xUnit.NET; Я нахожу это легким, простым, чистым и расширяемым.

Теперь допустим, что у меня есть такой класс:

public class AdditionSpecification
{
  static int result;

  public void Because()
  {
    result = 2 + 2;
  }

  public void Result_is_non_zero()
  {
    Assert.True(result <> 0);
  }

  public void Result_is_correct()
  {
    Assert.Equal(4, result);
  }
}

С помощью тестового класса, приведенного выше, я хочу, чтобы xUnit.NET видел 2 тестовых случая и запускал метод Потому () перед каждым из них.

Оставляя в стороне любые проблемы, которые могут возникнуть у вас с именами моих классов или методов, структурой этого теста / спецификации, структурой xUnit.NET или BDD, вот мой вопрос:

Как я могу сказать xUnit.NET, что я хочу настроить способ определения и выполнения методов тестирования из этого класса без , используя настраиваемый атрибут [Fact], как в каждом целевом методе тестирования

Я знаю, что могу наследовать от BeforeAfterAttribute, чтобы украсить каждый тестовый метод пользовательским до и после выполнения. Как я могу сделать это на уровне класса? Должен ли я написать собственный бегун?

Ответы [ 2 ]

10 голосов
/ 02 июня 2009

IUseFixture от xUnit.net позволяет вам выполнять настройку прибора. Поэтому вы можете определить свой собственный класс приборов:

public class AdditionFixture : IDisposable
{
  public int Because() 
  {
    return 2 + 2;
  }

  public void Dispose()
  {
   //test tear down code
  }      
}

Ваш тестовый класс может затем реализовать это (с помощью setFixture, требующей реализации):

public class AdditionSpecification : IUseFixture<AdditionFixture>
{
  int result;

  public void SetFixture(AdditionFixture Fixture)
  {
   result = Fixture.Because();
  }

  [Fact]
  public void Result_is_non_zero()
  {
   Assert.True(result <> 0);
  }

  [Fact]
  public void Result_is_correct()
  {
   Assert.Equal(4, result);
  }
}

Средство запуска xUnit создаст один экземпляр вашего прибора и перед выполнением каждого теста передаст его в SetFixture. После выполнения всех ваших тестов бегун избавится от прибора, если он реализует IDisposable. Надеюсь, это поможет!

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

9 голосов
/ 09 июня 2009

Получается, что я искал метод ITestClassCommand.EnumerateTestMethods ().

  1. Стандартный тестер xUnit.NET будет перебирать все классы в ваша тестовая сборка.
  2. Для каждого он будет проверять наличие атрибута RunWithAttribute; это ваш шанс переопределить Реализация ITestClassCommand который используется для определения методов содержащие тесты. (Хороший пример - RunWithNUnit)
  3. ITestClassCommand.EnumerateTestMethods () вызывается для обработки тестового класса и возврата IEnumerable из тестовых методов.
  4. каждый тест IMethodInfo затем передается в ITestClassCommand.EnumerateTestCommands (IMethodInfo testMethod), чтобы получить IEnumerable из ITestCommands
  5. Затем выполняется каждая ITestCommand, и ей предоставляется возможность вернуть результат.

В моем примере, приведенном выше, мне нужно что-то вроде:

[AttributeUsage(AttributeTargets.Class, AllowMultiple = false)]
public class RunWithMyTestClassCommandAttribute : RunWithAttribute
{
   public RunWithMyTestClassCommandAttribute()
               : base(typeof(MyTestClassCommand)) {}
}

Тогда я мог бы украсить свой пример выше с помощью:

[RunWithMyTestClassCommand]
public class AdditionSpecification
{
  static int result;

  public void Because()
  {
    result = 2 + 2;
  }

  public void Result_is_non_zero()
  {
    Assert.True(result <> 0);
  }

  public void Result_is_correct()
  {
    Assert.Equal(4, result);
  }
}

Наконец, в MyTestClassCommand я получаю возможность между EnumerateTestMethods () и EnumerateTestCommands (IMethodInfo testMethod) использовать любую логику, которую я хочу найти и создать экземпляры ITestCommand, которые выполняются как отдельные тесты.

Кстати, в процессе исследования этой проблемы я столкнулся с небольшой ошибкой в ​​платформе xUnit.NET, когда пользовательский IMethodInfo, сгенерированный EnumerateTestMethods (), никогда не обнаруживался в EnumerateTestCommands (..), потому что он был развернут и перемотан. от бегуна или одного из заводов.

Я отправил эту проблему в проект xUnit на codeplex, и это было исправлено 30 мая , 2009 для xUnit.NET 1.5 CTP 2

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...