Hello Mentors,
I'm Nikola, a third year undergraduate in computer science from Sofia, Bulgaria. My interests lie in functional programming. I also help out our university's elixir courses.
My proposal concerns the property testing library stream_data. At the moment you can generate streams of random data for our properties like this `StreamData.integer()`, check properties of functions and shrink failing data.
As discussed with Jose and Andrea, the project would aim to improve the user experience of the stream_data library.
Here are the two main goals of the project.
Goal 1: More often than not, users will build their own types and structs, which would inconvenience them, since they will have to manually generate their types.
Example:
# Given those simple types:
defmodule Example do
@type name :: binary()
@type age :: integer()
@type user :: {name(), age()}
end
# You would generate the following data stream.
users = gen all name <- binary(),
age <- integer(),
do: {name, age}
# We should be able to make this more concise:
users = gen all Example.user()
# or
import Example
users = gen all user
Goal 2: Whenever a user defines a function spec, he should be able to declare whether he wants a function to be tested with properties. If declared, we would get the specs of a functions, generate the arguments using the type generator from Goal 1, invoke the function and check whether the results belong to the output generator.
Example:
defmodule Example do
@spec add(number(), number()) :: number()
def add(a, b), do: a + b
end
defmodule ExampleTest do
# Long variant:
property "adding two numbers results in a number" do
check all a <- number(),
b <- number(),
do: assert is_number(add(a, b))
end
# We could reduce this to:
property spec: :add
# or
property :add
end
I already have a simple PoC
here. (The apis in the code and examples above are some I made up ad-hoc, I believe they will change overtime to better suit the users.)
The hard parts of the project, I imagine, would be generating recursive types and inferring the module the types come from if we want some implicitness in the tests.
Looking forward to your guidance, advice and recommendations on books/code to read,
Nikola!