如何正确指出要使用哪个StepArgumentTrasformation?

时间:2014-06-04 15:02:44

标签: specflow

我试图在两个不同的步骤中将SpecFlow步骤参数转换为相同的返回类型。

以下是简化的功能文件:

Feature: TransforMe

@UseTableToIntsTransform
Scenario: First
Given I have some condition
When I do something
Then the results should be
| Index |
| 1     |
| 2     |
| 3     |

@UseStringToIntsTransform
Scenario Outline: Second
Given I have some condition
When I do something
Then the results should contain <expectedResults>

Examples: 
| expectedResults |
| 0               |
| 0,3,5,7,10      |

我要做的是从Then中的场景转换表和字符串,以返回IEnumerable作为步骤参数。我正在尝试使用Scope,属性正则表达式限制,......没有成功。以下是步骤定义:

[Binding]
public class TransforMeSteps
{
    [Given(@"I have some condition")]
    public void GivenIHaveSomeCondition()
    { }

    [When(@"I do something")]
    public void WhenIDoSomething()
    { }

    [Then(@"the results should be")]
    [Scope(Scenario = "First", Tag = "UseTableToIntsTransform")]
    public void ThenTheResultsShouldBe(IEnumerable<int> results)
    {
        results.ToList().ForEach(x => Debug.WriteLine(x));
    }

    [Then(@"the results should contain (.*)")]
    [Scope(Scenario = "Second", Tag = "UseStringToIntsTransform")]
    public void ThenTheResultsShouldContain(IEnumerable<int> results)
    {
        results.ToList().ForEach(x => Debug.WriteLine(x));
    }
}

[Binding]
[Scope(Scenario = "First", Tag = "UseTableToIntsTransform")]
public class TableToIntsTransform
{
    [StepArgumentTransformation(@"the results should be")]
    public IEnumerable<int> TableToInts(Table intsTable)
    {
        return new List<int> { 1, 2, 3 };
    }
}

[Binding]
public class StringToIntsTransform
{
    [StepArgumentTransformation(@"the results should contain (.*)")]
    [Scope(Scenario = "Second", Tag = "UseStringToIntsTransform")]
    public IEnumerable<int> StringToInts(string integersString)
    {
        return new List<int> { 4, 5, 6 };
    }
}

对于“First”场景,我得到绿色测试,但有警告:多步转换匹配输入(| Index | | 1 | | 2 | | 3 | ,target type:[System.Collections.Generic.IEnumerable`1 [System.Int32]])。我们使用第一个。

对于“第二”场景,抛出InvalidCastException:从'System.String'到'System.Collections.Generic.IEnumerable`1 [[System.Int32,mscorlib,Version = 4.0.0.0,Culture = neutral]的无效转换,PublicKeyToken = b77a5c561934e089]]'。

每个转换本身都有相应的步骤定义。例如,如果我将变换类的顺序更改为首先使用StringToIntsTransform,那么“第二”方案的测试是绿色的。

那么如何正确指出或限制范围到正确的转型?

我希望能有这样的东西作为我的最终解决方案:

    [Then(@"the results should contain (.*)")]
    [Then(@"the results should be")]
    public void ThenTheResultsShouldContain(IEnumerable<int> results)
    {
        results.ToList().ForEach(x => Debug.WriteLine(x));
    }

仅限一步定义。

1 个答案:

答案 0 :(得分:1)

这可能不太理想,但我要做的是创建一个类来表示我正在返回的对象并在此处使用它。这个类可能只是包装一个int,但是作为一个不同的类将允许specflow区分要使用的步骤转换。所以有些东西:

[Binding]
public class TransforMeSteps
{
    [Given(@"I have some condition")]
    public void GivenIHaveSomeCondition()
    { }

    [When(@"I do something")]
    public void WhenIDoSomething()
    { }

    [Then(@"the results should be")]
    [Scope(Scenario = "First", Tag = "UseTableToIntsTransform")]
    public void ThenTheResultsShouldBe(IEnumerable<Index> results)
    {
        results.ToList().ForEach(x => Debug.WriteLine(x));
    }

    [Then(@"the results should contain (.*)")]
    [Scope(Scenario = "Second", Tag = "UseStringToIntsTransform")]
    public void ThenTheResultsShouldContain(IEnumerable<ExpectedResult> results)
    {
        results.ToList().ForEach(x => Debug.WriteLine(x));
    }
}

[Binding]
[Scope(Scenario = "First", Tag = "UseTableToIntsTransform")]
public class TableToIntsTransform
{
    [StepArgumentTransformation(@"the results should be")]
    public IEnumerable<Index> TableToInts(Table intsTable)
    {
        return new List<Index> { 1, 2, 3 };
    }
}

[Binding]
public class StringToIntsTransform
{
    [StepArgumentTransformation(@"the results should contain (.*)")]
    [Scope(Scenario = "Second", Tag = "UseStringToIntsTransform")]
    public IEnumerable<ExpectedResult> StringToInts(string integersString)
    {
        return new List<ExpectedResult> { 4, 5, 6 };
    }
}

public class Index
{
     private int value;
     public Index(int value)
     { this.value=value;}

     public static implicit operator int(Index index)
     {
         return index.value;
     }

     public static implicit operator Index(int value)
     {
         return new Index(value);
     }
}

您可以将IndexExpectedResult类隐式转换为int,以使其更方便使用。