Automatically Generating Multi-Language & Convention Based Test Objects With NAuto
After many years of writing boilerplate test models, random string generators and test builder pattern objects, my colleague Andrew Jutton and I have put together a collection of really useful test helpers into a new open source project called NAuto.
There are a number of really cool features which we believe are massively beneficial and time saving when writing unit and integration tests.
Please check out the project documentation site http://amido.github.io/NAuto/.
I’ll create a series of posts showing off the features and benefits as I’m really proud of it and truly believe people will love using it. Please grab the NuGet package and have a play, all feedback will be greatly appreciated.
To whet your appetites, here’s just one of the features…
NAuto.AutoBuild Overview
One of the key features of NAuto is AutoBuild.
It will take pretty much any models including deep object graphs and quickly populate them with data, even if the model contains complex lists, dictionaries, custom types and types without default constructors.
It will also let you easily switch characters sets between numerous languages such as:
- English
- Traditional Chinese
- Russian
- German
- Pinyin
- Spanish
- Italian
var testModel = NAuto.AutoBuild<TestModel>() .Construct() .Build();
var testModel = NAuto.AutoBuild<TestModel>() .Configure(x => x.DefaultLanguage = Language.Russian) .Construct() .Build();
Overriding & Conditionals
The generated data can easily be overridden using the With method. there a number of useful overloads but a simple example would look like the following:
var testModel = NAuto.AutoBuild<TestModel>() .Construct() .With(x => x.LastName = "MyOverridenLastName") .Build();
You can also use conditional statements to control how data is generated:
var testModel = NAuto.AutoBuild<TestModel>() .Construct() .If(x => x.FirstName == "Joe") .Then(x => x.ContactDetails.EmailAddress = "joe.bloggs@test.com") .Build();
AutoBuilder Conventions
The AutoBuilder accepts a configuration object which can be used to tweak how data is created, whilst this is a necessary feature, a much more interesting and powerful way to control AutoBuilder is by utilising the conventions configuration.
There are a number of different and more efficient ways to add a convention to AutoBuilder which I’ll cover in future posts, for now I just want to show what they look like and how useful they are.
A typical convention looks like the following (see the .AddConvention line):
var testModel = NAuto.AutoBuild<TestModel>() .Configure(x => x.DefaultLanguage = Language.Russian) .AddConvention(ConventionFilterType.Contains, "email", typeof(string), c => NAuto.GetRandomPropertyType(PropertyType.Email)) .Construct() .ToJson();
Instead of calling Build() I have called ToJson(), the resulting output from this call is:
{ "firstName": "Угдрг", "lastName": "Йшц", "contactDetails": { "emailAddress": "жф9ш1з2ц4а8н23ецб@19дтха8рчу4лмви.com" } }
For clarity, here is the TestModel class:
public class TestModel { public string FirstName { get; set; } public string LastName { get; set; } public ContactDetails ContactDetails { get; set; } } public class ContactDetails { public string EmailAddress { get; set; } }
As you can see, for any property no matter how deep in the object graph (max depth limit can be configured), if the property is a string and contains the text “email”, a random email address is generated using the NAuto.GetRandomPropertyType method.
You might notice that the first name and last name are in Propercase and only contain russian alpha characters, this is because AutoBuilder comes with a predefined set of conventions which you can use or discard if not required.
Anyway, please check it out and let me know what you think.
The project will continue to improve overtime and should not disappear into the open source ether as it is a library we use at work.
Have fun.
Sean.