You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@commons.apache.org by si...@apache.org on 2011/02/18 23:26:51 UTC

svn commit: r1072175 [2/2] - in /commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins: ./ strategies/

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/PluginRules.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/PluginRules.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/PluginRules.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/PluginRules.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,378 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins;
+
+import java.util.List;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.Rule;
+import org.apache.commons.digester3.rules.BaseRules;
+import org.apache.commons.digester3.spi.Rules;
+import org.apache.commons.logging.Log;
+
+/**
+ * A custom digester Rules manager which must be used as the Rules object
+ * when using the plugins module functionality.
+ * <p>
+ * During parsing, a linked list of PluginCreateRule instances develop, and
+ * this list also acts like a stack. The original instance that was set before 
+ * the Digester started parsing is always at the tail of the list, and the
+ * Digester always holds a reference to the instance at the head of the list
+ * in the rules member. Initially, this list/stack holds just one instance,
+ * ie head and tail are the same object.
+ * <p>
+ * When the start of an xml element causes a PluginCreateRule to fire, a new 
+ * PluginRules instance is created and inserted at the head of the list (ie
+ * pushed onto the stack of Rules objects). Digester.getRules() therefore
+ * returns this new Rules object, and any custom rules associated with that 
+ * plugin are added to that instance. 
+ * <p>
+ * When the end of the xml element is encountered (and therefore the 
+ * PluginCreateRule end method fires), the stack of Rules objects is popped,
+ * so that Digester.getRules returns the previous Rules object.
+ */
+public class PluginRules implements Rules {
+
+    /**
+     * The Digester instance with which this Rules instance is associated.
+     */
+    protected Digester digester = null;
+
+    /** 
+     * The (optional) object which generates new rules instances.
+     */
+    private RulesFactory rulesFactory;
+
+    /** 
+     * The rules implementation that we are "enhancing" with plugins
+     * functionality, as per the Decorator pattern.
+     */
+    private Rules decoratedRules;
+
+    /** Object which contains information about all known plugins. */
+    private PluginManager pluginManager;
+
+    /**
+     * The path below which this rules object has responsibility.
+     * For paths shorter than or equal the mountpoint, the parent's 
+     * match is called.
+     */
+    private String mountPoint = null;
+
+    /**
+     * The Rules object that holds rules applying "above" the mountpoint,
+     * ie the next Rules object down in the stack.
+     */
+    private PluginRules parent = null;
+
+    /**
+     * A reference to the object that holds all data which should only
+     * exist once per digester instance.
+     */
+    private PluginContext pluginContext = null;
+
+    /**
+     * Constructor for top-level Rules objects. Exactly one of these must
+     * be created and installed into the Digester instance as the Rules
+     * object before parsing starts.
+     */
+    public PluginRules() {
+        this(new BaseRules());
+    }
+
+    /**
+     * Constructor for top-level Rules object which handles rule-matching
+     * using the specified implementation.
+     */
+    public PluginRules(Rules decoratedRules) {
+        this.decoratedRules = decoratedRules;
+        this.digester = decoratedRules.getDigester();
+
+        pluginContext = new PluginContext();
+        pluginManager = new PluginManager(pluginContext);
+    }
+
+    /**
+     * Constructs a Rules instance which has a parent Rules object 
+     * (which is different from having a delegate rules object). 
+     * <p>
+     * One of these is created each time a PluginCreateRule's begin method 
+     * fires, in order to manage the custom rules associated with whatever 
+     * concrete plugin class the user has specified.
+     *
+     * @param digester is the object this rules will be associated with.
+     * @param mountPoint is the digester match path for the element 
+     * matching a PluginCreateRule which caused this "nested parsing scope"
+     * to begin. This is expected to be equal to digester.getMatch().
+     * @param parent must be non-null.
+     * @param pluginClass is the plugin class whose custom rules will be
+     * loaded into this new PluginRules object.
+     */
+     PluginRules(Digester digester, String mountPoint, PluginRules parent, Class<?> pluginClass) throws PluginException {
+        // no need to set digester or decoratedRules.digester,
+        // because when Digester.setRules is called, the setDigester
+        // method on this object will be called.
+
+        this.digester = digester;
+        this.mountPoint = mountPoint;
+        this.parent = parent;
+        this.rulesFactory = parent.rulesFactory;
+
+        if (rulesFactory == null) {
+            decoratedRules = new BaseRules();
+        } else {
+            decoratedRules = rulesFactory.newRules(digester, pluginClass);
+        }
+
+        pluginContext = parent.pluginContext;
+        pluginManager = new PluginManager(parent.pluginManager);
+    }
+
+    /**
+     * Return the parent Rules object.
+     */
+    public Rules getParent() {
+        return parent;
+    }
+
+    /**
+     * Return the Digester instance with which this instance is associated.
+     */
+    public Digester getDigester() {
+        return this.decoratedRules.getDigester();
+    }
+
+    /**
+     * Set the Digester instance with which this Rules instance is associated.
+     *
+     * @param digester The newly associated Digester instance
+     */
+    public void setDigester(Digester digester) {
+        this.digester = digester;
+        decoratedRules.setDigester(digester);
+    }
+
+    /**
+     * Return the object which "knows" about all declared plugins.
+     * 
+     * @return The pluginManager value
+     */
+    public PluginManager getPluginManager() {
+        return pluginManager;
+    }
+
+    /**
+     * See {@link PluginContext#getRuleFinders}.
+     */
+    public List<RuleFinder> getRuleFinders() {
+        return pluginContext.getRuleFinders();
+    }
+
+    /**
+     * See {@link PluginContext#setRuleFinders}.
+     */
+    public void setRuleFinders(List<RuleFinder> ruleFinders) {
+        pluginContext.setRuleFinders(ruleFinders);
+    }
+
+    /**
+     * Return the rules factory object (or null if one has not been specified).
+     */
+    public RulesFactory getRulesFactory() {
+        return rulesFactory;
+    }
+
+    /**
+     * Set the object which is used to generate the new Rules instances created
+     * to hold and process the rules associated with each plugged-in class.
+     */
+    public void setRulesFactory(RulesFactory factory) {
+        rulesFactory = factory;
+    }
+
+    /**
+     * This package-scope method is used by the PluginCreateRule class to
+     * get direct access to the rules that were dynamically added by the
+     * plugin. No other class should need access to this object.
+     */
+    Rules getDecoratedRules() {
+        return decoratedRules;
+    }
+
+    /**
+     * Return the list of rules registered with this object, in the order
+     * they were registered with this object.
+     * <p>
+     * Note that Rule objects stored in parent Rules objects are not
+     * returned by this method.
+     * 
+     * @return list of all Rule objects known to this Rules instance.
+     */
+    public List<Rule> rules() {
+        return decoratedRules.rules();
+    }
+
+    /**
+     * Register a new Rule instance matching the specified pattern.
+     * 
+     * @param pattern Nesting pattern to be matched for this Rule.
+     * This parameter treats equally patterns that begin with and without
+     * a leading slash ('/').
+     * @param rule Rule instance to be registered
+     */
+    public void add(String pattern, Rule rule) {
+        Log log = LogUtils.getLogger(digester);
+        boolean debug = log.isDebugEnabled();
+
+        if (debug) {
+            log.debug("add entry" + ": mapping pattern [" + pattern + "]" + 
+                  " to rule of type [" + rule.getClass().getName() + "]");
+        }
+
+        // allow patterns with a leading slash character
+        if (pattern.startsWith("/")) {
+            pattern = pattern.substring(1);
+        }
+
+        if (mountPoint != null
+                && !pattern.equals(mountPoint)
+                && !pattern.startsWith(mountPoint + "/")) {
+            // This can only occur if a plugin attempts to add a
+            // rule with a pattern that doesn't start with the
+            // prefix passed to the addRules method. Plugins mustn't
+            // add rules outside the scope of the tag they were specified
+            // on, so refuse this.
+
+            // alas, can't throw exception
+            log.warn(
+                "An attempt was made to add a rule with a pattern that"
+                + "is not at or below the mountpoint of the current"
+                + " PluginRules object."
+                + " Rule pattern: " + pattern
+                + ", mountpoint: " + mountPoint
+                + ", rule type: " + rule.getClass().getName());
+            return;
+        }
+
+        decoratedRules.add(pattern, rule);
+
+        if (rule instanceof InitializableRule) {
+            try {
+                ((InitializableRule) rule).postRegisterInit(pattern);
+            } catch (PluginConfigurationException e) {
+                // Currently, Digester doesn't handle exceptions well
+                // from the add method. The workaround is for the
+                // initialisable rule to remember that its initialisation
+                // failed, and to throw the exception when begin is
+                // called for the first time.
+                if (debug) {
+                    log.debug("Rule initialisation failed", e);
+                }
+                // throw e; -- alas, can't do this
+                return;
+            }
+        }
+
+        if (debug) {
+            log.debug("add exit" + ": mapped pattern [" + pattern + "]" + 
+                  " to rule of type [" + rule.getClass().getName() + "]");
+        }
+    }
+
+    /**
+     * Clear all rules.
+     */
+    public void clear() {
+        decoratedRules.clear();
+    }
+
+    /**
+     * Return a List of all registered Rule instances that match the specified
+     * nodepath, or a zero-length List if there are no matches.  If more
+     * than one Rule instance matches, they <strong>must</strong> be returned
+     * in the order originally registered through the <code>add()</code>
+     * method.
+     * <p>
+     * @param namespaceURI Namespace URI for which to select matching rules,
+     *  or <code>null</code> to match regardless of namespace URI
+     * @param path the path to the xml nodes to be matched.
+     */
+    public List<Rule> match(String namespaceURI, String path) {
+        Log log = LogUtils.getLogger(digester);
+        boolean debug = log.isDebugEnabled();
+        
+        if (debug) {
+            log.debug(
+                "Matching path [" + path +
+                "] on rules object " + this.toString());
+        }
+
+        List<Rule> matches;
+        if ((mountPoint != null) && 
+            (path.length() <= mountPoint.length())) {
+            if (debug) {
+                log.debug(
+                    "Path [" + path + "] delegated to parent.");
+            }
+
+            matches = parent.match(namespaceURI, path);
+
+            // Note that in the case where path equals mountPoint, 
+            // we deliberately return only the rules from the parent,
+            // even though this object may hold some rules matching
+            // this same path. See PluginCreateRule's begin, body and end
+            // methods for the reason.
+        } else {
+                log.debug("delegating to decorated rules.");
+            matches = decoratedRules.match(namespaceURI, path); 
+        }
+
+        return matches;
+    }
+
+    /** See {@link PluginContext#setPluginClassAttribute}. */
+    public void setPluginClassAttribute(String namespaceUri, String attrName) {
+        pluginContext.setPluginClassAttribute(namespaceUri, attrName);
+    }
+
+    /** See {@link PluginContext#setPluginIdAttribute}. */
+    public void setPluginIdAttribute(String namespaceUri, String attrName) {
+        pluginContext.setPluginIdAttribute(namespaceUri, attrName);
+    }
+
+    /** See {@link PluginContext#getPluginClassAttrNs}. */
+    public String getPluginClassAttrNs() {
+        return pluginContext.getPluginClassAttrNs();
+    }
+
+    /** See {@link PluginContext#getPluginClassAttr}. */
+    public String getPluginClassAttr() {
+        return pluginContext.getPluginClassAttr();
+    }
+
+    /** See {@link PluginContext#getPluginIdAttrNs}. */
+    public String getPluginIdAttrNs() {
+        return pluginContext.getPluginIdAttrNs();
+    }
+
+    /** See {@link PluginContext#getPluginIdAttr}. */
+    public String getPluginIdAttr() {
+        return pluginContext.getPluginIdAttr();
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/PluginRules.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/PluginRules.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/PluginRules.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleFinder.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleFinder.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleFinder.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleFinder.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,70 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins;
+
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+
+/**
+ * Each concrete implementation of RuleFinder is an algorithm for
+ * locating a source of digester rules for a plugin. The algorithm may 
+ * use info explicitly provided by the user as part of the plugin 
+ * declaration, or not (in which case the concrete RuleFinder subclass
+ * typically has Dflt as part of its name).
+ * <p>
+ * Instances of this class can also be regarded as a Factory for RuleLoaders,
+ * except that an instance of a RuleLoader is only created if the particular
+ * finder algorithm can locate a suitable source of rules given the plugin
+ * class and associated properties.
+ * <p>
+ * This is an abstract class rather than an interface in order to make
+ * it possible to enhance this class in future without breaking binary
+ * compatibility; it is possible to add methods to an abstract class, but
+ * not to an interface.
+ */
+public abstract class RuleFinder {
+
+    /**
+     * Apply the finder algorithm to attempt to locate a source of
+     * digester rules for the specified plugin class.
+     * <p>
+     * This method is invoked when a plugin is declared by the user, either
+     * via an explicit use of PluginDeclarationRule, or implicitly via an
+     * "inline declaration" where the declaration and use are simultaneous.
+     * <p>
+     * If dynamic rules for the specified plugin class are located, then
+     * the RuleFinder will return a RuleLoader object encapsulating those
+     * rules, and this object will be invoked each time the user actually
+     * requests an instance of the declared plugin class, to load the
+     * custom rules associated with that plugin instance.
+     * <p>
+     * If no dynamic rules can be found, null is returned. This is not an
+     * error; merely an indication that this particular algorithm found
+     * no matches.
+     * <p>
+     * The properties object holds any xml attributes the user may have
+     * specified on the plugin declaration in order to indicate how to locate
+     * the plugin rules.
+     * <p>
+     * @throws PluginConfigurationException if the algorithm finds a source
+     * of rules, but there is something invalid about that source.
+     */
+     public abstract RuleLoader findLoader(Digester d, Class<?> pluginClass, Properties p) throws PluginException;
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleFinder.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleFinder.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleFinder.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleLoader.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleLoader.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleLoader.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleLoader.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,47 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins;
+
+import org.apache.commons.digester3.Digester;
+
+/**
+ * Interface for classes which can dynamically load custom
+ * plugin rules associated with a user's plugin class.
+ * <p>
+ * Each plugin declaration has an associated RuleLoader instance, and that
+ * instance's addRules method is invoked each time the input xml specifies
+ * that an instance of that plugged-in class is to be created.
+ * <p>
+ * This is an abstract class rather than an interface in order to make
+ * it possible to enhance this class in future without breaking binary
+ * compatibility; it is possible to add methods to an abstract class, but
+ * not to an interface.
+ */
+public abstract class RuleLoader {
+
+    /**
+     * Configures the digester with custom rules for some plugged-in
+     * class.
+     * <p>
+     * This method is invoked when the start of an xml tag is encountered
+     * which maps to a PluginCreateRule. Any rules added here are removed
+     * from the digester when the end of that xml tag is encountered.
+     */
+    public abstract void addRules(Digester d, String path) throws PluginException;
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleLoader.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleLoader.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RuleLoader.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RulesFactory.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RulesFactory.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RulesFactory.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RulesFactory.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,50 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.spi.Rules;
+
+/**
+ * Whenever the scope of a plugin tag is entered, the PluginRules class
+ * creates a new Rules instance and configures it with the appropriate
+ * parsing rules for the plugged-in class.
+ * <p>
+ * Users of the plugins module can specify a subclass of this one to
+ * control the creation of that Rules object. In particular, it can
+ * set up default rules within the returned instance which are applicable
+ * to all plugged-in classes.
+ */
+public abstract class RulesFactory {
+
+    /**
+     * Return an instance of some Rules implementation that the plugged-in
+     * class shall use to match its private parsing rules.
+     * <p>
+     * @param d is the digester that the returned rules object will be 
+     * associated with.
+     *
+     * @param pluginClass is the class that is to be configured using rules
+     * added to the returned object.
+     * 
+     * @throws PluginException if the algorithm finds a source
+     * of rules, but there is something invalid about that source.
+     */
+     public abstract Rules newRules(Digester d, Class<?> pluginClass) throws PluginException;
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RulesFactory.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RulesFactory.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/RulesFactory.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/package-info.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/package-info.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/package-info.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/package-info.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,23 @@
+/* $Id$
+ *
+ * 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.
+ */
+
+/**
+ * The <code>plugins</code> package provides an easy mechanism whereby new
+ * digestion rules can be added dynamically during a digestion.
+ */
+package org.apache.commons.digester3.plugins;

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/package-info.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/package-info.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/package-info.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromClass.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromClass.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromClass.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromClass.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,130 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which expects the caller to specify a classname and
+ * methodname as plugin properties.
+ *
+ * @since 1.6
+ */
+
+public class FinderFromClass extends RuleFinder {
+
+    public static String DFLT_RULECLASS_ATTR = "ruleclass";
+
+    public static String DFLT_METHOD_ATTR = "method";
+
+    public static String DFLT_METHOD_NAME = "addRules";
+
+    private String ruleClassAttr;
+
+    private String methodAttr;
+
+    private String dfltMethodName;
+
+    /**
+     * See {@link #findLoader}.
+     */
+    public FinderFromClass() {
+        this(DFLT_RULECLASS_ATTR, DFLT_METHOD_ATTR, DFLT_METHOD_NAME);
+    }
+
+    /**
+     * Create a rule-finder which invokes a user-specified method on a
+     * user-specified class whenever dynamic rules for a plugin need to be
+     * loaded. See the findRules method for more info.
+     *
+     * @param ruleClassAttr must be non-null.
+     * @param methodAttr may be null.
+     * @param dfltMethodName may be null.
+     */
+    public FinderFromClass(String ruleClassAttr, String methodAttr, String dfltMethodName) {
+        this.ruleClassAttr = ruleClassAttr;
+        this.methodAttr = methodAttr;
+        this.dfltMethodName = dfltMethodName;
+    }
+
+    /**
+     * If there exists a property with the name matching constructor param
+     * ruleClassAttr, then load the specified class, locate the appropriate 
+     * rules-adding method on that class, and return an object encapsulating 
+     * that info.
+     * <p>
+     * If there is no matching property provided, then just return null.
+     * <p>
+     * The returned object (when non-null) will invoke the target method
+     * on the selected class whenever its addRules method is invoked. The
+     * target method is expected to have the following prototype:
+     * <code> public static void xxxxx(Digester d, String patternPrefix); </code>
+     * <p>
+     * The target method can be specified in several ways. If this object's
+     * constructor was passed a non-null methodAttr parameter, and the
+     * properties defines a value with that key, then that is taken as the
+     * target method name. If there is no matching property, or the constructor
+     * was passed null for methodAttr, then the dfltMethodName passed to the
+     * constructor is used as the name of the method on the target class. And
+     * if that was null, then DFLT_METHOD_NAME will be used.
+     * <p>
+     * When the user explicitly declares a plugin in the input xml, the
+     * xml attributes on the declaration tag are passed here as properties,
+     * so the user can select any class in the classpath (and any method on
+     * that class provided it has the correct prototype) as the source of
+     * dynamic rules for the plugged-in class.
+     */
+    public RuleLoader findLoader(Digester digester, Class<?> pluginClass, Properties p) throws PluginException {
+        String ruleClassName = p.getProperty(ruleClassAttr);
+        if (ruleClassName == null) {
+            // nope, user hasn't requested dynamic rules to be loaded
+            // from a specific class.
+            return null;
+        }
+
+        // ok, we are in business
+        String methodName = null;
+        if (methodAttr != null) { 
+            methodName = p.getProperty(methodAttr);
+        }
+        if (methodName == null) {
+            methodName = dfltMethodName;
+        }
+        if (methodName == null) {
+            methodName = DFLT_METHOD_NAME;
+        }
+
+        Class<?> ruleClass;
+        try {
+            // load the plugin class object
+            ruleClass = 
+                digester.getClassLoader().loadClass(ruleClassName);
+        } catch(ClassNotFoundException cnfe) {
+            throw new PluginException(
+                "Unable to load class " + ruleClassName, cnfe);
+        }
+
+        return new LoaderFromClass(ruleClass, methodName);
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromClass.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromClass.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromClass.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltClass.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltClass.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltClass.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltClass.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,91 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which looks for a method with a specific name
+ * on a class whose name is derived from the plugin class name.
+ */
+public class FinderFromDfltClass extends RuleFinder {
+
+    public static String DFLT_RULECLASS_SUFFIX = "RuleInfo";
+
+    public static String DFLT_METHOD_NAME = "addRules";
+
+    private String rulesClassSuffix;
+
+    private String methodName;
+
+    /** See {@link #findLoader}. */
+    public FinderFromDfltClass() {
+        this(DFLT_RULECLASS_SUFFIX, DFLT_METHOD_NAME);
+    }
+
+    /**
+     * Create a rule-finder which invokes a method on a class whenever 
+     * dynamic rules for a plugin need to be loaded. See the findRules 
+     * method for more info.
+     *
+     * @param rulesClassSuffix must be non-null.
+     * @param methodName may be null.
+     */
+     public FinderFromDfltClass(String rulesClassSuffix, String methodName) { 
+        this.rulesClassSuffix = rulesClassSuffix;
+        this.methodName = methodName;
+    }
+
+    /**
+     * If there exists a class whose name is the plugin class name + the
+     * suffix specified to the constructor, then load that class, locate 
+     * the appropriate rules-adding method on that class, and return an 
+     * object encapsulating that info.
+     * <p>
+     * If there is no such class, then just return null.
+     * <p>
+     * The returned object (when non-null) will invoke the target method
+     * on the selected class whenever its addRules method is invoked. The
+     * target method is expected to have the following prototype:
+     * <code> public static void xxxxx(Digester d, String patternPrefix); </code>
+     */
+    @Override
+    public RuleLoader findLoader(Digester digester, Class<?> pluginClass, Properties p) throws PluginException {
+        String rulesClassName = pluginClass.getName() + rulesClassSuffix;
+
+        Class<?> rulesClass = null;
+        try {
+            rulesClass = digester.getClassLoader().loadClass(rulesClassName);
+        } catch(ClassNotFoundException cnfe) {
+            // nope, no rule-info class in the classpath
+            return null;
+        }
+
+        if (methodName == null) {
+            methodName = DFLT_METHOD_NAME;
+        }
+
+        return new LoaderFromClass(rulesClass, methodName);
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltClass.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltClass.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltClass.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltMethod.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltMethod.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltMethod.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltMethod.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,77 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.lang.reflect.Method;
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which looks for a method with a specific name
+ * on the plugin class.
+ */
+public class FinderFromDfltMethod extends RuleFinder {
+
+    public static String DFLT_METHOD_NAME = "addRules";
+
+    private String methodName;
+
+    /** See {@link #findLoader}. */
+    public FinderFromDfltMethod() { 
+        this(DFLT_METHOD_NAME);
+    }
+
+    /**
+     * Create a rule-finder which invokes a specific method on the plugin
+     * class whenever dynamic rules for a plugin need to be loaded. See the 
+     * findRules method for more info.
+     *
+     * @param methodName must be non-null.
+     */
+    public FinderFromDfltMethod(String methodName) { 
+        this.methodName = methodName;
+    }
+
+    /**
+     * If there exists on the plugin class a method with name matching the 
+     * constructor's methodName value then locate the appropriate Method on 
+     * the plugin class and return an object encapsulating that info.
+     * <p>
+     * If there is no matching method then just return null.
+     * <p>
+     * The returned object (when non-null) will invoke the target method
+     * on the plugin class whenever its addRules method is invoked. The
+     * target method is expected to have the following prototype:
+     * <code> public static void xxxxx(Digester d, String patternPrefix); </code>
+     */
+    @Override
+    public RuleLoader findLoader(Digester d, Class<?> pluginClass, Properties p) throws PluginException {
+        Method rulesMethod = LoaderFromClass.locateMethod(pluginClass, methodName);
+        if (rulesMethod == null) {
+            return null;
+        }
+
+        return new LoaderFromClass(pluginClass, rulesMethod);
+    }
+
+}
+

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltMethod.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltMethod.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltMethod.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltResource.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltResource.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltResource.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltResource.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,82 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.io.InputStream;
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which looks for a resource file in the classpath
+ * whose name is derived from the plugin class name plus a specified suffix.
+ * <p>
+ * If the resource-file is found, then it is expected to define a set of
+ * Digester rules in xmlrules format.
+ */
+public class FinderFromDfltResource extends RuleFinder {
+
+    public static String DFLT_RESOURCE_SUFFIX = "RuleInfo.xml";
+
+    private String resourceSuffix;
+
+    /** See {@link #findLoader}. */
+    public FinderFromDfltResource() { 
+        this(DFLT_RESOURCE_SUFFIX);
+    }
+
+    /**
+     * Create a rule-finder which can load an xmlrules file, cache
+     * the rules away, and later add them as a plugin's custom rules
+     * when that plugin is referenced.
+     *
+     * @param resourceSuffix must be non-null.
+     */
+    public FinderFromDfltResource(String resourceSuffix) { 
+        this.resourceSuffix = resourceSuffix;
+    }
+
+    /**
+     * If there exists a resource file whose name is equal to the plugin
+     * class name + the suffix specified in the constructor, then
+     * load that file, run it through the xmlrules module and return an object 
+     * encapsulating those rules.
+     * <p>
+     * If there is no such resource file, then just return null.
+     * <p>
+     * The returned object (when non-null) will add the selected rules to
+     * the digester whenever its addRules method is invoked.
+     */
+    @Override
+    public RuleLoader findLoader(Digester d, Class<?> pluginClass, Properties p) throws PluginException {
+        String resourceName = pluginClass.getName().replace('.', '/') + resourceSuffix;
+
+        InputStream is = pluginClass.getClassLoader().getResourceAsStream(resourceName);
+
+        if (is == null) {
+            // ok, no such resource
+            return null;
+        }
+
+        return FinderFromResource.loadRules(d, pluginClass, is, resourceName);
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltResource.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltResource.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromDfltResource.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromFile.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromFile.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromFile.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromFile.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,102 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.io.FileInputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which expects the user to specify an absolute
+ * or relative path in the plugin declaration.
+ * <p>
+ * The file is expected to contain Digester rules in xmlrules format.
+ */
+public class FinderFromFile extends RuleFinder {
+
+    /**
+     * Xml attribute that needs to be present on a plugin declaration
+     * in order to specify the file to load rules from.
+     */
+    public static String DFLT_FILENAME_ATTR = "file";
+
+    /** See {@link #findLoader}. */
+    private String filenameAttr;
+
+    /** See {@link #findLoader}. */
+    public FinderFromFile() {
+        this(DFLT_FILENAME_ATTR);
+    }
+
+    /** See {@link #findLoader}. */
+    public FinderFromFile(String filenameAttr) { 
+        this.filenameAttr = filenameAttr;
+    }
+
+    /**
+     * If there exists a property with the name specified in the constructor,
+     * then load that file, run it through the xmlrules module and return an 
+     * object encapsulating those rules.
+     * <p>
+     * If there is no matching property provided, then just return null.
+     * <p>
+     * The returned object (when non-null) will add the selected rules to
+     * the digester whenever its addRules method is invoked.
+     */
+    @Override
+    public RuleLoader findLoader(Digester d, Class<?> pluginClass, Properties p) throws PluginException {
+        String rulesFileName = p.getProperty(filenameAttr);
+        if (rulesFileName == null) {
+            // nope, user hasn't requested dynamic rules to be loaded
+            // from a specific file.
+            return null;
+        }
+
+        InputStream is = null;
+        try {
+            is = new FileInputStream(rulesFileName);
+        } catch(IOException ioe) {
+            throw new PluginException(
+                "Unable to process file [" + rulesFileName + "]", ioe);
+        }
+
+        try {
+            RuleLoader loader = new LoaderFromStream(is);
+            return loader;
+        } catch(Exception e) {
+            throw new PluginException(
+                "Unable to load xmlrules from file [" + 
+                rulesFileName + "]", e);
+        } finally {
+            try {
+                is.close();
+            } catch(java.io.IOException ioe) {
+                throw new PluginException(
+                    "Unable to close stream for file [" + 
+                    rulesFileName + "]", ioe);
+            }
+        }
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromFile.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromFile.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromFile.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromMethod.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromMethod.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromMethod.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromMethod.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,76 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which expects the caller to specify a methodname
+ * as a plugin property, where the method exists on the plugin class.
+ */
+public class FinderFromMethod extends RuleFinder {
+
+    /**
+     * Xml attribute that needs to be present on a plugin declaration
+     * in order to specify the method to load rules from.
+     */
+    public static String DFLT_METHOD_ATTR = "method";
+
+    /** See {@link #findLoader}. */
+    private String methodAttr;
+
+    /** Constructor. */
+    public FinderFromMethod() {
+        this(DFLT_METHOD_ATTR);
+    }
+
+    /** See {@link #findLoader}. */
+    public FinderFromMethod(String methodAttr) { 
+        this.methodAttr = methodAttr;
+    }
+
+    /**
+     * If there exists a property with the name matching constructor param
+     * methodAttr, then locate the appropriate Method on the plugin class 
+     * and return an object encapsulating that info.
+     * <p>
+     * If there is no matching property provided, then just return null.
+     * <p>
+     * The returned object (when non-null) will invoke the target method
+     * on the plugin class whenever its addRules method is invoked. The
+     * target method is expected to have the following prototype:
+     * <code> public static void xxxxx(Digester d, String patternPrefix); </code>
+     */
+    @Override
+    public RuleLoader findLoader(Digester d, Class<?> pluginClass, Properties p) throws PluginException {
+        String methodName = p.getProperty(methodAttr);
+        if (methodName == null) {
+            // nope, user hasn't requested dynamic rules to be loaded
+            // from a specific class.
+            return null;
+        }
+
+        return new LoaderFromClass(pluginClass, methodName);
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromMethod.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromMethod.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromMethod.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromResource.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromResource.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromResource.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromResource.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,115 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.io.InputStream;
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which expects the user to specify a resource
+ * name (ie a file in the classpath). The file is expected to contain Digester
+ * rules in xmlrules format.
+ *
+ * @since 1.6
+ */
+
+public class FinderFromResource extends RuleFinder {
+
+    /**
+     * Name of xml attribute on the plugin declaration which is used
+     * to configure rule-loading for that declaration. 
+     */
+    public static String DFLT_RESOURCE_ATTR = "resource";
+
+    /** See {@link #findLoader}. */
+    private String resourceAttr;
+
+    /** Constructor. */
+    public FinderFromResource() {
+        this(DFLT_RESOURCE_ATTR);
+    }
+
+    /** See {@link #findLoader}. */
+    public FinderFromResource(String resourceAttr) { 
+        this.resourceAttr = resourceAttr;
+    }
+
+    /**
+     * If there exists a property with the name matching constructor param
+     * resourceAttr, then load that file, run it through the xmlrules
+     * module and return an object encapsulating those rules.
+     * <p>
+     * If there is no matching property provided, then just return null.
+     * <p>
+     * The returned object (when non-null) will add the selected rules to
+     * the digester whenever its addRules method is invoked.
+     */
+    @Override
+    public RuleLoader findLoader(Digester d, Class<?> pluginClass, Properties p) throws PluginException {
+        String resourceName = p.getProperty(resourceAttr);
+        if (resourceName == null) {
+            // nope, user hasn't requested dynamic rules to be loaded
+            // from a specific file.
+            return null;
+        }
+
+        InputStream is = pluginClass.getClassLoader().getResourceAsStream(resourceName);
+
+        if (is == null) {
+            throw new PluginException("Resource " + resourceName + " not found.");
+        }
+
+        return loadRules(d, pluginClass, is, resourceName);
+    }
+
+    /**
+     * Open the specified resource file (ie a file in the classpath, 
+     * including being within a jar in the classpath), run it through
+     * the xmlrules module and return an object encapsulating those rules.
+     * 
+     * @param d is the digester into which rules will eventually be loaded.
+     * @param pluginClass is the class whose xml params the rules are parsing.
+     * @param is is where the xmlrules will be read from, and must be non-null.
+     * @param resourceName is a string describing the source of the xmlrules,
+     *  for use in generating error messages.
+     */
+    public static RuleLoader loadRules(Digester d, Class<?> pluginClass, InputStream is, String resourceName) throws PluginException {
+        try {
+            RuleLoader loader = new LoaderFromStream(is);
+            return loader;
+        } catch(Exception e) {
+            throw new PluginException("Unable to load xmlrules from resource ["
+                    + resourceName
+                    + "]", e);
+        } finally {
+            try {
+                is.close();
+            } catch(java.io.IOException ioe) {
+                throw new PluginException("Unable to close stream for resource ["
+                        + resourceName
+                        + "]", ioe);
+            }
+        }
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromResource.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromResource.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderFromResource.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderSetProperties.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderSetProperties.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderSetProperties.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderSetProperties.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,98 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.util.Properties;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.RuleFinder;
+import org.apache.commons.digester3.plugins.RuleLoader;
+
+/**
+ * A rule-finding algorithm which expects the user to specify whether
+ * "automatic property setting" is desired. If this class discovers that
+ * this is in fact the case for a declaration, then a RuleLoader is returned
+ * which, when invoked, adds a single SetPropertiesRule instance to the
+ * digester.
+ * <p>
+ * This allows ordinary JavaBean classes to be used as plugins, and have
+ * xml attributes be mapped to bean properties of the same name, without
+ * any custom plugin rules being created for them.
+ * <p>
+ * This RuleFinder is typically used as the <i>last</i> RuleFinder, so that
+ * automatic property setting only occurs if there is no other source of
+ * custom rules available.
+ */
+public class FinderSetProperties extends RuleFinder {
+
+    public static String DFLT_PROPS_ATTR = "setprops";
+
+    public static String DFLT_FALSEVAL = "false";
+
+    private String propsAttr;
+
+    private String falseval;
+
+    /** See {@link #findLoader}. */
+    public FinderSetProperties() {
+        this(DFLT_PROPS_ATTR, DFLT_FALSEVAL);
+    }
+
+    /**
+     * Create a rule-finder which will arrange for a SetPropertiesRule to
+     * be defined for each instance of a plugin, so that xml attributes
+     * map to bean properties.
+     * <p>
+     * Param falseval will commonly be the string "false" for config files 
+     * written in English.
+     *
+     * @param propsAttr must be non-null.
+     * @param falseval must be non-null.
+     */
+    public FinderSetProperties(String propsAttr, String falseval) { 
+        this.propsAttr = propsAttr;
+        this.falseval = falseval;
+    }
+
+    /**
+     * Returns a RuleLoader <i>unless</i> the properties contain an entry
+     * with the name matching constructor param propsAttr, and the value 
+     * matching what is in falseval.
+     * <p>
+     * If no custom source of rules for a plugin is found, then the user
+     * almost always wants xml attributes to map to java bean properties,
+     * so this is the default behaviour unless the user explicitly indicates
+     * that they do <i>not</i> want a SetPropertiesRule to be provided for
+     * the plugged-in class.
+     * <p>
+     * The returned object (when non-null) will add a SetPropertiesRule to
+     * the digester whenever its addRules method is invoked.
+     */
+    @Override
+    public RuleLoader findLoader(Digester d, Class<?> pluginClass, Properties p) {
+        String state = p.getProperty(propsAttr);
+        if ((state != null)  && state.equals(falseval)) {
+            // user has explicitly disabled automatic setting of properties.
+            // this is not expected to be common, but allowed.
+            return null;
+        }
+        
+        return new LoaderSetProperties();
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderSetProperties.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderSetProperties.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/FinderSetProperties.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromClass.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromClass.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromClass.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromClass.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,94 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.lang.reflect.Method;
+
+import org.apache.commons.beanutils.MethodUtils;
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleLoader;
+import org.apache.commons.logging.Log;
+
+/**
+ * A RuleLoader which invokes a static method on a target class, leaving that
+ * method to actually instantiate and add new rules to a Digester instance.
+ */
+public class LoaderFromClass extends RuleLoader {
+
+    private Class<?> rulesClass;
+
+    private Method rulesMethod;
+
+    /** Constructor. */
+    public LoaderFromClass(Class<?> rulesClass, Method rulesMethod) {
+        this.rulesClass = rulesClass;
+        this.rulesMethod = rulesMethod;
+    }
+
+    /** Constructor. */
+    public LoaderFromClass(Class<?> rulesClass, String methodName) throws PluginException {
+        Method method = locateMethod(rulesClass, methodName);
+
+        if (method == null) {
+            throw new PluginException(
+                "rule class " + rulesClass.getName()
+                + " does not have method " + methodName
+                + " or that method has an invalid signature.");
+        }
+
+        this.rulesClass = rulesClass;
+        this.rulesMethod = method;
+    }
+
+    /**
+     * Just invoke the target method.
+     */
+    public void addRules(Digester d, String path) throws PluginException {
+        Log log = d.getLog();
+        boolean debug = log.isDebugEnabled();
+        if (debug) {
+            log.debug(
+                "LoaderFromClass loading rules for plugin at path [" 
+                + path + "]");
+        }
+
+        try {
+            Object[] params = {d, path};
+            rulesMethod.invoke(null, params);
+        } catch (Exception e) {
+            throw new PluginException(
+                "Unable to invoke rules method " + rulesMethod
+                + " on rules class " + rulesClass, e);
+        } 
+    }
+
+    /**
+     * Find a method on the specified class whose name matches methodName,
+     * and whose signature is:
+     * <code> public static void foo(Digester d, String patternPrefix);</code>.
+     *
+     * @return null if no such method exists.
+     */
+    public static Method locateMethod(Class<?> rulesClass, String methodName) throws PluginException {
+        Class<?>[] paramSpec = { Digester.class, String.class };
+        Method rulesMethod = MethodUtils.getAccessibleMethod(rulesClass, methodName, paramSpec);
+        return rulesMethod;
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromClass.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromClass.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromClass.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromStream.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromStream.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromStream.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromStream.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,81 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import static org.apache.commons.digester3.DigesterLoader.newLoader;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.InputStream;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.PluginException;
+import org.apache.commons.digester3.plugins.RuleLoader;
+import org.apache.commons.digester3.xmlrules.FromXmlRulesModule;
+import org.apache.commons.logging.Log;
+import org.xml.sax.InputSource;
+
+/**
+ * A rule-finding algorithm which loads an xmlplugins-format file.
+ * 
+ * Note that the "include" feature of xmlrules is not supported.
+ */
+public class LoaderFromStream extends RuleLoader {
+
+    private final byte[] input;
+
+    /** See {@link #load}. */
+    public LoaderFromStream(InputStream s) throws Exception {
+        ByteArrayOutputStream baos = new ByteArrayOutputStream();
+        byte[] buf = new byte[256];
+        for(;;) {
+            int i = s.read(buf);
+            if (i == -1)
+                break;
+            baos.write(buf, 0, i);
+        }
+        input = baos.toByteArray();
+    }
+
+    /**
+     * Add the rules previously loaded from the input stream into the
+     * specified digester.
+     */
+    @Override
+    public void addRules(Digester d, String path) throws PluginException {
+        Log log = d.getLog();
+        boolean debug = log.isDebugEnabled();
+        if (debug) {
+            log.debug(
+                "LoaderFromStream: loading rules for plugin at path [" 
+                + path + "]");
+        }
+
+        // Note that this input-source doesn't have any idea of its
+        // system id, so it has no way of resolving relative URLs
+        // such as the "include" feature of xmlrules. This is ok,
+        // because that doesn't work well with our approach of
+        // caching the input data in memory anyway.
+
+        InputSource source = new InputSource(new ByteArrayInputStream(this.input));
+        FromXmlRulesModule ruleModule = new FromXmlRulesModule(source);
+        // creating new digester allows decorating existing Rules instance
+        newLoader(ruleModule).setClassLoader(d.getClassLoader()).newDigester(d.getRules());
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromStream.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromStream.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderFromStream.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderSetProperties.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderSetProperties.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderSetProperties.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderSetProperties.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,49 @@
+/* $Id$
+ *
+ * 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.commons.digester3.plugins.strategies;
+
+import java.util.HashMap;
+
+import org.apache.commons.digester3.Digester;
+import org.apache.commons.digester3.plugins.RuleLoader;
+import org.apache.commons.digester3.rule.SetPropertiesRule;
+
+/**
+ * A RuleLoader which creates a single SetPropertiesRule and adds it to the
+ * digester when its addRules() method is invoked.
+ * <p>
+ * This loader ensures that any xml attributes on the plugin tag get
+ * mapped to equivalent properties on a javabean. This allows JavaBean
+ * classes to be used as plugins without any requirement to create custom
+ * plugin rules.
+ */
+public class LoaderSetProperties extends RuleLoader {
+
+    /**
+     * Just add a SetPropertiesRule at the specified path.
+     */
+    @Override
+    public void addRules(Digester digester, String path) {
+        if (digester.getLog().isDebugEnabled()) {
+            digester.getLog().debug(String.format("LoaderSetProperties loading rules for plugin at path [%s]", path));
+        }
+
+        digester.getRules().add(path, new SetPropertiesRule(new HashMap<String, String>(), true));
+    }
+
+}

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderSetProperties.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderSetProperties.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/LoaderSetProperties.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/package-info.java
URL: http://svn.apache.org/viewvc/commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/package-info.java?rev=1072175&view=auto
==============================================================================
--- commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/package-info.java (added)
+++ commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/package-info.java Fri Feb 18 22:26:49 2011
@@ -0,0 +1,23 @@
+/* $Id$
+ *
+ * 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.
+ */
+
+/**
+ * The <code>plugins.strategies</code> package contains "rule-finding" strategy
+ * classes, and their associated "helper" loader classes.
+ */
+package org.apache.commons.digester3.plugins.strategies;

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/package-info.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/package-info.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Propchange: commons/sandbox/digester3/trunk/src/main/java/org/apache/commons/digester3/plugins/strategies/package-info.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain