Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Passing discriminated unions to InlineData attributes

I am trying to unit test a parser that parses a string and returns the corresponding abstract syntax tree (represented as a discriminated union). I figured it would be pretty compact to use Xunit.Extensions' attribute InlineData to stack all test cases on one another:

[<Theory>]
[<InlineData("1 +1 ", Binary(Literal(Number(1.0)), Add, Literal(Number(1.0))))>]
...
let ``parsed string matches the expected result`` () =

However, compiler complains that the second argument is not a literal (compile time constant if I understand it correctly).

Is there a workaround for this? If not, what would be the most sensible way to structure parser result tests while keeping every case as a separate unit test?

like image 586
nphx Avatar asked Dec 31 '14 20:12

nphx


1 Answers

One possibility is to use xUnit's MemberData attribute. A disadvantage with this approach is that this parameterized test appears in Visual Studio's Test Explorer as one test instead of two separate tests because collections lack xUnit's IXunitSerializable interface and xUnit hasn't added build-in serialization support for that type either. See xunit/xunit/issues/429 for more information.

Here is a minimal working example.

module TestModule

  open Xunit

  type DU = A | B | C

  type TestType () =
    static member TestProperty
      with get() : obj[] list =
        [
          [| A; "a" |]
          [| B; "b" |]
        ]

    [<Theory>]
    [<MemberData("TestProperty")>]            
    member __.TestMethod (a:DU) (b:string) =
      Assert.Equal(A, a)

See also this similar question in which I give a similar answer.

like image 147
Tyson Williams Avatar answered Nov 05 '22 21:11

Tyson Williams