blob: 2d1c57c184bdd1855a53970335979718ee7d6cd5 [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you 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.felix.webconsole.internal;
import java.io.IOException;
import java.util.*;
import javax.servlet.*;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.felix.webconsole.AbstractWebConsolePlugin;
import org.apache.felix.webconsole.WebConsoleConstants;
import org.osgi.framework.ServiceReference;
/**
* The <code>WebConsolePluginAdapter</code> is an adapter to the
* {@link AbstractWebConsolePlugin} for regular servlets registered with the
* {@link org.apache.felix.webconsole.WebConsoleConstants#PLUGIN_TITLE}
* service attribute.
*/
public class WebConsolePluginAdapter extends AbstractWebConsolePlugin
{
/** serial UID */
private static final long serialVersionUID = 1L;
// the plugin label (aka address)
private final String label;
// the actual plugin to forward rendering requests to
private final Servlet plugin;
// the CSS references (null if none)
private final String[] cssReferences;
/**
* Creates a new wrapper for a Web Console Plugin
*
* @param label the label
* @param plugin the plugin itself
* @param serviceReference reference to the plugin
*/
public WebConsolePluginAdapter( String label, Servlet plugin, ServiceReference serviceReference )
{
this.label = label;
this.plugin = plugin;
this.cssReferences = toStringArray( serviceReference.getProperty( WebConsoleConstants.PLUGIN_CSS_REFERENCES ) );
// activate this abstract plugin (mainly to set the bundle context)
activate( serviceReference.getBundle().getBundleContext() );
}
//---------- AbstractWebConsolePlugin API
/**
* Returns the label of this plugin page as defined in the constructor.
*
* @see org.apache.felix.webconsole.AbstractWebConsolePlugin#getLabel()
*/
public String getLabel()
{
return label;
}
/**
* Returns the title of this plugin page as defined by the
* {@link WebConsoleConstants#PLUGIN_TITLE} service registration attribute
* which is exposed as the servlet name in the servlet configuration.
*
* @see org.apache.felix.webconsole.AbstractWebConsolePlugin#getTitle()
*/
public String getTitle()
{
// return the servlet name from the configuration but don't call
// the base class implementation, which calls getTitle()
return getServletConfig().getServletName();
}
/**
* Returns the CSS references from the
* {@link WebConsoleConstants#PLUGIN_CSS_REFERENCES felix.webconsole.css}
* service registration property of the plugin.
*
* @see org.apache.felix.webconsole.AbstractWebConsolePlugin#getCssReferences()
*/
protected String[] getCssReferences()
{
return cssReferences;
}
/**
* Call the plugin servlet's service method to render the content of this
* page.
*
* @see org.apache.felix.webconsole.AbstractWebConsolePlugin#renderContent(javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse)
*/
protected void renderContent( HttpServletRequest req, HttpServletResponse res ) throws ServletException,
IOException
{
plugin.service( req, res );
}
/**
* Returns the registered plugin class to be able to call the
* <code>getResource()</code> method on that object for this plugin to
* provide additional resources.
*
* @see org.apache.felix.webconsole.AbstractWebConsolePlugin#getResourceProvider()
*/
protected Object getResourceProvider()
{
return plugin;
}
//---------- Servlet API overwrite
/**
* Initializes this servlet as well as the plugin servlet.
*
* @see javax.servlet.GenericServlet#init(javax.servlet.ServletConfig)
*/
public void init( ServletConfig config ) throws ServletException
{
// no need to activate the plugin, this has already been done
// when the instance was setup
try
{
// base classe initialization
super.init( config );
// plugin initialization
plugin.init( config );
}
catch ( ServletException se )
{
// if init fails, the plugin will not be destroyed and thus
// the plugin not deactivated. Do it here
deactivate();
// rethrow the exception
throw se;
}
}
/**
* Detects whether this request is intended to have the headers and
* footers of this plugin be rendered or not. The decision is taken based
* on whether and what extension the request URI has: If the request URI
* has no extension or the the extension is <code>.html</code>, the request
* is assumed to be rendered with header and footer. Otherwise the
* headers and footers are omitted and the
* {@link #renderContent(HttpServletRequest, HttpServletResponse)}
* method is called without any decorations and without setting any
* response headers.
*
* @see org.apache.felix.webconsole.AbstractWebConsolePlugin#isHtmlRequest(javax.servlet.http.HttpServletRequest)
*/
protected boolean isHtmlRequest( final HttpServletRequest request )
{
final String requestUri = request.getRequestURI();
if ( requestUri.endsWith( ".html" ) ) {
return true;
}
// check if there is an extension
final int lastSlash = requestUri.lastIndexOf('/');
final int lastDot = requestUri.indexOf('.', lastSlash + 1);
return lastDot < 0;
}
/**
* Directly refer to the plugin's service method unless the request method
* is <code>GET</code> in which case we defer the call into the service method
* until the abstract web console plugin calls the
* {@link #renderContent(HttpServletRequest, HttpServletResponse)}
* method.
*
* @see javax.servlet.http.HttpServlet#service(javax.servlet.ServletRequest, javax.servlet.ServletResponse)
*/
public void service( ServletRequest req, ServletResponse resp ) throws ServletException, IOException
{
if ( ( req instanceof HttpServletRequest ) && ( ( HttpServletRequest ) req ).getMethod().equals( "GET" ) )
{
// handle the GET request here and call into plugin on renderContent
super.service( req, resp );
}
else
{
// not a GET request, have the plugin handle it directly
plugin.service( req, resp );
}
}
/**
* Destroys this servlet as well as the plugin servlet.
*
* @see javax.servlet.GenericServlet#destroy()
*/
public void destroy()
{
try
{
plugin.destroy();
super.destroy();
}
finally
{
deactivate();
}
}
//---------- internal
private String[] toStringArray( final Object value )
{
if ( value instanceof String )
{
return new String[]
{ ( String ) value };
}
else if ( value != null )
{
final Collection cssListColl;
if ( value.getClass().isArray() )
{
cssListColl = Arrays.asList( ( Object[] ) value );
}
else if ( value instanceof Collection )
{
cssListColl = ( Collection ) value;
}
else
{
cssListColl = null;
}
if ( cssListColl != null && !cssListColl.isEmpty() )
{
String[] entries = new String[cssListColl.size()];
int i = 0;
for ( Iterator cli = cssListColl.iterator(); cli.hasNext(); i++ )
{
entries[i] = String.valueOf( cli.next() );
}
return entries;
}
}
return null;
}
}