Thursday, March 22, 2007

Screwing up HTTP Session for Servlet/JSP

Prerequisites:
1. Browsers under Mozilla project (e.g. Firefox, SeaMonkey)
2. Enable cookies
3. Tomcat (probably all Java web containers)

Procedure:
1. Write a page that use back-slashes as the directory seperator (e.g. http://www.abc.com\app\page.jsp)
2. Include this page with absolute path in all pages

Why:
1. The browser encode back-slashes as %5C. So, http://www.abc.com\app\page.jsp will be encoded as http://www.abc.com%5Capp%5Cpage.jsp
2. The browser tries to look up the cookies for the domain. However, the browser think that the domain name is www.abc.com%5Capp%5Cpage.jsp instead of www.abc.com
3. The browser cannot find the cookies for the domain. So, it does not send the cookies to the browser.
4. When cookies is enabled, Java Servlet and JSP uses it to store the session ID
5. Since the cookies was not found in the request header, the web container creates a new session and send to session ID with Set-Cookie header.
6. The browser uses the new session ID for the next request.
7. As a result, the web container creates new session for each browser request and the sessions are screwed up.

What about other browsers? I think IE is smart enough to replace all back-slashes to slashes before it does further processing. I don't know about others though...

You may want to ask why you would use back-slash. My answer is "No, you may not but your staff or your outsource partner may." In a workflow engine we are studying, we found the following JavaScript:
document.write("<iframe src='<%=request.getContextPath()%>\\app\\page.jsp'>")

My colleague asked for help about why the session does not work in Firefox. Since the code was written by different parties, we know nothing about the workflow engine. I alone used 6 man-hours to fix the BUG. I think I know fairly well on HTTP and Java Servlet. I tried many possible solutions like finding the HttpSession.invalidate(), session.removeAttribute(), appending the jsessionid, etc. Finally, I used a packet sniffer to dig out the pattern that changes the jsessionid cookie and recognize the weired %5C URL in a GET command.

No comments: