public void init(PortletConfig config)
throws BridgeException
{
//TODO: Should we throw an exception if the bridge is already initialized?
if (mInitialized)
throw new BridgeException("Bridge already initialized.");
mPortletConfig = config;
PortletContext portletContext = mPortletConfig.getPortletContext();
// acquire any config information in faces-config.xml
FacesConfigurationProcessor processor = new FacesConfigurationProcessor(portletContext);
mPublicParameterMappings = processor.getPublicParameterMappings();
// get bridgeEventHandler, processPublicRenderParameterHandler, preserveActionParams, excludedAttributes configuration settings.
mEventHandler = (BridgeEventHandler) portletContext.getAttribute(Bridge.BRIDGE_PACKAGE_PREFIX + mPortletConfig.getPortletName() +
"." + Bridge.BRIDGE_EVENT_HANDLER);
mProcessPRPHandler = (BridgePublicRenderParameterHandler) portletContext.getAttribute(Bridge.BRIDGE_PACKAGE_PREFIX + mPortletConfig.getPortletName() +
"." + Bridge.BRIDGE_PUBLIC_RENDER_PARAMETER_HANDLER);
mPreserveActionParams =
(Boolean) portletContext.getAttribute(Bridge.BRIDGE_PACKAGE_PREFIX + mPortletConfig.getPortletName() +
"." + Bridge.PRESERVE_ACTION_PARAMS);
mBridgeWriteBehindResponse = (Class<? extends BridgeWriteBehindResponse>) portletContext.getAttribute(Bridge.BRIDGE_PACKAGE_PREFIX + mPortletConfig.getPortletName() +
"." + Bridge.WRITE_BEHIND_RESPONSE);
mExcludedRequestAttributes = (List<String>) portletContext.getAttribute(Bridge.BRIDGE_PACKAGE_PREFIX + mPortletConfig.getPortletName() +
"." + Bridge.EXCLUDED_REQUEST_ATTRIBUTES);
if (mExcludedRequestAttributes != null)
{
// copy the list as we may be adding to it and don't want to worry that this might be immutable
mExcludedRequestAttributes = new ArrayList(mExcludedRequestAttributes);
}
else
{
// Otherwise create an empty list
mExcludedRequestAttributes = new ArrayList(5);
}
// Read excludedAttributes that may be defined in any face-config.xml
readExcludedAttributesFromFacesConfig(portletContext, mExcludedRequestAttributes);
// Set up the synchronziation object for the RequestScopeMap as we don't
// want to sync on the PortletContext because its too broad. Note:
// needed
// because we not only need to sync the Map but also creating the Map
// and
// putting it in the PortletContext. Hence the sync object allows us
// to limit syncronizing the PortletContext to once per portlet (init
// time);
// TODO: What about synching on a static object or using a class lock?
// Perhaps even the LRUMap itself if said map is a singleton?
synchronized (portletContext)
{
Object lock = portletContext.getAttribute(REQUEST_SCOPE_LOCK);
if (lock == null)
{
portletContext.setAttribute(REQUEST_SCOPE_LOCK, new Object());
}
}
// Wrapped desired Application with our own to override createComponent and
// insert our NamingContainerUIViewRoot component. This was done through
// configuration via the META-INF/service/javax.faces.application.ApplicationFactory
// Add self as ELContextListener to the Faces App so we can add the
// portletConfig to any newly created contexts.
((ApplicationFactory)FactoryFinder.getFactory(FactoryFinder.APPLICATION_FACTORY))
.getApplication().addELContextListener(this);
// Process and cache the FacesServlet mappings for use by
// ExternalContext
WebConfigurationProcessor webConfig = new WebConfigurationProcessor(portletContext);
mFacesMappings = webConfig.getFacesMappings();
if (mFacesMappings == null || mFacesMappings.size() == 0)
{
throw new BridgeException("BridgeImpl.init(): unable to determine Faces servlet web.xml mapping.");
}
// Set defaults for each mode's last active view session attribute
mDefaultViewIdMap = (Map<String,String>) portletContext.getAttribute(
Bridge.BRIDGE_PACKAGE_PREFIX + mPortletConfig.getPortletName()