KUMAR ATLA
KUMAR ATLA

Reputation: 31

How to write unit test case which include FormsAuthenticationTicket in MVC

In the following method, I am decrypting a cookie to return it with a UserName in it. I tried writing a test case for it but the cookie returned is null as it is not logged in. Can any one help me write a test case for it?

public string Username()
        {
            LoggingManager.Debug("Entering Username - UserManager");
            var authCookie = HttpContext.Current.Request.Cookies[FormsAuthentication.FormsCookieName.ToString(CultureInfo.InvariantCulture)];
            if (authCookie != null)
            {
                FormsAuthenticationTicket authTicket = FormsAuthentication.Decrypt(authCookie.Value);
                if (authTicket != null) return authTicket.Name;
            }
            const string anonymys = "xyz";
            LoggingManager.Debug("Exiting Username - UserManager");
            return anonymys;
        }

Upvotes: 3

Views: 925

Answers (1)

Daniel Mann
Daniel Mann

Reputation: 59010

You're bumping into the fun of unit testing something that uses static classes right now. You have two options:

  1. Wrap the functionality you want to get out of HttpContext in a class that implements an interface, then inject a mock into the class for unit testing purposes.

  2. Use something like the Fakes framework to create a shim that will temporarily create a fake HttpContext for unit testing.

Example of approach #1:

public interface ICookieProvider
{
    HttpCookieCollection GetCookies();
}

public class RealCookieProvider : ICookieProvider
{
    public HttpCookieCollection GetCookies() 
    {
        return HttpContext.Current.Request.Cookies;
    }
}

Then, inject the cookie provider into your controller via the constructor:

private ICookieProvider cookieProvider;
public MyController(ICookieProvider cookieProvider)
{
    this.cookieProvider = cookieProvider;
}
public MyController() : this(new RealCookieProvider()) { }

Then you can use a mocking framework to create an ICookieProvider that returns whatever you want.

Note that I prefer approach #1 in almost all cases. Approach #2 just only hides the issue, which is that you've written tightly-coupled, hard-to-test code. Approach #1 solves the problem by introducing loose coupling.

Upvotes: 3

Related Questions