Search:

Search all manuals
Search this manual
Manual
Couchbase Client Library: .NET (C#) 1.0
Additional Resources
Community Wiki
Community Forums
Couchbase SDKs
Parent Section
2 Couchbase and ASP.NET MVC 3 Tutorial
Chapter Sections
Chapters

2.5. Stage 4: Adding Login and Logout actions

A web application needs some form of user authentication. You will be creating one that uses Couchbase to store the user records. You would most likely back this data up to long-term persistent storage to avoid any data loss. Couchbase does write to disk in the case of memory pressure, and it can be considered persistent if the all of the machines are running perfectly. You can also ensure that there are replicas in the case of single or multiple machine failures. For illustrative purposes, we'll just store the user records into Couchbase.

Edit HomeController.cs and add the methods in Listing 8 after the Create() actions.

Listing 8, Login actions

/// <summary>
        /// GET: /Home/Login
        /// </summary>
        /// <returns></returns>
        public ActionResult Login()
        {
            return View();
        }

        /// <summary>
        /// POST: /Home/Login
        /// </summary>
        /// <param name="collection"></param>
        /// <returns></returns>
        [HttpPost]
        public ActionResult Login(FormCollection collection)
        {
            var client = MvcApplication.CouchbaseClient;

            var sessionToken = Guid.NewGuid();
            var cookie = new HttpCookie("COUCHBASE_SESSION", sessionToken.ToString());
            ControllerContext.HttpContext.Response.Cookies.Add(cookie);

            var encodedPassword = EncodePassword(collection["Password"]);

            // Design a key that the user will be able to retrieve again, if and only if
            // they remember what their password is. This is likely not the only way to
            // do something like this.
            String userKey = string.Format("User-{0}-{1}{2}", collection["UserName"],
                         AppSecret, encodedPassword);

            client.Store(StoreMode.Set, sessionToken.ToString() + AppSecret, userKey,
                         TimeSpan.FromMinutes(SessionTimeoutMinutes));

            // Try to retrieve the user data from the database. If it returns null,
            // the user has logged in incorrectly
            var userId = client.Get<Guid>(userKey);
            var user = client.Get<User>(userId.ToString());

            // If user is null the login failed otherwise show the Index page.
            return RedirectToAction(user == null ? "Login" : "Index");
        }

The first method returns the login form, and the second method responds to the POST when the user presses the submit button. The user's entered UserName and Password are taken from the collection object. Here, we format the userKey in the same way, and store the userKey into the database by using the sessionToken combined with the AppSecret. This is to help you learn about Couchbase, not to be taught a lesson about security. This is not secure at all, in fact. More thought would have to be made on how to provide even a small amount of security to keep unauthorized people out.

Once the keys are correct, if the database contains a record for the userKey, the user's userId will be found, and from that the stored User record will be found. If the code finds a User, the browser will be redirected to the Index action, otherwise back to the Login action it goes.

Next add a new view to the Views/Home folder named Login with content from Listing 9.

Listing 9, Login.cshtml

@{
    ViewBag.Title = "Login";
}
<h2>Login</h2>

@using (Html.BeginForm())
{
    Html.ValidationSummary(true);
    <fieldset>
        <legend>Please log in to the system:</legend>
        <p>
            UserName:
            <input type="text" name="UserName" />
        </p>
        <p>
            Password:
            <input type="password" name="Password" />
        </p>
        <p> Don't have an account? @Html.ActionLink("Create one...","Create")
</p>
        <p>
            <input type="submit" value="Log In" />
        </p>
    </fieldset>
}

Notice here, that an action link has been set up in the login page to create a new user account if you haven't already created one. This executes the create action from the previous stage.

Next you will likely want to be able to log out of the application to add other users for testing. Add the Logout action in Listing 10 after the Login actions in HomeController.cs.

Listing 10, Logout action

/// <summary>
        /// GET /Home/Logout
        /// </summary>
        /// <returns></returns>
        public ActionResult Logout()
        {
            var client = MvcApplication.CouchbaseClient;

            var cookie = ControllerContext.HttpContext
                .Request.Cookies["COUCHBASE_SESSION"];
            if (cookie != null)
            {
                var sessionToken = cookie.Value;
                client.Remove(sessionToken + AppSecret);
            }

            return RedirectToAction("Login");
        }

The Logout action gets the COUCHBASE_SESSION cookie, reads the sessionToken and removes that token from the database. Then it redirects the user's browser to the Login action. Once the session token is removed, the cookie is effectively invalid.

Finally you need to add the logout link to the bottom of the Index view:

<p>@Html.ActionLink("Logout...","Logout")</p>

At this point, you should be able to start using the application to create user accounts, and log in and out of these accounts given the username and password. However, the flow of the application would be enhanced by the addition of an authentication check. You will add this in the next stage.