Lakkakula's Blog

September 9, 2009

Developing Web 2.0 Portal using Asp.Net MVC, Microsoft Ajax Client Templates and jQuery with drag and drop widget personalization – Part 4

Filed under: Ajax Client Templates, Asp.Net, Asp.Net MVC, jQuery, MVC, OpenID — Tags: — Venkata Uma lakkakula @ 7:43 pm

In this series:
1. Introduction
2. Part 1 – Portal Core Functionality
3. Part 2 – Drag and Drop Widget Personalization
4. Part 3 – Building Widget Gallery
5. Part 4 – Introduce Tabs and Users
6. Part 5 – Enhancements and Conclusion

Working portal at: http://aspspider.info/lakkakula/local.aspx

Alright, finally I’ve got some time to write about users and tabs. In previous posts we have seen the core functionality of the portal which is to load widgets through ajax calls and displaying widget gallery. Once we have the core functionality ready, its time to tie it to Users and Tabs. Talking about users, it is typical to implement forms based authentication  for public web sites. When it comes to asp.net or asp.net MVC the natural way is to go through Membership, Role and Profile “Providers“. Let us do it something different here, the latest buzz is “Open ID“, so why not implement it?

Guest User Screenshot

lg-guest

Authenticated user screen-shot

lg-auth

This is what we will do here:lg-flow

To keep things simple, we will not be storing guest user’s activity, such as new widget creation, widget location move etc. For the logged in users we will allow to create new tabs, add widgets, move widgets and delete widgets.

Now for some code: Open ID implementation is straight forward, you can download samples from dotnetopenid project site. What I want to show is, generally after authentication we would be interested to know more about the user such as email, full name etc. DotnetOpenId library has an response extension method which will pull this extra information for us. (note: the extra user information depends on the actual open id provider, in other words its not guaranteed that we will always get response for extra user info.)  Here is the simple implementation of authentication:

[ValidateInput(false)]
public ActionResult Authenticate()
{
var openid = new OpenIdRelyingParty();
var response = openid.GetResponse();
if (response == null)
{
// Stage 2: user submitting Identifier
/*var req = openid.CreateRequest(Request.Form["openid_identifier"]);
var fields = new DotNetOpenAuth.OpenId.Extensions.SimpleRegistration.ClaimsRequest();// .SimpleRegistrationRequestFields();
fields.Email = DotNetOpenAuth.OpenId.Extensions.SimpleRegistration.ClaimsRequest;
fields.Nickname = DotNetOpenId.Extensions.SimpleRegistrationRequest.Request;
fields. .AddToRequest(req);
req.RedirectToProvider(); */
Identifier id;
if (Identifier.TryParse(Request.Form["openid_identifier"], out id))
{
try
{
//return openid.CreateRequest(Request.Form["openid_identifier"]).RedirectingResponse.AsActionResult();
var request = openid.CreateRequest(Request.Form["openid_identifier"]);

request.AddExtension(new ClaimsRequest
{
BirthDate = DemandLevel.Request,
Country = DemandLevel.Request,
Email = DemandLevel.Require,
FullName = DemandLevel.Request,
Gender = DemandLevel.Request,
Language = DemandLevel.Request,
Nickname = DemandLevel.Request,
PostalCode = DemandLevel.Request,
TimeZone = DemandLevel.Request
});

return request.RedirectingResponse.AsActionResult();

}
catch (ProtocolException ex)
{
ViewData[“Message”] = ex.Message;
return RedirectToAction(“Index”, “Home”);
}
}
else
{
ViewData[“Message”] = “Invalid identifier”;
return RedirectToAction(“Index”, “Home”);
}
}
else
{
var res = response.GetUntrustedExtension<ClaimsResponse>();
//var res = response.GetExtension<ClaimsResponse>();
// Stage 3: OpenID Provider sending assertion response
switch (response.Status)
{
case AuthenticationStatus.Authenticated:
var name = response.ClaimedIdentifier.ToString();

if (res != null && res.Nickname != null)
Session[“FriendlyIdentifier”] = res.Nickname;
else if(res!=null && res.Email!=null)
Session[“FriendlyIdentifier”] = res.Email;
else
Session[“FriendlyIdentifier”] = name;

//user setup
using (LinksgridDataContext db = new LinksgridDataContext())
{
var userId = (from u in db.LGUsers
where u.Name == name
select u.Id).SingleOrDefault();
if (userId <= 0)
{
LGUser newUser = new LGUser();
newUser.Name = name;

newUser.BirthDate = res.BirthDate.ToString();
newUser.Country = res.Country;
newUser.Email = res.Email;
newUser.FullName = res.FullName;
newUser.Gender = res.Gender==null?string.Empty:res.Gender.Value.ToString();
newUser.Language = res.Language;
newUser.Nickname = res.Nickname;
newUser.PostalCode = res.PostalCode;
newUser.TimeZone = res.TimeZone;

db.LGUsers.InsertOnSubmit(newUser);

db.SubmitChanges();

repoWidget.NewUserSetup(newUser.Id);

}

}

FormsAuthentication.SetAuthCookie(response.ClaimedIdentifier, false);
return RedirectToAction(“Index”, “Home”);
case AuthenticationStatus.Canceled:
ViewData[“Message”] = “Canceled at provider”;
return RedirectToAction(“Index”, “Home”);
case AuthenticationStatus.Failed:
ViewData[“Message”] = response.Exception.Message;
return RedirectToAction(“Index”, “Home”);
}
}
return new EmptyResult();
}

}

Here is the configuration required for OpenId response extension

<configSections>

<section name=”uri” type=”System.Configuration.UriSection, &#xD;&#xA;            System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089″
/>
<section name=”dotNetOpenAuth” type=”DotNetOpenAuth.Configuration.DotNetOpenAuthSection”
requirePermission=”false” allowLocation=”true”/>
</configSections>
<uri>
<idn enabled=”All”/>
<iriParsing enabled=”true”/>
</uri>
<dotNetOpenAuth>
<openid maxAuthenticationTime=”0:05″>
<relyingParty>
<security
requireSsl=”false”
minimumRequiredOpenIdVersion=”V10″
minimumHashBitLength=”160″
maximumHashBitLength=”256″
requireDirectedIdentity=”false”
requireAssociation=”false”
rejectUnsolicitedAssertions=”false”
rejectDelegatingIdentifiers=”false”
ignoreUnsignedExtensions=”false”
privateSecretMaximumAge=”07:00:00″ />
<behaviors>
<add type=”DotNetOpenAuth.OpenId.Behaviors.AXFetchAsSregTransform, DotNetOpenAuth” />
</behaviors>
</relyingParty>
</openid>
<messaging>
<untrustedWebRequest>
<whitelistHosts>
<!– since this is a sample, and will often be used with localhost –>
<add name=”localhost” />
</whitelistHosts>
</untrustedWebRequest>
</messaging>
</dotNetOpenAuth>

Blog at WordPress.com.