Web Api – Integration Testing

Sorry, it has been a few months since my last post, time flies by and before you know it, the seasons have changed and you haven’t written a blog post in roughly three months.

Anyway, something that I have been working a lot on lately is creating web api applications for a project that I am involved in for work.  The main purpose of this post will be to try and describe the testing method involved.  This is to try to help with two points. One, when I started I didn’t know a lot about web api and the ways that you could test your newly created api.  This could maybe help someone.  Second, to allow me to have somewhere to dump my brain so when I’m asked again I don’t need to search for the information or spend time on the old problems.

To start with, three blogs that I used were:
In memory client, host and integration testing of your Web API service
ASP.NET Web API integration testing with in-memory hosting
Integration testing ASP .NET Web API

Glenn Block has written a book covering web api
Designing Evolvable Web APIs with ASP.NET

I was also very lucky that someone inside the company I work for had arranged for Glenn Block to talk to the developers and the same person had almost completed the template that we would use to write the api but they had followed a different approach for testing, particularly integration testing.  Going for a self hosted solution and this involved using the full IIS to deploy the application and run tests against that application.  In the project I am involved in, we used IIS Express and changing the web server wasn’t an option plus I had to write tests that could run and safely clean up after themselves in the continuous integration (CI) server. I opted for the in-memory integration tests.

I started off creating an infrastructure library for my configuration classes, interfaces and server class.  The configuration class consisted of all the plumbing for Castle Windsor and routes and filters for my api project and the server classes utilised the configuration classes to set the http configuration and http server to use in my tests. Then called the classes in the infrastructure library from the main api project.  I also had both unit and integration test projects.  I have seen some create an project to house all the models and any other logic necessary.  Essentially use the main api project as a host only but I did not want to create a large number of projects so opted to use my main project to hold the models and some configuration code.

Structure:
– Api – controller and view models.
– Infrastructure – in-memory server and configuration.
– Integration tests – for the api code only.
– Unit tests – for the api code only.

The command and queries that were executed from the api project were all housed in another project and had their own test projects.

One of the main issues that I had was how to dispose of the Castle Windsor container after each test run.  The test harness would only run one test successfully.  It would fail the other tests but if you ran the other tests individually they would pass.  It was not disposing of the classes the way it should or we were not setting the lifecycle up on the classes right.  If we set up the configuration in the constructor of the server class it would fail as well with the same error that it could not dispose of the object.  In the end, a new container was created on each test and this solved the issue.  There was no way to remove the items from an existing container.  I would be interested in hearing from anyone that has solved that problem in a different or better way.

One of the other issues was the serialized auto properties were generating the k_backingfield text and as a result automapper could not resolve the property names.  The data returned was always null.  A couple of ways to resolve this were using [Data Contract] at the top of the class with [Data Member] for each of the properties or using the Newtonsoft.Json Library using the data annotation [JsonProperty] with the k_backingfield added to the name above the property.

One of the things that I did in case we ever wanted to go down the self hosted route was to create an in-memory test class, which inherited the actual test class.  This way it was simple enough to create a self hosted test class, which inherited the actual test class without repeating code or configuration over and over.

Example:
[TestFixture]
public class InMemoryApiTests : ApiTests
{
public InMemorysApiTests() : base(new InMemoryApiServer())
{
}
}

One tool that proved invaluable was the Postman REST client, it is a chrome plugin and I used this to compare the outputs that I got from the tests and the returned data in post value to make sure everything was good.

I have now implemented another api and this time it was a lot easier because I could use the pattern developed earlier to test.  Testing was by the far the greatest challenge that I faced when developing the api.

Until next time…..As ever any feedback on the way I write these posts or the content is appreciated.

The Great (Failed) Family Agile Experiment

Taking a break from the AngularJS series this time.  I decided to write about an experience of using Agile in the home.  I had listened to a podcast from Scott Hanselman interviewing David Starr, Scrum.org and then read his paper on Agile Practices for Families.  I watched a TED talk by Bruce Feiler where he talked about the same ideas as David Starr.  I thought this would be really good idea in our house where 99% of the arguments between my wife and I are about who is doing household tasks (and admittedly Mrs I.D. doing most of the them).  

So, one bright sunny Saturday morning, I embarked on a journey of discovery and purchased a new cork board for the kitchen.  The reason I bought the board is that Mrs I.D. likes the old fashioned methods instead of something like trello.com.  After the purchase, I sat the family down including my two year old daughter and told them that I was going to try this “work thing” and could we have a family meeting the next day at 11am?  When the laughter had stopped, Mrs I.D reluctantly agreed to this request.  

At 10am the next day,  I started to put my fledging plan into action.  Armed with post notes, a calender (for all our commitments), and breakfast.  I gathered the family around our dinning room table.  I started off by trying to explain what was going to happen and what I would like the outcome to be.  At this point, Mrs I.D. made a very interesting statement, something along the lines of “Well, I already do this in my head every day, what do I need an enormous cork board in the kitchen for?”  I tried to explain that if it is in her head then no one else knows about it, she gets frustrated because I don’t do the tasks that she expects me to do and I get frustrated because she always shouting and asking me to do things when I haven’t the time.  I tried to add a competitive edge to it by giving each task one point and setting a threshold of 30 points for a reward.  This was mainly set for my two year old (who maybe is a bit too young, but likes a reward) but it would motivate Mrs I.D. as well.  I asked for a two week window to do this experiment, it was granted. 

The board was broken into three swim lanes, ToDo, Doing, and Done.  Each of us had an area on the board for our tasks and we would meet once a week to discuss the week and decide the next lot of tasks (with the repetitive ones like hoovering and dishes being swapped between us every cycle).  We would also discuss our commitments during the week and make sure that our commitments did not delay/stop the tasks assigned.  This allowed us to plan dinners, nights out and classes that we had, to make sure we were prepared.  I also explained that we should have informal stand up every day to discuss the tasks (only involving Mrs I.D and I).  This was sitting on the sofa after work.

After about an hour, we had enough tasks to keep us going for the week on fancy post it notes that I thought would keep everyone interested.  My daughter’s task were kept to one or two light ones so that she would get used it.

The first few days and the rest of that week went okay.  Everyone was getting into it and it generated a bit of discussion around the house, mainly laughing and joking about the lack of tasks I’d completed but there was no arguments.  We just got on with it.

The second week however I found that the novelty had worn off.  The tasks were practically the same but we stopped communicating about them.  The arguments started again and in the end, no one was paying the slightest bit of attention to the tasks or the board.  The final nail in the coffin came as the board was removed and we started to use trello.com.  Mrs I.D. didn’t like the board in the kitchen so we moved to the electronic world.  It became chaos, we were added our own tasks (that hadn’t been discussed) and doing tasks that weren’t on the board.  Eventually it just fizzled out with our family going back to what we normally do.  Just doing the tasks when they bother us enough to do them.

In conclusion, I believe this could still work in our house but a few things need to happen:

  1. The rules need to be bit clearer.  (i.e. we can’t add tasks that haven’t been discussed)
  2. Some tasks need to given time limits, especially for me 
  3. We need to communicate a bit better when doing this sort of thing.
  4. Everyone needs to buy into it and understand the reasons for doing it.

If there is any further update, then I’ll post about it.  Hopefully it won’t be the last time I write about this subject.

Learning AngularJS – Part 3

Following on from my previous posts about AngularJS Learning AngularJS – The beginning and Learning AngularJS – Part 2. I would like to talk a bit about the form to add a person to my personnel application. My trials on how it went plus what I learnt along the way.

First of all, returning to the main page of the application. The page will always have a button to add a record and when the records are added, there will be a button to amend those records. So what happens when you click the add button. Soon as you hit the main page, the application makes use of the routing engine “#”, so that the application knows where to go, we add another entry into the module config saying that when #/addperson is called, use this controller and go to this template (sometimes called a partial). Example:

$routeProvider.when("/addNewPerson", {
controller: "newPeopleController",
templateUrl: "/templates/addNewPerson.html",
});

The addPerson.html is then injected into data-ng-view on the index.cshtml page.

The add person page is made slightly easier by the fact that I didn’t need to populate the form with data. However, a function to add a person is still needed in your service or factory (it is probably worth pointing out that although I used the terms there, my data service uses factory, confused?? Any examples that I seen have used factory when defining a service and most people can’t give you an answer when questioning the differencing between the two terms).

var _addPerson = function (newPerson) {
var deferred = $q.defer();


$http.post("/api/People", newPerson)
.then(function (result) {
var newlyCreatedPerson = result.data;
_people.splice(0, 0, newlyCreatedPerson);
deferred.resolve(newlyCreatedPerson);
},
function() {
deferred.reject();
});


return deferred.promise;
};

This function will go to the post method of the WebAPI people controller and save the input entered to the database. It uses a promise to return data to the controller, the promise is accessed through the deferred API in AngularJS. The resolve indicates a successful outcome and reject, an error or something isn’t right, and promise wraps it up and passes it back. In the dataservice, we can’t have bespoke controller functionality like error messages or redirecting to specific addresses. The promise allows the code to pass back the outcome to controller and the controller can do the details. It is probably worth pointing out that although I’ve used .then to define the outcome of my promises newer versions of AngularJS can use .success and .error. The final thing on the addPerson function is that splice will add the record into the personnel list without having to call the WebAPI get method again and the position specified.

The dataservice will have a public part to it in the return { addPerson = _addPerson }. The addPerson can be accessed in controllers, something like dataservice.addPerson so you don’t need to duplicate code. Good, right?

Hopefully now this should be making sense. The controller code is as follows:

function newPeopleController($scope, $http, $window, dataService)
{
$scope.newPerson = {};
$scope.salary = {};


$scope.save = function () {
dataService.addPerson($scope.newPerson)
.then(function () {
$window.location = "/#";
},
function() {
alert("Cannot save person");
});
};

The save() function is called in the html template by using ng-submit on the form tag . The data- bit is ro stop the editor complaining about the syntax.

In the HTML itself, there is couple of nice wee things. For example, I take advantage of the HTML5 required and placeholder attributes plus use ng-class=”{‘has-error’: AddNewPerson.salutation.$error.required}”. This will highlight the outline of the textbox in red if there is no text in a required field and then remove it as you type. Following on from that, I included the ng-disabled=”AddNewPerson.$invalid” tag so that the save button is disabled until all invalid data is removed. In addition, I use the ng-model attribute (ng-model=”newPerson.surname”) to gather up the data to post to the WebAPI method. Simple things but all good stuff.

Coupled with Bootstrap 3.0 to style the application it is all fairly lightweight and easy to learn so far.

Problems

In the first post I spoke about a problem relating to adding a person with an address but it was really the way that I was using the data and Automapper.

I think going forward the way that salary is entered has to change. The domain property is a list and I struggled to get the data into the list. Eventually I used an individual salary amount property and used Automapper to map it correctly. I may try to do this differently by changing the page to either use a table for salary and add to it or break the pages up to add person details first then salary. That’s a brief insight into my thinking now. Any thoughts welcome?

Until next time…

Learning AngularJS – Part 2

As part of the series of posts that I’m planning to write about learning AngularJS, I’m going to write about each piece of significant functionality in the application.  I provided a brief explanation of the application in Learning AngularJS – The beginning.  In this post, I’m going to detail the search feature, explaining the way that I want it to work and what the problems that I encountered were.

I had decided early on that I wanted to place a search box and button on the header of each of my pages, mainly because of ease of use.  Partly because I wanted the user to be able to search from any point in the application.  I had originally looked at the Bootstrap Typeahead Component but keeping with the AngularJS theme, my next stop was Angular UI Bootstrap.  I had previously looked at these components for the work project that I was on.

In the module, I defined

var module = angular.module("mainIndex", ['ui.bootstrap']);

Specifying ui.bootstrap in the square brackets as part of the module declaration allows the Angular UI Bootstrap to be used,

The code to use the typeahead on the Index.cshtml is:

<div data-ng-controller="SearchController">
     <div class="form-group">
     <input type="text" 
               typeahead-on-select="setPerson($item.Id)"
               data-ng-model="selected" 
               placeholder="Personal Records" 
               typeahead="person as person.FirstName + ' ' + person.Surname for person in getPersonalRecords($viewValue) | filter:$viewValue"                                  typeahead-loading="loadingRecords" class="form-control">                                 
                 </div>                                                                                                                                                    <button class="btn btn-default" data-ng click="search()">Search</button>          
                 </div>

On the first div, there is a attribute value with the controller name defined.  I’m not sure whether I strictly need this as at the top of the index.cshtml page, I have an attribute, which tells me the AngularJS module to use.  The attribute is ng-controller but by adding “data-” you can stop the editor thinking ng-controller is a problem. By defining “data-“, the editor is tricked into thinking that this is a custom attribute.

The typeahead-on-select attribute allows the id of the person selected to be sent back to the controller.  The attribute data-ng-model should have performed this function too but I could not get the variable selected to pass a value across even with the $scope object injecting it.  The typeahead attribute specifies what the user will see like first name and surname and also called the function within the controller code to take what has been entered into the search box and contact the web api get method to return people.  The typeahead loading attribute will display the text or image specified.  The image up to now always goes slightly wrong for me.  That’s how I stuck with text.  Finally, I have a search button to take my selection and display it on a search results page.

Problems:

When I first added the typeahead input box I couldn’t get the person list to display at all.  This turned out be a flaw in the way that I returned the data to the page.  I was trying to add the data to $scope.person variable thinking that it would bind it and I could use person on the index page.  All that was needed was return result.data and the person list would display correctly.

My other issue was that when the user clicked search, the selected values were not be passed across.  The examples and posts were all favouring ng-model selected.  selected would then bind back to the controller providing it was specified.  I could never get this to work instead using typeahead-on-select, which used a function within the controller to pass back the value and assign it to variable.  Exactly the same way ng-model would but with more code.

The AngularJS controller itself is:

function SearchController($scope, $http, $log, $window) {

$scope.selected = '';
$scope.personal = [];
$scope.$log = $log;

$scope.getPersonalRecords = function (val) {
return $http.get('/api/People', {
params: {
searchTerm: val
}
}).then(function (res) {
return res.data;
});
};

$scope.setPerson = function (person) {
$scope.selectedPerson = person;
};

$scope.search = function () {
$log.log("Selected: " + $scope.selectedPerson)

$window.location = "Main#/searchPerson/" + $scope.selectedPerson;
}

The four parameters that are injected into the controller are $scope, which helps with the two way data binding, $http, which allows me to call the web api methods via a callback, $log, which is useful for outputting value and debugging through the code, and $window, which allows the controller to navigate away from the current view.

The first function gets the personal records using web api based on a search term that is entered by the user. For some reason, I have chosen to use a $http shortcut instead of using a data service that I have defined. I will speak more about the data service in later posts but that should change to dataService.getPeople(…) instead of $http.get(…).  When injecting the dataService into the controller the dollar ($) sign is not needed. The web api method will then return the result enabling the data to rendered on the page.

The second function setPerson is used to capture the id of the person selected after the search so that can be passed back to the search function further down. Opted for this way because I struggled to get ng-model to pass the value on its own. The input tag typeahead-on-select will then call the function, which sets selectedPerson variable.

The third function search takes the selected value and uses it to redirect the user to a search page.

I think that just about covers the basics of what I did. If there is anything that I’ve left out or could be done better, please do not hesitate to leave a message. Also sorry about the code examples formatting, just getting used to wordpress.

Learning AngularJS – The beginning

Hi, first post.

A few months back I got an opportunity to use AngularJS on a project in work.  Unfortunately, the AngularJS bits got pulled before the end of the first sprint but this was enough to peak my interest and motivate me to build a simple application using AngularJS.  This post and subsequent posts will chart my progress and pain during this journey of discovery on my own project.

Let’s go back to the beginning, my journey started at work, part of the learning curve was to go onto Pluralsight and complete a course.  The course was by Shaun Wildermuth around Bootstrap, MVC and AngularJS.   Coupled with the extensive documentation for AngularJS and what seems to me as a big push by Google to drive AngularJS forward, there was a lot of examples and people using it.

I started by taking an old existing MVC application, which I generally use for experimentation and added AngularJS to it.  This used Entity Framework 6.0, AutoFac, Automapper, MVC 4, NUnit, and Rhino Mocks.  Later I added Web API and I hope to talk about that in blogs later.

Brief Summary of Application

The application is a small fake personal management system, which allows the user to log in, view, search, and and update personal records for a company.

After logging into the application, the user will be presented with an index page with the company employees’ on it.  It serves as a main navigation place for the rest of the application.

In the module, I set up a routeProvider to look at a url and go to my given AngularJS controller, which will use a partial view html template to render the display.

$routeProvider.when("/", {
controller: "peopleController",
templateUrl: "/templates/peopleView.html",
});

To get the data, I use a very simple WebAPI controller to get people, get a person, add a person and update a person.  The two way data-binding in the templates, which AngularJS provides is great, essentially {{ Person.FirstName }} is enough to render and persist the data back to the Web API controller and ending up in the database.

Inside the index view, I have a ViewData.InitModule property which tells the application which modules that I want to use. There is also this line data-ng-view which allows me to inject the partial view html template into the page

Right now, I’ve put all my controllers, modules and services within the one main-index.js.  Later on, I’ll split out the modules and services into separate files.  I’ve looked at angular seed and once I get more confident with the syntax I’ll use this to structure the project correctly.

In later blogs, I will try and talk about each part individually, but that provides enough detail for now.  Just now, I want to talk about some issues that I had.

First problem

I had used the aspx view engine and try as I might, I was unable to get the routing engine in AngularJS to work using this view engine.  All the examples and posts were all using the Razor view engine.  So after several nights of trying I converted all the pages in the solution to Razor.  I still don’t know if it is possible and it will something that I will try again once I become more familiar with AngularJS.  The point that I thought enough was enough was when I tried to give the page the AnguarJS module name so that I could use the routing engine to direct the controller to all the partial page templates and nothing happened.  I think the page was treating the name of the module as just text to be added to the page rather than text that could be a name of module.  Hence it would not see the controllers on the page and nothing would work.  I was getting a blank page.

Second problem

When it came to adding a new person into my application, one of the properties was Address Line 1.  This property was stored within an Address object.  I could see that  Address Line 1 was not getting populated from the page.  Initially I tried Person.Address[0].AddressLine1, this is wrong, the reason that this doesn’t work is that Address is not an array.  In AngularJS, you will access such a property as follows as Person.Address['AddressLine1'].  The actual problem with the Address Line 1 was that the object that I was querying for Address Line 1 didn’t contain the data.  Once I corrected the query, everything was okay.  Lesson Learned!

Third problem

I had a salary collection in my person object.  This was so that I could return a history of a person’s salary.  The problem was that I had to add a single salary to the collection every time I added or updated the personal record.  This time though, I could access salary like an array Person.Salary[0].Amount.  The problem was that the data sent to the method within the web api controller wasn’t mapping the salary in the person object.  In the end, I solved this problem with automapper mapping the salary to a new list object which I would create when doing the mapping.  I could not find a solution to make the salary map through pure AngularJS.  I did try to work a solution to the problem with ng-repeat and ng-model but the problem still existed or the application would output how many salaries I had stored.

These are the main silly issues I have encountered.  There will be better ways to solve these issues but at this current time this is way that I solved them.

The application itself is ongoing and currently I’m adding a typeahead input search box using AngularJS UI Bootstrap to search and view personal records.  The application is work in progress and will continue to evolve.  I am interested in any best practices and ways that I can build my knowledge around AngularJS.  Hopefully I can get feedback and blog about it here.

A few links that may help..

  1. AngularJS Google Group – https://groups.google.com/forum/#!forum/angular
  2. AngularJS documentation – https://angularjs.org/
  3. Dan Wahlin’s blog – http://weblogs.asp.net/dwahlin/default.aspx
  4. Angular Seed – https://github.com/angular/angular-seed

In the meantime, if I can help please leave a comment.