09 August 2006

Coping with links in cookieless mode in ASP.NET2

A new web site project that I am working on might be used a lot from internet cafes and the like where it is possible that cookies are disabled. I therefore started to look at how to support cookieless mode in an existing alpha web site of mine www.spacebrowse.com - go there to try it out with cookies disabled once you have registered for free.

The ASP.NET2 site uses Forms authentication, specified in Web.Config as follows:
<authentication mode="Forms">
   <forms protection="All">
</authentication>


cookieless - UseDeviceProfile

The forms element "cookieless" attribute has a default value of "UseDeviceProfile". Basically this doesn't work if a browser has cookies turned off. "UseDeviceProfile" looks at the type of viewer, so it will assume that cookies are turned on for IE/FF/etc, but will assume they are not for some other device types.

cookieless - UseUri

Another option for "cookieless" is "UseUri" which means that cookies are not used. Instead, ASP.NET2 mangles the URL to include the information that would have been stored in the cookie. A http: URL such as this:
http://localhost/SpaceBrowse/Default.aspx
is mangled to look like this:
http://localhost/SpaceBrowse/(F(ekocDSRz...PZKv3ah41))/Default.aspx
where a lot of characters have been removed at the ellipses.

If you look carefully, you will see that the mangled URL contains an extra folder name. When I saw this, I thought that all resources and relative links from this page would go wrong. In fact, they don't because the ASP.NET ISAPI DLL filter intercepts all requests and resolves them correctly if it detects mangled URLs. Also note that Request.Path as seen by the ASPX page is correctly SpaceBrowse/Default.aspx, ie without any mangling.

cookieless mangled URL links

However there is an issue as regards links. If you want the user to stay logged in, then the URL they browse to has to have a mangled URL. This means that you must use relative links to stay logged in. Any absolute links will not include the mangled URL. You will be OK if you use <asp:hyperlink> and the like with NavigateUrl="~/sites.aspx" or whatever because ASP.NET resolves the ~/ correctly.

My MasterPage template is used by pages in various directories. My original code included static absolute HTML links to pages on the site. These links did not include the mangled URL and so the user's login status is forgotten. The solution is to use ASP.NET controls for all such links (even though that might require a small amount more server-side processing).

Aside 1: When testing "UseUri" mode in IE using ASP.NET Development Server, if you have links to directories then they will not work if they end in "/". You must change them to "/Default.aspx" to be able to see the requested page in cookieless mode. When working through IIS, ordinary directory requests will work OK.

Actually, it is important that all your links to directories end in / - otherwise the mangled URL will be lost.

Aside 2: When you log off in mangled URL mode (using asp:LoginStatus LogoutPageUrl="~/default.aspx"), the URL you get redirected looks like this:
http://localhost/SpaceBrowse/(X(1))/default.aspx
Although strange, everything works OK.

cookieless - AutoDetect

Anyway, back at my original problem: how to cope if a browser has cookies turned off. The best option is to set "cookieless" to "AutoDetect" in the Forms element. With this setting, ASP.NET probes to see if cookies are set; if cookies are enabled, then they are used; if not, then mangled URLs are used.

The probing mechanism seems to kick in when you click a Login button. To determine if a browser session has cookies enabled, this parameter is added to the login URL: AspxAutoDetectCookieSupport=1.

PS. I found it easiest to test in FF rather than IE because FF has a simple method of turning off cookies; IE does it on a zone basis which I could quickly not get to work for the dev server URL http://localhost:1234/whatever/

PPS. Found that cookies must be enabled for yahoo/flickr to let you log on.

7 comments:

Anonymous said...

Chris, This helps a lot. I have been playing with setting the Cookieless="UseUri" and came across this post and it helped a lot.

Anonymous said...

There is also an issue with browsers saving your password. Since the url will change on every visit, browsers will never recognize your saved passwords as being from that url.

Anonymous said...

thanks a lot, i'm a day that i search a workaround for use link and useUri

Raj said...

Thanks for helpful article .
I want to know more about Cookieless.
What is difference between these
cookieless="UseUri"
and
cookieless="true"

I have used both mode , Result is same. But , I don't know where to use these mode.
Please clarify my doubts.
Regards
Rajesh

Chris Cant said...

According to the MS docs, there isn't a cookieless="true" option, so I don't know what this does.

Anonymous said...

Fyi, you can use the IE Developer's Toolbar to disable cookies. When you have it up and running select "Cache->Disable Cookies".

Anonymous said...

It looks like cookieless="true|false" was used in .NET 1.1 (http://msdn.microsoft.com/en-us/library/h6bb9cz9%28v=vs.71%29.aspx)