I have created a module to handle authentication to Microsoft HealthVault. In the BeginRequest event handler I am checking for the authToken and when it's received, I am creating a new cookie to hold the user's information for use later on in the controller.
I am losing the cookie but maybe I am looking in the wrong place.
The event handler take an HttpApplication as the only parameter, so I add the cookie to application.Response.Cookies collection. The question comes down to: is this instance of HttpApplication a singleton? Is it the same as System.Web.HttpContext.Current.ApplicationInstance?
Perhaps though, cookies set at this point in the lifecycle are later wiped out. Is that what I am doing wrong?
Any help is greatly appreciated.
UPDATE
I have changed a few things since I posed the question. I am now handling PreRequestEventHandler in my HttpModule. I am letting HealthVault's WebApplicationUtilities object do the cookie creation and storage, though conceptually nothing has really changed. I am not having any trouble creating the cookie or reading it the first time after it's created.
Here is my cookie creation code in the HttpModule event handler:
static void PreRequestHandlerExecute(Object sender, EventArgs e)
{
HttpContext ctx = System.Web.HttpContext.Current;
string authToken = ctx.Request.Params["wctoken"];
if (!String.IsNullOrEmpty(authToken))
{
personInfo = WebApplicationUtilities.GetPersonInfo(authToken);
WebApplicationUtilities.SavePersonInfoToCookie(ctx, personInfo);
NameValueCollection query = HttpUtility.ParseQueryString(ctx.Request.Url.Query);
query.Remove("wctoken");
query.Remove("suggestedtokenttl");
UriBuilder newUrl = new UriBuilder(ctx.Request.Url);
newUrl.Query = query.ToString();
//app.Response.Redirect(newUrl.Uri.OriginalString);
}
}
Notice that the redirect is commented. On the first request (after auth) the cookie is created and my default action is able to then read it using LoadPersonInfoFromCookie(). I found that doing the redirect caused the cookie not to be sent to the client.
I have also noticed that on the subsequent requests, the cookie is not present in the Request.Cookies collection, so when LoadPersonInfoFromCookie() runs, I end up with a null. Strangely I can see the cookie in the Response object, but the contents are empty.
Here is the action code, just because...
public HttpContext Context
{
get { return System.Web.HttpContext.Current; }
}
public ActionResult Dashboard()
{
try
{
HealthVaultAccountModel model = new HealthVaultAccountModel();
PersonInfo personInfo = WebApplicationUtilities.LoadPersonInfoFromCookie(Context);
if (personInfo != null)
model.PersonName = personInfo.Name;
return View(model);
}
catch (Exception ex)
{
return RedirectToAction("Index", "Error");
}
}
UPDATE
Here is the cookie from the Immediate Window. I even bumped the Expires time out 30 days.
In the default action right after it is created
Context.Request.Cookies["_wcpage"]
{System.Web.HttpCookie}
Domain: null
Expires: {8/13/2012 5:24:02 PM}
HasKeys: true
HttpOnly: true
Name: "_wcpage"
Path: "/"
Secure: true
Shareable: false
Value: "p=1:1234-pVTbctowEP0V..."
Values: {p=1%3a1234-pVTbctowEP0V...}
In the action on the next request
Context.Request.Cookies["_wcpage"]
null
Interestingly the cookie is defined in the response object, but the value is gone and the expires time is reset.
Context.Response.Cookies["_wcpage"]
{System.Web.HttpCookie}
Domain: null
Expires: {1/1/0001 12:00:00 AM}
HasKeys: false
HttpOnly: false
Name: "_wcpage"
Path: "/"
Secure: false
Shareable: false
Value: ""
Values: {}
How are you creating/fetching the cookie? The SavePersonInfoToCookie
and LoadPersonInfoFromCookie
methods on the WebApplicationUtilities
class will do it for you.
BeginRequest:
// given an authToken from the querystring/post values
var personInfo = WebApplicationUtilities.GetPersonInfo(authToken);
WebApplicationUtilities.SavePersonInfoToCookie(application.Context, personInfo);
Controller:
var personInfo = WebApplicationUtilities.LoadPersonInfoFromCookie(HttpContext);