/* | |
* Copyright 2003,2004 The Apache Software Foundation. | |
* | |
* 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 org.apache.pluto.internal.impl; | |
import java.util.Enumeration; | |
import java.util.Vector; | |
import javax.portlet.PortletContext; | |
import javax.portlet.PortletSession; | |
import javax.portlet.PortletSessionUtil; | |
import javax.servlet.http.HttpSessionContext; | |
import javax.servlet.http.HttpSession; | |
import javax.servlet.ServletContext; | |
import org.apache.pluto.internal.InternalPortletWindow; | |
import org.apache.pluto.util.ArgumentUtility; | |
import org.apache.commons.logging.Log; | |
import org.apache.commons.logging.LogFactory; | |
/** | |
* Implementation of the <code>javax.portlet.PortletSession</code> interface. | |
* | |
* @author <a href="mailto:ddewolf@apache.org">David H. DeWolf</a> | |
* @author <a href="mailto:zheng@apache.org">ZHENG Zhong</a> | |
*/ | |
public class PortletSessionImpl implements PortletSession, HttpSession { | |
/** Logger. */ | |
private static final Log LOG = LogFactory.getLog(PortletSessionImpl.class); | |
/** The default scope (<code>PORTLET_SCOPE</code>) for storing objects. */ | |
private static final int DEFAULT_SCOPE = PortletSession.PORTLET_SCOPE; | |
/** The portlet scope namespace as defined in PLT. 15.3. */ | |
private static final String PORTLET_SCOPE_NAMESPACE = "javax.portlet.p."; | |
/** The portlet window ID / attribute name separator as defined in PLT. 15.3. */ | |
private static final char ID_NAME_SEPARATOR = '?'; | |
// Private Member Variables ------------------------------------------------ | |
/** The wrapped HttpSession object. */ | |
private HttpSession httpSession = null; | |
/** The portlet context. */ | |
private PortletContext portletContext = null; | |
/** The internal portlet window. */ | |
private InternalPortletWindow internalPortletWindow = null; | |
// Constructor ------------------------------------------------------------- | |
/** | |
* Constructs an instance. | |
*/ | |
public PortletSessionImpl(PortletContext portletContext, | |
InternalPortletWindow internalPortletWindow, | |
HttpSession httpSession) { | |
this.portletContext = portletContext; | |
this.internalPortletWindow = internalPortletWindow; | |
this.httpSession = httpSession; | |
} | |
// PortletSession Impl: Attributes ----------------------------------------- | |
public Object getAttribute(String name) { | |
return getAttribute(name, DEFAULT_SCOPE); | |
} | |
/** | |
* Returns the attribute of the specified name under the given scope. | |
* | |
* @param name the attribute name. | |
* @param scope the scope under which the attribute object is stored. | |
* @return the attribute object. | |
*/ | |
public Object getAttribute(String name, int scope) { | |
ArgumentUtility.validateNotNull("attributeName", name); | |
String key = (scope == PortletSession.APPLICATION_SCOPE) | |
? name : createPortletScopedId(name); | |
return httpSession.getAttribute(key); | |
} | |
public Enumeration getAttributeNames() { | |
return getAttributeNames(DEFAULT_SCOPE); | |
} | |
public Enumeration getAttributeNames(int scope) { | |
// Return all attribute names in the nested HttpSession object. | |
if (scope == PortletSession.APPLICATION_SCOPE) { | |
return httpSession.getAttributeNames(); | |
} | |
// Return attribute names with the portlet-scoped prefix. | |
else { | |
Vector portletScopedNames = new Vector(); | |
for (Enumeration en = httpSession.getAttributeNames(); | |
en.hasMoreElements(); ) { | |
String name = (String) en.nextElement(); | |
if (isInCurrentPortletScope(name)) { | |
portletScopedNames.add( | |
PortletSessionUtil.decodeAttributeName(name)); | |
} | |
} | |
return portletScopedNames.elements(); | |
} | |
} | |
public void removeAttribute(String name) { | |
removeAttribute(name, DEFAULT_SCOPE); | |
} | |
public void removeAttribute(String name, int scope) { | |
ArgumentUtility.validateNotNull("attributeName", name); | |
if (scope == PortletSession.APPLICATION_SCOPE) { | |
httpSession.removeAttribute(name); | |
} else { | |
httpSession.removeAttribute(createPortletScopedId(name)); | |
} | |
} | |
public void setAttribute(String name, Object value) { | |
setAttribute(name, value, DEFAULT_SCOPE); | |
} | |
public void setAttribute(String name, Object value, int scope) { | |
ArgumentUtility.validateNotNull("attributeName", name); | |
if (scope == PortletSession.APPLICATION_SCOPE) { | |
httpSession.setAttribute(name, value); | |
} else { | |
httpSession.setAttribute(createPortletScopedId(name), value); | |
} | |
} | |
// PortletSession Impl: Other Methods -------------------------------------- | |
public PortletContext getPortletContext() { | |
return portletContext; | |
} | |
public long getCreationTime() { | |
return httpSession.getCreationTime(); | |
} | |
public String getId() { | |
return httpSession.getId(); | |
} | |
public long getLastAccessedTime() { | |
return httpSession.getLastAccessedTime(); | |
} | |
public int getMaxInactiveInterval() { | |
return httpSession.getMaxInactiveInterval(); | |
} | |
public void invalidate() throws IllegalStateException { | |
httpSession.invalidate(); | |
} | |
public boolean isNew() throws IllegalStateException { | |
return httpSession.isNew(); | |
} | |
/** | |
* Specifies the time, in seconds, between client requests, before the | |
* portlet container invalidates this session. A negative time indicates | |
* the session should never timeout. | |
* <p> | |
* [Portlet Spec. PLT. 15.4.] If the PortletSession object is invalidated | |
* by a portlet, the portlet container must invalidate the associated | |
* HttpSession object. | |
* </p> | |
* @param interval an integer specifying the number of seconds. | |
*/ | |
public void setMaxInactiveInterval(int interval) { | |
httpSession.setMaxInactiveInterval(interval); | |
if (LOG.isDebugEnabled()) { | |
LOG.debug("Session timeout set to: " + interval); | |
} | |
} | |
// Private Methods --------------------------------------------------------- | |
/** | |
* Creates portlet-scoped ID for the specified attribute name. | |
* Portlet-scoped ID for a given attribute name has the following form: | |
* <code>javax.portlet.p.<ID>?<name></code> | |
* where <code>ID</code> is a unique identification for the portlet window | |
* (assigned by the portal/portlet-container) that must not contain a '?' | |
* character. <code>name</code> is the attribute name. | |
* <p> | |
* Refer to Portlet Specification PLT. 15.3 for more details. | |
* </p> | |
* @param name the attribute name. | |
* @return portlet-scoped ID for the attribute name. | |
*/ | |
private String createPortletScopedId(String name) { | |
StringBuffer buffer = new StringBuffer(); | |
buffer.append(PORTLET_SCOPE_NAMESPACE); | |
buffer.append(internalPortletWindow.getId().getStringId()); | |
buffer.append(ID_NAME_SEPARATOR); | |
buffer.append(name); | |
return buffer.toString(); | |
} | |
/** | |
* Checks if the attribute name in APPLICATION_SCOPE is in the current | |
* portlet scope. | |
* @param name the attribute name to check. | |
* @return true if the attribute name is in the current portlet scope. | |
* @see #createPortletScopedId(String) | |
*/ | |
private boolean isInCurrentPortletScope(String name) { | |
// Portlet-scoped attribute names MUST start with "javax.portlet.p.", | |
// and contain the ID-name separator '?'. | |
if (name.startsWith(PORTLET_SCOPE_NAMESPACE) | |
&& name.indexOf(ID_NAME_SEPARATOR) > -1) { | |
String id = name.substring(PORTLET_SCOPE_NAMESPACE.length(), | |
name.indexOf(ID_NAME_SEPARATOR)); | |
return (id.equals(internalPortletWindow.getId().getStringId())); | |
} | |
// Application-scoped attribute names are not in portlet scope. | |
else { | |
return false; | |
} | |
} | |
// HttpSession Impl -------------------------------------------------------- | |
public ServletContext getServletContext() { | |
return httpSession.getServletContext(); | |
} | |
/** | |
* DEPRECATED: implemented for backwards compatability with HttpSession. | |
* @deprecated | |
*/ | |
public HttpSessionContext getSessionContext() { | |
return httpSession.getSessionContext(); | |
} | |
public Object getValue(String name) { | |
return this.getAttribute(name, DEFAULT_SCOPE); | |
} | |
/** | |
* DEPRECATED: Implemented for backwards compatibility with HttpSession. | |
* @deprecated | |
*/ | |
public String[] getValueNames() { | |
return httpSession.getValueNames(); | |
} | |
public void putValue(String name, Object value) { | |
this.setAttribute(name, value, DEFAULT_SCOPE); | |
} | |
public void removeValue(String name) { | |
this.removeAttribute(name, DEFAULT_SCOPE); | |
} | |
} |