// Copyright (C) 2008 Google Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package com.google.enterprise.connector.servlet;

import com.google.common.base.Preconditions;
import com.google.enterprise.saml.server.BackEndImpl;
import com.google.enterprise.saml.common.SecurityManagerServlet;
import com.google.enterprise.saml.common.GsaConstants;
import com.google.enterprise.sessionmanager.SessionManagerInterface;
import com.google.enterprise.security.connectors.formauth.CookieUtil;

import java.util.Vector;
import java.io.IOException;
import java.io.PrintWriter;

import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.Cookie;

/**
 * Reads and outputs any available SessionManager data generated by the
 * Security Manager.
 */
public class SessionReader extends HttpServlet {

  private static final long serialVersionUID = 1L;

  @Override
  protected void doGet(HttpServletRequest req,
                       HttpServletResponse res)
      throws IOException
  {
    Preconditions.checkNotNull(req);
    // TODO: implement a way to retrieving specific SID/key values via browser
    // param
    BackEndImpl backend = (BackEndImpl) SecurityManagerServlet.getBackEnd(getServletContext());
    SessionManagerInterface sm = backend.getSessionManager();

    StringBuilder msg = new StringBuilder("Message: <br>");
    for (String sid : backend.sessionIds) {
      msg.append(readSession(sm, sid));
    }
   
    res.setContentType("text/html");
    PrintWriter out = res.getWriter();
    out.println("<HTML><HEAD><TITLE>Session Test</TITLE>"+
                "</HEAD><BODY>Session Test!<br>" + msg.toString() +
                "</BODY></HTML>");
    out.close();
  }

  private String readSession(SessionManagerInterface sm, String sessionId) {
    String user = denullify(sm.getValue(sessionId, GsaConstants.AUTHN_MECH_PREFIX
        + GsaConstants.AuthNMechanism.BASIC_AUTH.toString()
        + GsaConstants.AUTHN_MECH_ID));
    String domain = denullify(sm.getValue(sessionId, GsaConstants.AUTHN_MECH_BASIC_AUTH_USER_DOMAIN_KEY));
    String password = denullify(sm.getValue(sessionId, GsaConstants.AUTHN_MECH_PREFIX
        + GsaConstants.AuthNMechanism.BASIC_AUTH.toString()
        + GsaConstants.AUTHN_MECH_TOKEN));
    String cookies = denullify(sm.getValue(sessionId, GsaConstants.AUTHN_MECH_PREFIX
        + GsaConstants.AuthNMechanism.FORMS_AUTH.toString()
        + GsaConstants.AUTHN_MECH_TOKEN));

    StringBuilder dCookies = new StringBuilder("");
    Vector<Cookie> v = CookieUtil.deserializeCookies(cookies);
    for (Cookie c : v) {
      dCookies.append(c.getName() + ":" + c.getValue() + "<br>");
    }

    return "<p>Session ID: " + sessionId + "<br>" +
        "User: " + user + "<br>" +
        "Domain: " + domain + "<br>" +
        "Password: " + password + "<br>" +
        "Cookies: " + cookies + "<br>" +
        "Deserialized Cookies: " + dCookies.toString() + "</p>";
  }

  private String denullify(String s) {
    return (null == s) ? "null" : s;
  }

  /**
   * Returns servlet info.
   * @return informational message
   *
   */
  @Override
  public String getServletInfo()
  {
    return "Session Test";
  }
}

@@ -1986,41 +1986,216 @@
     
-msg.append(readSession(sm, sid));
+if (sm.sessionExists(sid)) %7B%0A        msg.append(readSession(sm, sid));%0A      %7D else %7B%0A        backend.sessionIds.remove(sid);%0A        msg.append(%22%3Cp%3ESession ID: %22 + sid + %22 expired. Removing...%3C/p%3E%22);%0A      %7D
 %0A   

Make SessionReader work even with expired session ids.