Reputation: 793
I am using Tomcat 7 and trying to store some object into session, but whenever there is a new request from the same client it looks like Tomcat is creating a new session.
Following is my code which is basically a filter which is calling another application which does the Authentication and Authorization and returns an object. I am using Apache httpclient for this communication
Filter Class
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
// If the request is for any static contents do not invoke this filter
if (!isWorthyRequest((HttpServletRequest)request)) {
chain.doFilter(request, response);
return;
}
HttpClient httpClient = null;
try {
if (validateApp && request instanceof HttpServletRequest) {
HttpServletRequest httpServletRequest = (HttpServletRequest)request;
HttpSession httpSession = httpServletRequest.getSession(false);
if (null != httpSession && null != httpSession.getAttribute("userInfoMap")) {
LOG.info(" User is already Authenticated :: session Id :: "+httpSession.getId()
+" Created At :: "+ new Date(httpSession.getCreationTime())
+" Last Accessed At :: "+new Date(httpSession.getLastAccessedTime()));
// The user is already Authenticated & Authorize just pass the request to next chain
} else {
LOG.info("Calling Authenication / Authorization Module :: URL "+securityServiceURL);
// Calling Authentication and Authorization
httpClient = new DefaultHttpClient();
HttpPost httpPost = new HttpPost(securityServiceURL);
// Getting the SM Header
httpPost.setHeader(IaasConstants.SM_USER, httpServletRequest.getHeader(IaasConstants.SM_USER));
List<NameValuePair> urlParameters = new ArrayList<NameValuePair>();
// urlParameters.add(new BasicNameValuePair(IaasConstants.SOURCE_APP_NAME, "vElite"));
urlParameters.add(new BasicNameValuePair(IaasConstants.SUB_SERVICE_NAME, IaasConstants.SERVICE_AUTHENTICATE_USER));
httpPost.setEntity(new UrlEncodedFormEntity(urlParameters));
HttpResponse httpResponse = httpClient.execute(httpPost);
HttpEntity httpEntity = httpResponse.getEntity();
String jsonString = null;
if (null != httpEntity) {
jsonString = EntityUtils.toString(httpEntity);
}
HttpServletResponse httpServletResponse = (HttpServletResponse)response;
// User is a valid user
if (httpResponse.getStatusLine().getStatusCode() == HttpServletResponse.SC_OK) {
LOG.info(" User is valid :: user :: "+httpServletRequest.getHeader(IaasConstants.SM_USER)+" jsonObject :: "+jsonString);
if (null != jsonString) {
Gson gSon = new Gson();
Type mapType = new TypeToken<Map<String, Object>>(){}.getType();
Map<String, Object> userInfoMap = gSon.fromJson(jsonString, mapType);
httpSession = httpServletRequest.getSession(false);
if (null == httpSession) {
LOG.info("Session Created and the userInfoMap is stored inside session :: ");
httpSession = httpServletRequest.getSession(true);
httpSession.setAttribute(IaasConstants.USER_INFO_MAP, userInfoMap);
} else {
httpSession.setAttribute(IaasConstants.USER_INFO_MAP, userInfoMap);
}
}
} else {
// Bad User
LOG.info("Invalid User ::: with status code :: "
+httpResponse.getStatusLine().getStatusCode()
+" Status Message :: "+httpResponse.getStatusLine().getReasonPhrase());
httpServletResponse.setStatus(httpResponse.getStatusLine().getStatusCode());
httpServletResponse.sendError(httpResponse.getStatusLine().getStatusCode());
httpServletResponse.flushBuffer();
return;
}
}
}
HttpServletResponseCopier responseCopier = new HttpServletResponseCopier((HttpServletResponse) response);
// pass the request along the filter chain
chain.doFilter(request, responseCopier);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
if (null != httpClient) {
httpClient.getConnectionManager().shutdown();
}
}
}
/**
* @see Filter#init(FilterConfig)
*/
public void init(FilterConfig fConfig) throws ServletException {
// TODO Auto-generated method stub
this.fConfig = fConfig;
validateApp = Boolean.valueOf(fConfig.getInitParameter(IaasConstants.VALIDATE_APP));
securityServiceURL = fConfig.getInitParameter(IaasConstants.SECURITY_SERVICE_URL);
}
private boolean isWorthyRequest(HttpServletRequest request) {
String url = request.getRequestURI().toString();
Matcher m = excludeUrls.matcher(url);
return (!m.matches());
}
Web.xml
<session-config>
<session-timeout>15</session-timeout>
<cookie-config>
<http-only>true</http-only>
<secure>true</secure>
</cookie-config>
</session-config>
What to do so that Tomcat will maintain session for requests coming from same client?
I have tried following options which did not work for me.
Adding Valve in global context.xml like
<Valve className="org.apache.catalina.authenticator.BasicAuthenticator" changeSessionIdOnAuthentication="false"/>
removing <http-only>true</http-only>
option from web.xml
As I understand due to Session Fixation Protection Issue Tomcat creates new session ID for every request but then is there any other alternative to maintain session?
Upvotes: 2
Views: 10310
Reputation: 24146
<secure>true</secure>
means that cookie should be set only in HTTPS connection, I suppose you making HTTP, so remove it
Upvotes: 4