17

使用流利的断言,我想断言给定的字符串包含两个字符串之一:

actual.Should().Contain("oneWay").Or().Should().Contain("anotherWay"); 
// eiter value should pass the assertion.
// for example: "you may do it oneWay." should pass, but
// "you may do it thisWay." should not pass

只有当这两个值都不包含时,断言才应该失败。由于没有运算符,这不起作用(甚至无法编译)Or()

这就是我现在的做法:

bool isVariant1 = actual.Contains(@"oneWay");
bool isVariant2 = actual.Contains(@"anotherWay");
bool anyVariant = (isVariant1 || isVariant2);
anyVariant.Should().BeTrue("because blahblah. Actual content was: " + actual);

这是冗长的,并且必须手动创建“因为”参数才能获得有意义的输出。

有没有办法以更易读的方式做到这一点?解决方案还应适用于其他流畅的断言类型,例如Be()HaveCount()...

我在 .NET 3.5 上使用 FluentAssertions 版本 2.2.0.0,如果这很重要的话。

4

3 回答 3

13

我会将其作为字符串断言的扩展。像这样的东西:

public static void BeAnyOf(this StringAssertions assertions, string[] expectations, string because, params string[] args) {
    Execute.Assertion
           .ForCondition(expectations.Any(assertions.Subject.Contains))
           .BecauseOf(because, args)
           .FailWith("Expected {context:string} to be any of {0}{reason}", expectations);
}

你甚至可以 fork存储库并向我提供一个Pull Request以使其成为下一个版本的一部分。

于 2014-08-29T07:04:03.947 回答
13

这不应该工作吗?

actual.Should().BeOneOf("oneWay", "anotherWay");

使用 v3.1.229 为我工作。

于 2014-09-25T02:09:10.057 回答
2

您可以通过编写一个简单的字符串扩展名使其更具可读性:

public static class StringExt
{
    public static bool ContainsAnyOf(this string self, params string[] strings)
    {
        return strings.Any(self.Contains);
    }
}

然后你可以这样做:

actual.ContainsAnyOf("oneWay", "anotherWay").Should().BeTrue("because of this reason");

不幸的是,这对消息的“原因”部分没有帮助,但我认为这要好一些。

于 2014-08-28T08:11:28.177 回答