All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.directwebremoting.fluent.FluentConfigurator Maven / Gradle / Ivy

Go to download

DWR is easy Ajax for Java. It makes it simple to call Java code directly from Javascript. It gets rid of almost all the boiler plate code between the web browser and your Java code.

There is a newer version: 3.0.2-RELEASE
Show newest version
package org.directwebremoting.fluent;

import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.logging.LogFactory;
import org.apache.commons.logging.Log;
import org.directwebremoting.AjaxFilter;
import org.directwebremoting.Container;
import org.directwebremoting.extend.AccessControl;
import org.directwebremoting.extend.AjaxFilterManager;
import org.directwebremoting.extend.Configurator;
import org.directwebremoting.extend.Converter;
import org.directwebremoting.extend.ConverterManager;
import org.directwebremoting.extend.Creator;
import org.directwebremoting.extend.CreatorManager;
import org.directwebremoting.impl.SignatureParser;
import org.directwebremoting.util.LocalUtil;

/**
 * A {@link Configurator} that used the FluentInterface style as
 * described by
 * Martin Fowler.
 *
 * 

To wire up the configuration programmatically rather than having to use * dwr.xml. In order to use this style, you'll need to:

* *
    *
  • Create a concrete implementation of {@link FluentConfigurator} which * implements the {@link #configure()} method.
  • *
  • Add an init param 'customConfigurator' to the DWR servlet in * web.xml to point at your new class.
  • *
* *

The implementation of {@link #configure()} will look something like * this:

* *
 * public void configure() {
 *    withConverterType("dog", "com.yourcompany.beans.Dog");
 *    withCreatorType("ejb", "com.yourcompany.dwr.creator.EJBCreator");
 *    withCreator("new", "ApartmentDAO")
 *        .addParam("scope", "session")
 *        .addParam("class", "com.yourcompany.dao.ApartmentDAO")
 *        .exclude("saveApartment")
 *        .withAuth("method", "role");
 *    withCreator("struts", "DogDAO")
 *        .addParam("clas", "com.yourcompany.dao.DogDAO")
 *        .include("getDog")
 *        .include("getColor");
 *    withConverter("dog", "*.Dog")
 *        .addParam("name", "value");
 *    withSignature()
 *        .addLine("import java.util.List;")
 *        .addLine("import com.example.Check;")
 *        .addLine("Check.setLotteryResults(List nos);");
 * }
 * 
* @author Aaron Johnson [ajohnson at cephas dot net / http://cephas.net/blog] * @author Joe Walker [joe at getahead dot ltd dot uk] */ public abstract class FluentConfigurator implements Configurator { /** * This method is used to configure DWR using the fluent style. */ public abstract void configure(); /** * Add a new {@link Converter} definition. * @param id The id referred to by the {@link #withConverter(String, String)} * @param converterClassName The implementation of {@link Converter} to instantiate. * @return this to continue the fluency */ public FluentConfigurator withConverterType(String id, String converterClassName) { setState(STATE_INIT_CONVERT); converterManager.addConverterType(id, converterClassName); return this; } /** * Use a {@link Converter} to instantiate a class * @param newConverter A predefined {@link Converter} or one defined by * {@link #withConverterType(String, String)}. * @param newMatch The javascript name of this component * @return this to continue the fluency */ public FluentConfigurator withConverter(String newConverter, String newMatch) { setState(STATE_ALLOW_CONVERT); this.converter = newConverter; this.match = newMatch; return this; } /** * Add a new {@link Creator} definition. * @param id The id referred to by the {@link #withCreator(String, String)} * @param creatorClassName The implementation of {@link Creator} to instantiate. * @return this to continue the fluency */ public FluentConfigurator withCreatorType(String id, String creatorClassName) { setState(STATE_INIT_CREATE); creatorManager.addCreatorType(id, creatorClassName); return this; } /** * Use a {@link Creator} to instantiate a class * @param newTypeName A predefined {@link Creator} or one defined by * {@link #withCreatorType(String, String)}. * @param newScriptName The javascript name of this component * @return this to continue the fluency */ public FluentConfigurator withCreator(String newTypeName, String newScriptName) { setState(STATE_ALLOW_CREATE); this.typeName = newTypeName; this.scriptName = newScriptName; return this; } /** * @param newFilterClassName filter class name * @return this to continue the fluency */ public FluentConfigurator withFilter(String newFilterClassName) { setState(STATE_ALLOW_FILTER); this.filterClassName = newFilterClassName; return this; } /** * Add a parameter to whatever is being configured. * @param name The name of the parameter * @param value The value of the parameter * @return this to continue the fluency */ public FluentConfigurator addParam(String name, String value) { if (params == null) { params = new HashMap(); } params.put(name, value); return this; } /** * Add a filter to whatever is being configured. * @param newFilterClassName The class to add as a filter * @return this to continue the fluency */ public FluentConfigurator addFilter(String newFilterClassName) { if (filters == null) { filters = new ArrayList(); } filters.add(newFilterClassName); return this; } /** * Add an include rule to a {@link Creator}. * This should be used during a {@link #withCreator(String, String)} call. * @param methodName The method name to be allowed * @return this to continue the fluency */ public FluentConfigurator include(String methodName) { accessControl.addIncludeRule(scriptName, methodName); return this; } /** * Add an exclude rule to a {@link Creator} * This should be used during a {@link #withCreator(String, String)} call. * @param methodName The method name to be disallowed * @return this to continue the fluency */ public FluentConfigurator exclude(String methodName) { accessControl.addExcludeRule(scriptName, methodName); return this; } /** * Add an authorization rule to a {@link Creator} * This should be used during a {@link #withCreator(String, String)} call. * @param methodName The method name to have a required role * @param role The required role for the given method * @return this to continue the fluency */ public FluentConfigurator withAuth(String methodName, String role) { accessControl.addRoleRestriction(scriptName, methodName, role); return this; } /** * Add lines to a signature. * @return this to continue the fluency */ public FluentConfigurator withSignature() { setState(STATE_SIGNATURE); return this; } /** * Add lines to a signature. * @param line The line of text to add to the signature configuration * @return this to continue the fluency */ public FluentConfigurator addLine(String line) { if (null == line) { return this; } if (null == signature) { signature = new StringBuffer(); } signature.append(line); signature.append(System.getProperty("line.separator")); return this; } /** * Because some parts of the configuration require multiple steps, the instance * needs to maintain a state across invocations. Whenever the state is changed * by calling this method, the instance will 'flush' anything in the queue * applicable to that state EVEN IF the state itself doesn't change. Thus, it's * important that the child methods don't call setState() when being invoked. * @param state The new state. See the STATE_* constants. */ private void setState(int state) { flush(); this.state = state; } /** * Takes and configuration that is in progress and calls methods on the * various objects to enable that configuration. */ private void flush() { switch (state) { case STATE_INIT_CONVERT: // do nothing; break; case STATE_INIT_CREATE: // do nothing; break; case STATE_ALLOW_CONVERT: try { if (params == null) { converterManager.addConverter(match, converter, EMPTY_MAP); } else { converterManager.addConverter(match, converter, params); } } catch (Exception e) { log.warn("Failed to add converter of type='" + converter + "', match=" + match + ": ", e); } params = null; match = null; converter = null; break; case STATE_ALLOW_CREATE: try { if (params == null) { creatorManager.addCreator(scriptName, typeName, EMPTY_MAP); } else { creatorManager.addCreator(scriptName, typeName, params); } if (filters != null) { for (String className : filters) { AjaxFilter filter = LocalUtil.classNewInstance(scriptName, className, AjaxFilter.class); if (filter != null) { LocalUtil.setParams(filter, Collections.emptyMap(), Collections.emptyList()); ajaxFilterManager.addAjaxFilter(filter, scriptName); } } } } catch (Exception e) { log.warn("Failed to add creator of type='" + typeName + "', scriptName=" + scriptName + ": ", e); } params = null; scriptName = null; typeName = null; filters = null; break; case STATE_ALLOW_FILTER: try { Class impl = LocalUtil.classForName(filterClassName); AjaxFilter object = (AjaxFilter) impl.newInstance(); if (params != null) { LocalUtil.setParams(object, params, Collections.emptyList()); } ajaxFilterManager.addAjaxFilter(object); } catch (ClassCastException ex) { log.error(filterClassName + " does not implement " + AjaxFilter.class.getName(), ex); } catch (NoClassDefFoundError ex) { log.info("Missing class for filter (class='" + filterClassName + "'). Cause: " + ex.getMessage()); } catch (Exception ex) { log.error("Failed to add filter: class=" + filterClassName, ex); } params = null; filterClassName = null; break; case STATE_SIGNATURE: if (signature != null && signature.length() > 0) { SignatureParser sigp = new SignatureParser(converterManager, creatorManager); sigp.parse(signature.toString()); } break; default: break; } } /* (non-Javadoc) * @see org.directwebremoting.Configurator#configure(org.directwebremoting.Container) */ public void configure(Container container) { converterManager = container.getBean(ConverterManager.class); ajaxFilterManager = container.getBean(AjaxFilterManager.class); accessControl = container.getBean(AccessControl.class); creatorManager = container.getBean(CreatorManager.class); configure(); setState(STATE_COMPLETE); } /** * Used for */ private String typeName = null; /** * Used for */ private String scriptName = null; /** * Used for */ private String filterClassName = null; /** * Used for */ private String converter = null; /** * Used for */ private String match = null; /** * holds name / value pairs used in */ private Map params = null; /** * holds classNames of filters used in */ private List filters = null; /** * holds signature lines */ private StringBuffer signature = null; /** * What section of a configuration are we in? */ private int state = -1; /** * JDK5: we can convert this to Collections.emptyMap(); */ private static final Map EMPTY_MAP = Collections.unmodifiableMap(new HashMap()); /** * What AjaxFilters apply to which Ajax calls? */ private AjaxFilterManager ajaxFilterManager = null; /** * The ConverterManager that we are configuring */ private ConverterManager converterManager = null; /** * The AccessControl that we are configuring */ private AccessControl accessControl = null; /** * The CreatorManager that we are configuring */ private CreatorManager creatorManager = null; /** * {@link #state} to say we are working in {@link #withCreatorType(String, String)} */ private static final int STATE_INIT_CREATE = 0; /** * {@link #state} to say we are working in {@link #withConverterType(String, String)} */ private static final int STATE_INIT_CONVERT = 1; /** * {@link #state} to say we are working in {@link #withCreator(String, String)} */ private static final int STATE_ALLOW_CREATE = 2; /** * {@link #state} to say we are working in {@link #withFilter(String)} */ private static final int STATE_ALLOW_FILTER = 3; /** * {@link #state} to say we are working in {@link #withConverter(String, String)} */ private static final int STATE_ALLOW_CONVERT = 4; /** * {@link #state} to say we are working in {@link #withSignature()} */ private static final int STATE_SIGNATURE = 5; /** * {@link #state} to say {@link #configure()} has completed */ private static final int STATE_COMPLETE = 6; /** * The log stream */ private static final Log log = LogFactory.getLog(FluentConfigurator.class); }




© 2015 - 2025 Weber Informatics LLC | Privacy Policy