Saturday, May 16, 2015

API versioning in WEBAPI

API versioning is very common requirement of API developer. In the very initial stage you will require to share stubs and then later you have to maintain version. A very trivial and simple solution is to have different URL for different versions and have different handlers(controllers) for each.
Ofcourse the approch will work but there are features available in WebApi by which we can avoid having multiple URLs and make caller's life easy.
As we know that in MVC and WEBAPI, there is controller resolved which resolves the controller based on mapping. I will try to use the same thing to put our logic in between by which we can resolve the controller based on our logic.
For this first of all we need to create a controller selector -
public class CustomControllerSelector : DefaultHttpControllerSelector
{
private HttpConfiguration _config { get; set; }
public CustomControllerSelector(HttpConfiguration config) : base(config)
{
   _config = config;
}

public override HttpControllerDescriptor SelectController(HttpRequestMessage request)
{
}
}
In WebApi we DefaultHttpControllerSelector is the default Httpcontrollerselecotr. Here we have created our own selector and inheritied from Default one. DefaultControllerSelector has parametrized constructor which takes Httpconfiguration as input, so we will follow the same and here we have basic implementation in place.
Lets start writing something in SelectController, because this is the method which resolves the controller and returns HttpControllerDescriptor object.

1) lets get all the mapping availble in the application -
var controllers = GetControllerMapping();








If you see the screenshot, we get the mapping of Controller name with the actual controller object.

2) Get the parameters or routing info - var routeData = request.GetRouteData();
Based on the request URL, how it mapped with the mapping registered. For example if the following mapping is registered -
config.Routes.MapHttpRoute(
                name: "DefaultApi",
                routeTemplate: "api/{controller}/{id}",
                defaults: new { id = RouteParameter.Optional }
            );
then based on URL matched, what is the value of controller or id, we get this kind of values in the routeData.
3) Based on routeData, get he value of current controller -
 var controllername = (string)routeData.Values["controller"];

4) If we have followed attribute based mapping , then we will not get the controller named with above approach, hence we will just return the default mapping -
if (string.IsNullOrWhiteSpace(controllername))
            {
                return base.SelectController(request);
            }

5) Based on controller name, we can get the controller instance from the controller collection(step 1).
6) There are different ways of getting the version information from the URL- might be query parameter, or header. Here is the code of getting this version from query parameter -
        private string GetVersionFromQueryString(HttpRequestMessage request)
        {
            var query = HttpUtility.ParseQueryString(request.RequestUri.Query);
            var version = query["ver"];

            if (version != null)
            {
                return version;
            }
            return "";

        }
7) once we have version we just have to form the name of controller accordingly and return the controller instance. Here is the example of version to be "stub", then we make the controller name as current controller + "_stub" and return it back -
string newName = string.Empty;
                if ("stub".Equals(version))
                {
                    newName = string.Concat(controllername, "_stub", "");

                    HttpControllerDescriptor versionedDescriptor;
                    if (controllers.TryGetValue(newName, out versionedDescriptor))
                    {
                        return versionedDescriptor;
                    }
                }

Here is the complete code for the reference  -
public override HttpControllerDescriptor SelectController(HttpRequestMessage request)
{
    var controllers = GetControllerMapping();
    var routeData = request.GetRouteData();
    var controllername = (string)routeData.Values["controller"]; // values determined by route
    HttpControllerDescriptor descriptor;
    if (string.IsNullOrWhiteSpace(controllername))
    {
return base.SelectController(request);
    }
    else if (controllers.TryGetValue(controllername, out descriptor))
    {
var version = GetVersionFromQueryString(request);
string newName = string.Empty;
if ("stub".Equals(version))
{
   newName = string.Concat(controllername, "_stub", "");

   HttpControllerDescriptor versionedDescriptor;
   if (controllers.TryGetValue(newName, out versionedDescriptor))
   {
return versionedDescriptor;
   }
}
return descriptor;
    }
    return null;
}

We just have to register this selector in our webapi config -
config.Services.Replace(typeof(IHttpControllerSelector), new CustomControllerSelector(config));

Thats all, the versioning is done, you can write your own logic on which case you want to pass which controller instance. 

Saturday, May 9, 2015

Paging in WEBAPI

Lets talk about paging using webapi.There are multiple ways we can achieve pagination. We will talk about only 2 here -
1) OData :-
OData is liberary provided by Microsoft.
OData has its own query parameters and its data structure defined which can be used to achieve paging. Lot of details are given here –
http://www.asp.net/web-api/overview/odata-support-in-aspnet-web-api/supporting-odata-query-options

Lets try to understand it using an example. Lets say i have a controller named ODataSample where i am implementing paging for a Get method.
public PageResult Get(ODataQueryOptions queryOptions)
{
    List returnValue = new List() { 
"1","2","3","4","5","6","7","8"
    };
    ODataQuerySettings settings = new ODataQuerySettings() { PageSize = 2 };
    IQueryable results = queryOptions.ApplyTo(returnValue.AsQueryable(),settings);
    return new PageResult(results as IEnumerable, Request.GetNextPageLink(), Request.GetInlineCount());
}

The above example implements simple paging using power of Odata. Lets start analyzing it one by one -
1) Query parameter - ODataQueryOptions - 
public PageResult Get(ODataQueryOptions queryOptions)
this the the query options where all the odata specific query parameters will be parsed. This class has method named as ApplyTo which will be used to filter the result based on query params passed.
2) settings - 
ODataQuerySettings settings = new ODataQuerySettings() { PageSize = 1 };
ODataQuerySetting is by which we can set the default page size. The same thing can be achieved by Attributes also.
3) ApplyTo - 
IQueryable results = queryOptions.ApplyTo(returnValue.AsQueryable(),settings);
apply the filter based on query parameter passed. By this method Odata is saving you from writing custom logic for the same.
4) Return type - PageResult
return new PageResult(results as IEnumerable, Request.GetNextPageLink(), Request.GetInlineCount());
PageResult is data structure provided by Odata library. 
GetNextPageLink generate the next page link whenever required. 
GetInlineCount will give you the number of items available.

lets try to analyze few sample URLs and their responses -
get 1 item, and count of all - 
http://localhost:52252/api/ODataSample?$top=1&$inlinecount=allpages
{"Items":["1"],"NextPageLink":null,"Count":8}

get 2 items and all count
http://localhost:52252/api/ODataSample?$top=2&$inlinecount=allpages
{"Items":["1","2"],"NextPageLink":null,"Count":8}

get 3 items and count - 
http://localhost:52252/api/ODataSample?$top=3&$inlinecount=allpages
{"Items":["1","2"],"NextPageLink":"http://localhost:52252/api/ODataSample?$top=1&$inlinecount=allpages&$skip=2","Count":8}
(only first page is returned and next page link is been provided)

get 1 item after skiping 2 - 
http://localhost:52252/api/ODataSample?$top=1&$inlinecount=allpages&$skip=2
{"Items":["3"],"NextPageLink":null,"Count":8}

get 5 items and count - 
http://localhost:52252/api/ODataSample?$top=5&$inlinecount=allpages
{"Items":["1","2"],"NextPageLink":"http://localhost:52252/api/ODataSample?$top=3&$inlinecount=allpages&$skip=2","Count":8}

If you observe we asked for 5 items and in the response we got 2 and next item link saying ask for $top=3 and skip 2 items. 
Once we hit it again we get – 
{"Items":["3","4"],"NextPageLink":"http://localhost:52252/api/ODataSample?$top=1&$inlinecount=allpages&$skip=4","Count":8}

Another 2 items and link for the last one – 
http://localhost:52252/api/ODataSample?$top=1&$inlinecount=allpages&$skip=4
which eventually returns - {"Items":["5"],"NextPageLink":null,"Count":8}

Whenever the request is not able to accommodate all data in the single response, w get the link of next page in it.

2) Custom :- In case of custom paging, we can follow the same design like OData followed. Based on some query parameter we can identify which page we need to send back. The easiest way to implement this is using LINQ.
Lets try to understand this approch using an example  -

public object Get(int page = 0)
{
    return GetAccounts(page,Request);          
}
const int PAGE_SIZE = 2;
private static object GetAccounts(int page, HttpRequestMessage request)
{
    var output = new string[] { "value1", "value2", "value3", "value4", "value5", "value6", "value7", "value8" };
    var result = output.Skip(PAGE_SIZE * page)
.Take(PAGE_SIZE);
    return new {
Results = result
    };
}

lets say we implement the Get method which take which page to return.
Using LINQ skip and Take method we can filter the result and return it back.

The basic requirement of pagination is done. Now we can make it more intutive for user to use it. For example, with above implementation no client will get to know how many pages are there, and also there is no way i can identify the URL of next/previous page.

Getting the total count -
var totalCount = output.Count();
    var totalPages = Math.Ceiling((double)totalCount / PAGE_SIZE);

Creating the link for next and previous page -
var helper = new UrlHelper(request);
    var prevUrl = page>0 ? helper.Link("DefaultApi", new { page = page - 1 }) : "";
    var nextUrl = page<totalPages-1 ?  helper.Link("DefaultApi", new { page = page + 1 }) : "";

helper take the route name and route value. Routename in this case is DefaultApi only and for previous page we need to pass page number 1 less than current, and for next page it will be 1 more than current.

Hence the final code for the same becomes -
private static object GetAccounts(int page, HttpRequestMessage request)
    var output = new string[] { "value1", "value2", "value3", "value4", "value5", "value6", "value7", "value8" };
    var totalCount = output.Count();
    var totalPages = Math.Ceiling((double)totalCount / PAGE_SIZE);
    var helper = new UrlHelper(request);
    var prevUrl = page>0 ? helper.Link("DefaultApi", new { page = page - 1 }) : "";
    var nextUrl = page<totalPages-1 ?  helper.Link("DefaultApi", new { page = page + 1 }) : "";
    var result = output.Skip(PAGE_SIZE * page)
.Take(PAGE_SIZE);
    return new {
Pagination = new  {
   TotalCount = totalCount,
   TotalPages = totalPages,
   PrevPageUrl = prevUrl,
   NextPageUrl = nextUrl,
},              
Results = result
    };
}

Its good idea to pass all the pagination information in separate object, rather tahn combining it with the actual result.


Monday, February 2, 2015

Dependency Injection in MVC

Why do we need DI?
Dependency injection is very hot topic in current web world. Having DI in MVC has its own advantage. Let’s take a scenario –
I have a controller named as HomeController and it is calling a service to fetch some data.
Simple answer is we create the instance of service in the Controller itself and use it. But it won’t let us write testable code, because somebody creating Controller object in his/her test case will have to create service object first. What if we have some dependency in service also.  Tester will have to spend lot of time resolving these dependency, rather than focusing on the controller test cases.
So we should never rely upon the instance of the service in the controller, instead we should have interface. Using this we can easily mock it for our testing. Also in future if we want to replace it with some other service instance, it will be pretty straight forward to replace.

DI in MVC –
Now we agree on having a reference of interface type in the controller(because of obvious reason), now the question comes is, where to initialize it? Ideally it should be passed as a parameter to the controller, because it is not controller’s responsibility to create the service(testable code). But default MVC won’t allow us to have parameterized constructor of controller.
In order to achieve this objective we have been provided with ControllerFactory and Dependency resolver. Let’s learn in detail how it works.

Controller Creation –
MVC handler request controllerbuilder to give object of type IControllerFactory.
Controller builder- It is responsible for getting the controllerfactory.
ControllerFactory – Responsible for resolving the correct controller object
In the lifecycle of MVC, once we hit the URL, routing redirects our request to MVCHandler and which in terns request controllerBuilder for IControllerFactory object. This object is responsible for providing the object of controller. MVC provide default implementation of ControllerFacotry with name DefaultControllerFactory. This factory calls the default constructor of controller and give us the object of it.


In MVC, Every controller inherits Controller(abstract) class, which in tern inherits from ControllerBase(abstract) which inherits from IController.

Customization of Controller – 
We can create our own ControllerFactory and replace the default factory with it. We can write our own logic of how to resolve the controller. Her is the example of Controller MyController and we are introducing dependency of a service in it-
ControllerFactory implements IControllerFactory interface. 

The interface has mainly 3 methods in it – 
IController CreateController(RequestContext requestContext, string controllerName);       
SessionStateBehavior GetControllerSessionBehavior(RequestContext requestContext, string controllerName);      
void ReleaseController(IController controller);
We can create our own custom factory in the following manner – 
public class MyControllerFactory : IControllerFactory
    {
        public IController CreateController(System.Web.Routing.RequestContext requestContext, string controllerName)
        {
//Special logic to handle our controller
            if (controllerName.Equals("My"))
            {
                var svc = new MySVC();
                return new MyController(svc);
            }
            else
            {
// Default handling for other controllers
                return new DefaultControllerFactory().CreateController(requestContext,controllerName);
            }
        }
        public System.Web.SessionState.SessionStateBehavior GetControllerSessionBehavior(System.Web.Routing.RequestContext requestContext, string controllerName)
        {
            return SessionStateBehavior.Default;
        }
        public void ReleaseController(IController controller)
        {
            IDisposable disposable = controller as IDisposable;
            if (disposable != null)
                disposable.Dispose();
        }
    }

We need to register this factory in Global.asax -> application start event – 
ControllerBuilder.Current.SetControllerFactory(new MyControllerFactory());

Setting current factory using ControllerBuilder will modify the current factory and will invoke our code on resolving the controller.