db-torque-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From tfisc...@apache.org
Subject svn commit: r910600 [8/29] - in /db/torque/torque4/trunk: maven-torque-gf-plugin/ maven-torque-gf-plugin/src/ maven-torque-gf-plugin/src/main/ maven-torque-gf-plugin/src/main/java/ maven-torque-gf-plugin/src/main/java/org/ maven-torque-gf-plugin/src/ma...
Date Tue, 16 Feb 2010 17:16:02 GMT
Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/ControllerState.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/ControllerState.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/ControllerState.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/ControllerState.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,495 @@
+package org.apache.torque.gf.control;
+
+/*
+ * 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.
+ */
+
+import java.io.File;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.torque.gf.configuration.UnitConfiguration;
+import org.apache.torque.gf.configuration.controller.GeneratorReference;
+import org.apache.torque.gf.configuration.controller.Output;
+import org.apache.torque.gf.generator.Generator;
+import org.apache.torque.gf.option.Option;
+import org.apache.torque.gf.option.OptionName;
+import org.apache.torque.gf.option.Options;
+import org.apache.torque.gf.qname.Namespace;
+import org.apache.torque.gf.qname.QualifiedName;
+import org.apache.torque.gf.source.SourceElement;
+import org.apache.torque.gf.variable.VariableStore;
+
+/**
+ * The state of the controller.  Contains all stuff the controller needs to
+ * track.
+ */
+public class ControllerState
+{
+    /**
+     * The output which currently processed .
+     */
+    private Output output;
+
+    /**
+     * The current stack of generators being executed.
+     */
+    private List<Generator> generators = new ArrayList<Generator>();
+
+    /**
+     * The root element of the source graph.
+     */
+    private SourceElement rootElement;
+
+    /**
+     * The current element within the source.
+     */
+    private SourceElement sourceElement;
+
+    /**
+     * The generation unit which is currently processed.
+     */
+    private UnitConfiguration unitConfiguration;
+
+    /**
+     * The reference in the controller to the root generator.
+     * May override mergepoints in the generators.
+     */
+    private GeneratorReference rootGeneratorReference;
+
+    /**
+     * The variable store.
+     */
+    private VariableStore variableStore = new VariableStore();
+
+    /**
+     * The currently generated output file. May be null if
+     * no file is currently generated (e.g. if the filename is currently
+     * generated).
+     */
+    private File outputFile;
+
+    /**
+     * The name of the currently processed source file. May be null if
+     * no source file is used (e.g. if the input is created by other means
+     * than reading a file).
+     */
+    private File sourceFile;
+
+    /**
+     * The name space in which the current generator operates.
+     */
+    private Namespace generatorNamespace;
+
+    /**
+     * Returns the output declaration which is currently processed.
+     *
+     * @return the output declaration which is currently processed, may be null
+     *         only if no output is processed at the moment.
+     */
+    public Output getOutput()
+    {
+        return output;
+    }
+
+    /**
+     * Sets the output declaration which is currently processed.
+     *
+     * @param output the output which is currently processed.
+     */
+    void setOutput(Output output)
+    {
+        this.output = output;
+    }
+
+    /**
+     * Returns the topmost generator in the stack of generators.
+     *
+     * @return the topmost generator in the stack of generators, or null
+     *         if the stack is empty.
+     */
+    public Generator getGenerator()
+    {
+        if (generators.isEmpty())
+        {
+            return null;
+        }
+        return generators.get(generators.size() - 1);
+    }
+
+    /**
+     * Pushes a generator onto the stack of generators.
+     *
+     * @param generator the generator to be added to the stack of generators,
+     *        not null.
+     */
+    public void pushGenerator(Generator generator)
+    {
+        if (generator == null)
+        {
+            throw new NullPointerException("generator must not be null");
+        }
+        this.generators.add(generator);
+    }
+
+    /**
+     * Pops the topmost generators from the stack of generators.
+     *
+     * @return the removed generator, not null.
+     *
+     * @throws IndexOutOfBoundsException if the stack is empty.
+     */
+    public Generator popGenerator()
+    {
+        return generators.remove(generators.size() - 1);
+    }
+
+    /**
+     * Returns the current source element. Does not return null
+     * during generation.
+     *
+     * @return the current source element.
+     */
+    public SourceElement getSourceElement()
+    {
+        return sourceElement;
+    }
+
+    /**
+     * Sets the current source element.
+     *
+     * @param sourceElement the new current source element, or null
+     *        to remove the current source element.
+     */
+    public void setSourceElement(SourceElement sourceElement)
+    {
+        this.sourceElement = sourceElement;
+    }
+
+    /**
+     * Returns the root element of the current source.
+     *
+     * @return The the root element of the current source;
+     *         may be null only if no source is currently processed.
+     */
+    public SourceElement getRootElement()
+    {
+        return rootElement;
+    }
+
+    /**
+     * Sets the root element of the current source.
+     *
+     * @param rootElement the the root element of the current source,
+     *        or null to remove the current root element.
+     */
+    void setRootElement(SourceElement rootElement)
+    {
+        this.rootElement = rootElement;
+    }
+
+    /**
+     * Returns the reference to the current content generator.
+     *
+     * @return the reference to the current content generator, or null if no
+     *         content generator is currently active.
+     */
+    public GeneratorReference getRootGeneratorReference()
+    {
+        return rootGeneratorReference;
+    }
+
+    /**
+     * Sets the reference to the current content generator.
+     *
+     * @param rootGeneratorReference the reference to the root generator
+     *        (i.e. the generator which produces the whole content),
+     *        or null to remove the reference.
+     */
+    void setRootGeneratorReference(GeneratorReference rootGeneratorReference)
+    {
+        this.rootGeneratorReference = rootGeneratorReference;
+    }
+
+
+    /**
+     * Sets the name space of the generator which is currently active.
+     *
+     * @param namespace the name space of the generator which is currently
+     *        active, or null to remove the name space.
+     */
+    void setGeneratorNamespace(Namespace namespace)
+    {
+        generatorNamespace = namespace;
+    }
+
+    /**
+     * Returns the name space of the generator which is currently active.
+     *
+     * @return the name space of the active generator. May be null only
+     *         if no generation is in progress.
+     */
+    public Namespace getGeneratorNamespace()
+    {
+        return generatorNamespace;
+    }
+
+    /**
+     * Calculates the value of an option in the current generator's context.
+     * The default namespace which is used when no namespace is given in
+     * <code>name</code> is the namespace of the currently used generator.
+     *
+     * @param name the name of the option, can contain a namespace.
+     *
+     * @return The value of the option, or null if no option with that name
+     *         is visible from the given namespace.
+     */
+    public Object getOption(String name)
+    {
+        Options options = unitConfiguration.getOptions();
+        QualifiedName qualifiedName = getQualifiedName(name);
+        Option option = options.getInHierarchy(qualifiedName);
+        Object result = null;
+        if (option != null)
+        {
+            result = option.getValue();
+        }
+        return result;
+    }
+
+    /**
+     * Calculates the value of an option in the current generator's context.
+     * The default namespace which is used when no namespace is given in
+     * <code>name</code> is the namespace of the currently used generator.
+     *
+     * @param name the object containing the name of the option,
+     *        which can contain a namespace, not null.
+     *
+     * @return The value of the option, or null if no option with that name
+     *         is visible from the given namespace.
+     *
+     * @throws NullPointerException if optionName is null.
+     */
+    public Object getOption(OptionName optionName)
+    {
+        return getOption(optionName.getName());
+    }
+
+    /**
+     * Convenience method to return the value of an option as boolean.
+     * The option is evaluated in the current generator's context, see
+     * getOption(String). <br/>
+     * Uses Boolean.paseBoolean() for String->Boolean conversion.
+     * @param name the name of the option, can contain a namespace.
+     *
+     * @return The value of the option as boolean, or false if no option
+     *         with that name is visible from the given namespace,
+     */
+    public boolean getBooleanOption(String name)
+    {
+        Object option = getOption(name);
+        if (option == null)
+        {
+            return false;
+        }
+        return Boolean.parseBoolean(option.toString());
+    }
+
+    /**
+     * Convenience method to return the value of an option as boolean.
+     * The option is evaluated in the current generator's context, see
+     * getOption(String). <br/>
+     * Uses Boolean.paseBoolean() for String->Boolean conversion.
+     *
+     * @param optionName the object containing the name of the option,
+     *        which can contain a namespace.
+     *
+     * @return The value of the option as boolean, or false if no option
+     *         with that name is visible from the given namespace.
+     *
+     * @throws NullPointerExeption if optionName is null.
+     */
+    public boolean getBooleanOption(OptionName optionName)
+    {
+        return getBooleanOption(optionName.getName());
+    }
+
+    /**
+     * Convenience method to return the value of an option as String.
+     * The option is evaluated in the current generator's context, see
+     * getOption(String). <br/>
+     *
+     * @param name the name of the option, can contain a namespace.
+     *
+     * @return The value of the option as boolean, or false if no option
+     *         with that name is visible from the given namespace,
+     */
+    public String getStringOption(String name)
+    {
+        Object option = getOption(name);
+        if (option == null)
+        {
+            return null;
+        }
+        return option.toString();
+    }
+
+    /**
+     * Convenience method to return the value of an option as String.
+     * The option is evaluated in the current generator's context, see
+     * getOption(String). <br/>
+     *
+     * @param optionName the object containing the name of the option,
+     *        which can contain a namespace.
+     *
+     * @return The value of the option as boolean, or false if no option
+     *         with that name is visible from the given namespace,
+     *
+     * @throws NullPointerExeption if optionName is null.
+     */
+    public String getStringOption(OptionName optionName)
+    {
+        return getStringOption(optionName.getName());
+    }
+
+    /**
+     * Returns all options which are visible from the current generator's
+     * namespace.
+     *
+     * @return all visible options, not null.
+     */
+    public Options getVisibleOptions()
+    {
+        return unitConfiguration.getOptions().getInHierarchy(
+                generatorNamespace);
+    }
+
+    /**
+     * Returns the VariableStore where generation variables can be set.
+     *
+     * @return the variableStore, never null.
+     */
+    public VariableStore getVariableStore()
+    {
+        return variableStore;
+    }
+
+    /**
+     * Converts a name to a QualifiedName, using the generator namespace as
+     * default namespace is fone is given.
+     *
+     * @param name the name to convert to a qualifiedName, not null.
+     * @return the corresponding qualifiedName.
+     *
+     * @throws NullPointerException if name is null
+     * @throws IllegalArgumentException if name is no valid qualifiedName.
+     */
+    public QualifiedName getQualifiedName(String name)
+    {
+        QualifiedName qualifiedName = new QualifiedName(
+                name,
+                generatorNamespace);
+        return qualifiedName;
+    }
+
+    /**
+     * Returns the currently generated file.
+     *
+     * @return the current output file. May only be null if no
+     *         output file is currently generated (e.g. if the file name
+     *         is currently generated).
+     */
+    public File getOutputFile()
+    {
+        return outputFile;
+    }
+
+    /**
+     * Sets the currently generated file.
+     *
+     * @param outputFilePath the currently generated file, or null to remove
+     *        the current output file.
+     */
+    void setOutputFile(File outputFilePath)
+    {
+        this.outputFile = outputFilePath;
+    }
+
+
+    /**
+     * Returns the currently used source file.
+     *
+     * @return the current source file. May be null if no
+     *         source file is currently used (e.g. if the source is created
+     *         by other means than reading a file).
+     */
+    public File getSourceFile()
+    {
+        return sourceFile;
+    }
+
+    /**
+     * Sets the currently used source file.
+     *
+     * @param sourceFile the current source file, or null to remove the
+     *        source file.
+     */
+    public void setSourceFile(File sourceFile)
+    {
+        this.sourceFile = sourceFile;
+    }
+
+
+    /**
+     * Returns the configuration of the currently processed generation unit.
+     *
+     * @return the configuration of the currently processed generation unit.
+     */
+    public UnitConfiguration getUnitConfiguration()
+    {
+        return unitConfiguration;
+    }
+
+    /**
+     * Sets the configuration of the currently processed generation unit.
+     *
+     * @param unitConfiguration the configuration of the currently processed
+     *        generation unit.
+     */
+    void setUnitConfiguration(UnitConfiguration unitConfiguration)
+    {
+        this.unitConfiguration = unitConfiguration;
+    }
+
+    @Override
+    public String toString()
+    {
+        StringBuffer result = new StringBuffer();
+        result.append("output=").append(output)
+                .append("outputFilePath=").append(outputFile)
+                .append("\ngeneratorNamespace=").append(generatorNamespace)
+                .append("\ngenerators=").append(generators)
+                .append("\nrootElement=").append(rootElement)
+                .append("\nsourceElement").append(sourceElement)
+                .append("\nrootGeneratorReference=")
+                .append(rootGeneratorReference)
+                .append("\nunitConfiguration=").append(unitConfiguration)
+                .append("\nvariableStore=").append(variableStore);
+        return result.toString();
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/TokenReplacer.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/TokenReplacer.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/TokenReplacer.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/TokenReplacer.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,181 @@
+package org.apache.torque.gf.control;
+
+/*
+ * 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.
+ */
+
+import org.apache.torque.gf.processor.string.StringProcessor;
+
+/**
+ * Replaces placeholder tokens like ${option:optionName} in a string by the
+ * resolved values. The escape character is the backslash (\).
+ *
+ * $Id: $
+ */
+public class TokenReplacer implements StringProcessor
+{
+    /** First character of a Token start. */
+    public static final char TOKEN_START_1 = '$';
+
+    /** Second character of a Token start. */
+    public static final char TOKEN_START_2 = '{';
+
+    /** The character ending a token. */
+    public static final char TOKEN_END = '}';
+
+    /** The escape character. */
+    public static final char ESCAPE = '\\';
+
+    /** The prefix for an option token. */
+    public static final String OPTION_PREFIX = "option";
+
+    /** The separator between prefix and key. */
+    public static final char PREFIX_SEPARATOR = ':';
+
+    /**
+     * The controller state for resolving options.
+     */
+    private ControllerState controllerState;
+
+    public TokenReplacer(ControllerState controllerState)
+    {
+        if (controllerState == null)
+        {
+            throw new NullPointerException("controllerState must not be null");
+        }
+        this.controllerState = controllerState;
+    }
+
+    /**
+     * Resolves all Tokens ${option:optionName} and replaces them with the
+     * appropriate value.
+     *
+     * @param toProcess the String to remove tokens from, or null.
+     */
+    public String process(String toProcess)
+    {
+        if (toProcess == null)
+        {
+            return null;
+        }
+        StringBuilder result = new StringBuilder();
+        StringBuilder tokenName = new StringBuilder();
+        boolean escape = false;
+        boolean inTokenStart = false;
+        boolean inToken = false;
+        for (char currentChar : toProcess.toCharArray())
+        {
+            if (currentChar == ESCAPE && !escape)
+            {
+                escape = true;
+                if (inTokenStart)
+                {
+                    result.append(TOKEN_START_1);
+                    inTokenStart = false; // $\ is not token start
+                }
+                continue;
+            }
+            if (escape)
+            {
+                if (inToken)
+                {
+                    tokenName.append(currentChar);
+                }
+                else
+                {
+                    result.append(currentChar);
+                }
+                escape = false;
+                continue;
+            }
+            escape = false;
+            if (currentChar == TOKEN_START_1 && !inTokenStart && !inToken)
+            {
+                inTokenStart = true;
+                continue;
+            }
+            if (inTokenStart)
+            {
+                if (currentChar == TOKEN_START_2)
+                {
+                    inTokenStart = false;
+                    inToken = true;
+                    continue;
+                }
+                else
+                {
+                    result.append(TOKEN_START_1); // did not copy that before
+                    result.append(currentChar);
+                    inTokenStart = false;
+                    continue;
+                }
+            }
+            if (currentChar == TOKEN_END && inToken)
+            {
+                result.append(resolveToken(tokenName.toString()));
+                tokenName = new StringBuilder();
+                inToken = false;
+                continue;
+            }
+            if (inToken)
+            {
+                tokenName.append(currentChar);
+            }
+            else
+            {
+                result.append(currentChar);
+            }
+        }
+        if (escape)
+        {
+            throw new IllegalArgumentException("Single escape character "
+                    + ESCAPE
+                    + " encountered at end of String "
+                    + toProcess);
+        }
+        if (inTokenStart)
+        {
+            result.append(TOKEN_START_1);
+        }
+        if (inToken)
+        {
+            throw new IllegalArgumentException("Token end "
+                    + TOKEN_END
+                    + " missing at end of String "
+                    + toProcess);
+        }
+        return result.toString();
+    }
+
+    private String resolveToken(String tokenName)
+    {
+        if (!tokenName.startsWith(OPTION_PREFIX + PREFIX_SEPARATOR))
+        {
+            throw new IllegalArgumentException("Token name must start with"
+                    + OPTION_PREFIX + PREFIX_SEPARATOR);
+        }
+        String optionName = tokenName.substring(
+                (OPTION_PREFIX + PREFIX_SEPARATOR).length());
+        Object optionValue = controllerState.getOption(optionName);
+        if (optionValue == null)
+        {
+            return "";
+        }
+        return optionValue.toString();
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/ApplyAction.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/ApplyAction.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/ApplyAction.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/ApplyAction.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,200 @@
+package org.apache.torque.gf.control.action;
+
+/*
+ * 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.
+ */
+
+import java.util.List;
+
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.control.TokenReplacer;
+import org.apache.torque.gf.generator.Generator;
+import org.apache.torque.gf.generator.GeneratorException;
+import org.apache.torque.gf.qname.Namespace;
+import org.apache.torque.gf.qname.QualifiedName;
+import org.apache.torque.gf.source.SourceElement;
+import org.apache.torque.gf.source.SourcePath;
+
+/**
+ * Applies a generator to the matching element.
+ * The output of the generator is appended to the output.
+ */
+public class ApplyAction implements MergepointAction
+{
+    /**
+     * The path to the source element to be processed, not null.
+     */
+    private String path;
+
+    /**
+     * The name of the generator to be invoked on the element, not null.
+     */
+    private String generatorName;
+
+    /**
+     * Whether it is correct to have no element to apply.
+     */
+    private boolean acceptNotSet = true;
+
+    /**
+     * Constructor.
+     *
+     * @param path The path to the source element to be processed.
+     *        <code>null</code> means ".".
+     * @param generatorName the name of the generator to apply.
+     * @param acceptNotSet true if no error should be thrown if no element
+     *        matches the given path, true if an error should be thrown in
+     *        such a case. null means true.
+     */
+    public ApplyAction(String path, String generatorName, Boolean acceptNotSet)
+    {
+        if (path == null)
+        {
+            this.path = ".";
+        }
+        else
+        {
+            this.path = path;
+        }
+
+        if (generatorName == null)
+        {
+            throw new IllegalArgumentException(
+                    "ApplyAction: generatorName must not be null");
+        }
+        this.generatorName = generatorName;
+        if (acceptNotSet != null)
+        {
+            this.acceptNotSet = acceptNotSet.booleanValue();
+        }
+    }
+
+    /**
+     * Applies a generator to the matching element.
+     * The output of the generator is appended to the output.
+     * ${...} Tokens are replaced within generatorName and path.
+     */
+    public String execute(ControllerState controllerState)
+        throws GeneratorException
+    {
+        TokenReplacer tokenReplacer = new TokenReplacer(controllerState);
+        String detokenizedGeneratorName = tokenReplacer.process(generatorName);
+        QualifiedName qualifiedGeneratorName = new QualifiedName(
+                detokenizedGeneratorName,
+                Namespace.ROOT_NAMESPACE);
+        Generator generator
+                = controllerState.getUnitConfiguration()
+                    .getGeneratorConfiguration()
+                    .getGenerator(qualifiedGeneratorName);
+        if (generator == null)
+        {
+            throw new GeneratorException("ApplyAction : The generator "
+                    + generatorName
+                    + " does not exist");
+        }
+
+        SourceElement currentElement = controllerState.getSourceElement();
+        String detokenizedPath = tokenReplacer.process(path);
+
+        List<SourceElement> selectedElements
+                = SourcePath.getElements(currentElement, detokenizedPath);
+        if (!acceptNotSet && selectedElements.isEmpty())
+        {
+            throw new GeneratorException(
+                    "ApplyAction : selected path "
+                        + path
+                        + " does not match an element"
+                        + " and acceptNotSet was set to false");
+        }
+        if (selectedElements.size() > 1)
+        {
+            throw new GeneratorException(
+                    "ApplyAction : selected path "
+                        + path
+                        + " contains more than one element ("
+                        + selectedElements.size()
+                        + " times)");
+        }
+        StringBuffer result = new StringBuffer();
+        for (SourceElement sourceElement : selectedElements)
+        {
+            controllerState.setSourceElement(sourceElement);
+            generator.beforeExecute(controllerState);
+            result.append(generator.execute(controllerState));
+            generator.afterExecute(controllerState);
+        }
+        controllerState.setSourceElement(currentElement);
+        return result.toString();
+    }
+
+    @Override
+    public String toString()
+    {
+        return "(ApplyAction: path = "
+                + path
+                + ", generator = "
+                + generatorName
+                + ", acceptNotSet = "
+                + acceptNotSet
+                + ")";
+    }
+
+    @Override
+    public int hashCode()
+    {
+        final int prime = 31;
+        final int secondPrime = 1231;
+        final int thirdPrime = 1237;
+        int result = 1;
+        result = prime * result + (acceptNotSet ? secondPrime : thirdPrime);
+        result = prime * result + path.hashCode();
+        result = prime * result + generatorName.hashCode();
+        return result;
+    }
+
+    @Override
+    public boolean equals(Object obj)
+    {
+        if (this == obj)
+        {
+            return true;
+        }
+        if (obj == null)
+        {
+            return false;
+        }
+        if (getClass() != obj.getClass())
+        {
+            return false;
+        }
+        final ApplyAction other = (ApplyAction) obj;
+        if (acceptNotSet != other.acceptNotSet)
+        {
+            return false;
+        }
+        if (!path.equals(other.path))
+        {
+            return false;
+        }
+        if (!generatorName.equals(other.generatorName))
+        {
+            return false;
+        }
+        return true;
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/MergepointAction.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/MergepointAction.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/MergepointAction.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/MergepointAction.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,42 @@
+package org.apache.torque.gf.control.action;
+
+/*
+ * 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.
+ */
+
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.generator.GeneratorException;
+
+/**
+ * An action which can be executed in a mergepoint.
+ */
+public interface MergepointAction
+{
+    /**
+     * Executes the action.
+     *
+     * @param controllerState The current state of the controller.
+     *
+     * @return The value to insert into the mergepoint, not null.
+     *
+     * @throws GeneratorException if an error occurs during generation.
+     */
+    String execute(ControllerState controllerState)
+        throws GeneratorException;
+
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OptionAction.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OptionAction.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OptionAction.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OptionAction.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,101 @@
+package org.apache.torque.gf.control.action;
+
+/*
+ * 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.
+ */
+
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.generator.GeneratorException;
+
+/**
+ * Inserts the value of an option into a mergepoint.
+ */
+public class OptionAction implements MergepointAction
+{
+    /**
+     * The name of the option to insert.
+     */
+    private String optionName;
+
+    /**
+     * Whether it is acceptable that the option is not set.
+     */
+    private boolean acceptNotSet = true;
+
+    /**
+     * Constructor.
+     *
+     * @param option the name of the option. May or may not be prefixed
+     *        with a namespace (if no namespace is used, the namespace of the
+     *        current generator is used).
+     * @param acceptNotSet true if it is acceptable that the option is not set,
+     *        false if it is an error that the option is not set.
+     *        null means true.
+     */
+    public OptionAction(String option, Boolean acceptNotSet)
+    {
+        if (option == null)
+        {
+            throw new IllegalArgumentException(
+                    "option must not be null");
+        }
+        this.optionName = option;
+        if (acceptNotSet != null)
+        {
+            this.acceptNotSet = acceptNotSet.booleanValue();
+        }
+    }
+
+    /**
+     * Returns the value of the configured option.
+     *
+     * @param controllerState the current state of the controller.
+     *
+     * @return The value of the option, or the empty String if
+     *         acceptNotSet is true and the option is not set.
+     *
+     * @throws GeneratorException if acceptNotSet is false and the option
+     *         is not set.
+     */
+    public String execute(ControllerState controllerState)
+        throws GeneratorException
+    {
+        Object option = controllerState.getOption(optionName);
+        if (option == null)
+        {
+            if (acceptNotSet)
+            {
+                return "";
+            }
+            throw new GeneratorException("OptionAction: The option "
+                    + optionName
+                    + " is not set");
+        }
+        return option.toString();
+    }
+
+    @Override
+    public String toString()
+    {
+        return "(OptionAction: optionName="
+                + optionName
+                + ", acceptNotSet="
+                + acceptNotSet
+                + ")";
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OutputAction.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OutputAction.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OutputAction.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/OutputAction.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,77 @@
+package org.apache.torque.gf.control.action;
+
+/*
+ * 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.
+ */
+
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.control.TokenReplacer;
+import org.apache.torque.gf.generator.GeneratorException;
+
+/**
+ * Inserts a fixed String into a mergepoint.
+ */
+public class OutputAction implements MergepointAction
+{
+    /**
+     * The fixed value to insert.
+     */
+    private String value;
+
+    /**
+     * Constructor.
+     *
+     * @param value fixed value to insert, not null.
+     */
+    public OutputAction(String value)
+    {
+        if (value == null)
+        {
+            throw new IllegalArgumentException(
+                    "value must not be null");
+        }
+        this.value = value;
+    }
+
+    /**
+     * Returns the value. ${...} Tokens are replaced within the value.
+     *
+     * @param controllerState the current state of the controller.
+     *
+     * @return The value of the option, or the empty String if
+     *         acceptNotSet is true and the option is not set.
+     *
+     * @throws GeneratorException if acceptNotSet is false and the option
+     *         is not set.
+     */
+    public String execute(ControllerState controllerState)
+        throws GeneratorException
+    {
+        TokenReplacer tokenReplacer = new TokenReplacer(controllerState);
+        String detokenizedValue = tokenReplacer.process(value);
+        return detokenizedValue;
+    }
+
+    @Override
+    public String toString()
+    {
+        return "(OutputAction: value="
+                + value
+                + ")";
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/SourceElementAttributeAction.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/SourceElementAttributeAction.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/SourceElementAttributeAction.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/SourceElementAttributeAction.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,146 @@
+package org.apache.torque.gf.control.action;
+
+/*
+ * 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.
+ */
+
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.control.TokenReplacer;
+import org.apache.torque.gf.generator.GeneratorException;
+import org.apache.torque.gf.source.SourceElement;
+import org.apache.torque.gf.source.SourcePath;
+
+/**
+ * Applies an generator to a given source element.
+ */
+public class SourceElementAttributeAction implements MergepointAction
+{
+    /**
+     * The SourePath to find the element which should be used as input
+     * relative to the current element.
+     */
+    private String elementPath;
+
+    /**
+     * The name of the attribute which should be output.
+     */
+    private String attributeName;
+
+    /**
+     * Whether it is acceptable that the element does not exist or the given
+     * attribute is not set.
+     */
+    private boolean acceptNotSet = true;
+
+    /**
+     * Constructor.
+     *
+     * @param element the SourcePath to the element, not null.
+     * @param attributeName The name of the attribute to evaluate,
+     *        or null to access the attribute with name null.
+     * @param acceptNotSet true if the attribute may not exist,
+     *        false if it is an error that the attribute does not exist,
+     *        null means true.
+     */
+    public SourceElementAttributeAction(
+            String element,
+            String attributeName,
+            Boolean acceptNotSet)
+    {
+        if (element == null)
+        {
+            throw new IllegalArgumentException(
+                    "element must not be null");
+        }
+        this.elementPath = element;
+        this.attributeName = attributeName;
+        if (acceptNotSet != null)
+        {
+            this.acceptNotSet = acceptNotSet.booleanValue();
+        }
+    }
+
+    /**
+     * Returns the value of the configured attribute of the configured source
+     * element. ${...} Tokens are replaced within the element path and the
+     * attribute name.
+     *
+     * @param controllerState the current state of the controller.
+     *
+     * @return The value of the attribute, or the empty String if
+     *         acceptNotSet is true and the attribute is not set.
+     *
+     * @throws GeneratorException if acceptNotSet is false and either no
+     *         source element can be found or the attribute is not set.
+     */
+    public String execute(ControllerState controllerState)
+        throws GeneratorException
+    {
+        TokenReplacer tokenReplacer = new TokenReplacer(controllerState);
+        String detonizedElementPath = tokenReplacer.process(elementPath);
+
+        SourceElement sourceElement = SourcePath.getElement(
+                controllerState.getSourceElement(),
+                detonizedElementPath,
+                acceptNotSet);
+        if (sourceElement == null)
+        {
+            if (acceptNotSet)
+            {
+                return "";
+            }
+            else
+            {
+                throw new GeneratorException("SourceElementAttributeAction: "
+                        + "No element "
+                        + elementPath
+                        + "can be found.");
+            }
+        }
+        String detonizedAttributeName = tokenReplacer.process(attributeName);
+        Object result = sourceElement.getAttribute(detonizedAttributeName);
+        if (result == null)
+        {
+            if (acceptNotSet)
+            {
+                return "";
+            }
+            throw new GeneratorException("SourceElementAttributeAction: "
+                    + "The attribute "
+                    + attributeName
+                    + " is not set on the element "
+                    + sourceElement.getName()
+                    + " (element path was "
+                    + elementPath
+                    + ")");
+        }
+        return result.toString();
+    }
+
+    @Override
+    public String toString()
+    {
+        return "(ApplyAction: element="
+                + elementPath
+                + ", attribute="
+                + attributeName
+                + ", acceptNotSet="
+                + acceptNotSet
+                + ")";
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/TraverseAllAction.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/TraverseAllAction.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/TraverseAllAction.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/TraverseAllAction.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,204 @@
+package org.apache.torque.gf.control.action;
+
+/*
+ * 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.
+ */
+
+import java.util.List;
+
+import org.apache.torque.gf.configuration.generator.GeneratorConfiguration;
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.control.TokenReplacer;
+import org.apache.torque.gf.generator.Generator;
+import org.apache.torque.gf.generator.GeneratorException;
+import org.apache.torque.gf.qname.Namespace;
+import org.apache.torque.gf.qname.QualifiedName;
+import org.apache.torque.gf.source.SourceElement;
+import org.apache.torque.gf.source.SourcePath;
+
+/**
+ * Traverses all matching elements, and applies a generator to each matching
+ * element. The output of each generator is appended to the output.
+ */
+public class TraverseAllAction implements MergepointAction
+{
+    /**
+     * The filter for the elements to traverse, not null.
+     */
+    private String elementsToTraverseName;
+
+    /**
+     * The name of the generator to be invoked for each element, not null.
+     */
+    private String generatorName;
+
+    /**
+     * Whether it is correct to have no element to traverse.
+     */
+    private boolean acceptEmpty = true;
+
+    /**
+     * Constructor.
+     *
+     * @param elementsToTraverseName the elements to traverse, not null.
+     * @param generatorName the name of the generator to be invoked for each
+     *        element, not null.
+     * @param acceptEmpty true if it is correct if no matching elements are
+     *        found, false to throw an error if no matching elements are found,
+     *        null means true.
+     */
+    public TraverseAllAction(
+            String elementsToTraverseName,
+            String generatorName,
+            Boolean acceptEmpty)
+    {
+        if (elementsToTraverseName == null)
+        {
+            throw new IllegalArgumentException(
+                    "elementsToTraverseName must not be null");
+        }
+        this.elementsToTraverseName = elementsToTraverseName;
+
+        if (generatorName == null)
+        {
+            throw new IllegalArgumentException(
+                    "generatorName must not be null");
+        }
+        this.generatorName = generatorName;
+        if (acceptEmpty != null)
+        {
+            this.acceptEmpty = acceptEmpty.booleanValue();
+        }
+    }
+
+    /**
+     * Traverses all matching elements, and applies a generator to each matching
+     * element. The output of each generator is appended to the output.
+     * ${...} Tokens are replaced within generatorName and
+     * elementsToTraverseName.
+     */
+    public String execute(ControllerState controllerState)
+        throws GeneratorException
+    {
+        TokenReplacer tokenReplacer = new TokenReplacer(controllerState);
+
+        Generator generator;
+        {
+            GeneratorConfiguration generatorConfiguration
+                    = controllerState.getUnitConfiguration()
+                        .getGeneratorConfiguration();
+            String detokenizedGeneratorName
+                    = tokenReplacer.process(generatorName);
+            QualifiedName generatorQName = new QualifiedName(
+                    detokenizedGeneratorName,
+                    Namespace.ROOT_NAMESPACE);
+
+            generator = generatorConfiguration.getGenerator(generatorQName);
+            if (generator == null)
+            {
+                throw new GeneratorException("TraverseAllAction : The generator "
+                        + generatorName
+                        + " does not exist");
+            }
+        }
+
+        SourceElement currentElement = controllerState.getSourceElement();
+        String detokenizedElementToTraverseName
+                = tokenReplacer.process(elementsToTraverseName);
+
+        List<SourceElement> selectedElements
+                = SourcePath.getElements(
+                        currentElement,
+                        detokenizedElementToTraverseName);
+        if (!acceptEmpty && selectedElements.isEmpty())
+        {
+            throw new GeneratorException(
+                    "TraverseAllAction : selected element "
+                        + elementsToTraverseName
+                        + " does not exist and acceptEmpty was set to false");
+        }
+
+        StringBuffer result = new StringBuffer();
+        for (SourceElement sourceElement : selectedElements)
+        {
+            controllerState.setSourceElement(sourceElement);
+            generator.beforeExecute(controllerState);
+            result.append(generator.execute(controllerState));
+            generator.afterExecute(controllerState);
+        }
+        controllerState.setSourceElement(currentElement);
+        return result.toString();
+    }
+
+    @Override
+    public String toString()
+    {
+        return "(TraverseAllAction: element = "
+                + elementsToTraverseName
+                + ", generator = "
+                + generatorName
+                + ", acceptEmpty = "
+                + acceptEmpty
+                + ")";
+    }
+
+    @Override
+    public int hashCode()
+    {
+        final int prime = 31;
+        final int secondPrime = 1231;
+        final int thirdPrime = 1237;
+        int result = 1;
+        result = prime * result + (acceptEmpty ? secondPrime : thirdPrime);
+        result = prime * result + elementsToTraverseName.hashCode();
+        result = prime * result + generatorName.hashCode();
+        return result;
+    }
+
+    @Override
+    public boolean equals(Object obj)
+    {
+        if (this == obj)
+        {
+            return true;
+        }
+        if (obj == null)
+        {
+            return false;
+        }
+        if (getClass() != obj.getClass())
+        {
+            return false;
+        }
+
+        final TraverseAllAction other = (TraverseAllAction) obj;
+        if (acceptEmpty != other.acceptEmpty)
+        {
+            return false;
+        }
+        if (!elementsToTraverseName.equals(other.elementsToTraverseName))
+        {
+            return false;
+        }
+        if (!generatorName.equals(other.generatorName))
+        {
+            return false;
+        }
+        return true;
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/package.html
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/package.html?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/package.html (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/action/package.html Tue Feb 16 17:15:43 2010
@@ -0,0 +1,25 @@
+<!--
+ Copyright 2001-2006 The Apache Software Foundation.
+
+ Licensed under the Apache License, Version 2.0 (the "License")
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+     http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<html>
+  <head>
+    <title>Torque-gf actions</title>
+  </head>
+  <body>
+    <p>
+      This package defines and implements mergepoint actions.
+    </p>
+  </body>
+</html>

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/package.html
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/package.html?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/package.html (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/control/package.html Tue Feb 16 17:15:43 2010
@@ -0,0 +1,25 @@
+<!--
+ Copyright 2001-2006 The Apache Software Foundation.
+
+ Licensed under the Apache License, Version 2.0 (the "License")
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+     http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<html>
+  <head>
+    <title>Torque-gf control</title>
+  </head>
+  <body>
+    <p>
+      This package implements the torque-gf Controller .
+    </p>
+  </body>
+</html>

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Generator.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Generator.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Generator.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Generator.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,135 @@
+package org.apache.torque.gf.generator;
+
+/*
+ * 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.
+ */
+
+import java.util.Map;
+
+import org.apache.torque.gf.configuration.ConfigurationException;
+import org.apache.torque.gf.configuration.mergepoint.MergepointMapping;
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.qname.QualifiedName;
+
+/**
+ * Generates String output from the AST.
+ */
+public interface Generator
+{
+    /**
+     * Returns the name of the Template. The namespace part of the name defines
+     * the default context of the template.
+     *
+     * @return the name of the Template, not null.
+     */
+    QualifiedName getName();
+
+    /**
+     * Adds an mergepoint mapping to the generator. No mergepoint
+     * mappings must exist with the given name.
+     *
+     * @param mergepointMapping the mergepointMapping to add, not null.
+     *
+     * @throws NullPointerException if mergepointMapping is null.
+     * @throws ConfigurationException if an mergepointMapping
+     *          for the given name already exists.
+     */
+    void addMergepointMapping(MergepointMapping mergepointMapping)
+        throws ConfigurationException;
+
+    /**
+     * Sets an mergepoint mapping in the generator. If a mergepoint
+     * mapping with the given name already exists, it is replaced.
+     *
+     * @param mergepointMapping the mergepointMapping to add, not null.
+     *
+     * @return the replaced mergepoint mapping, not null.
+     *
+     * @throws NullPointerException if mergepointMapping is null.
+     */
+    MergepointMapping setMergepointMapping(MergepointMapping mergepointMapping);
+
+    /**
+     * Returns the mergepoint mapping for the given mergepoint name.
+     *
+     * @param name the name of the mergepoint mapping.
+     *
+     * @return the mergepoint mapping for the given name, or null if no
+     *           mergepoint mapping exists for this name.
+     */
+    MergepointMapping getMergepointMapping(String name);
+
+    /**
+     * Returns the map of all mergepoint mappings, keyed by their name.
+     *
+     * @return the map of mergepoint mappings, not null.
+     */
+    Map<String, MergepointMapping> getMergepointMappings();
+
+    /**
+     * Sets the name of the input root element. If set, the generator must
+     * check if the name of the input root element corresponds to the set
+     * element name and throw an exception if the names do not match.
+     *
+     * @param inputName the name of the root element of the source,
+     *        or null to accept any input name.
+     */
+    void setInputElementName(String inputName);
+
+    /**
+     * Returns the name of the input root element. If not null, the generator
+     * checks if the name of the input root element corresponds to the set
+     * element name and throw an exception if the names do not match.
+     *
+     * @return inputName the name of the root element of the source,
+     *          or if any input name is accepted.
+     */
+    String getInputElementName();
+
+    /**
+     * Adjusts the state of the Controller before generation.
+     *
+     * @param controllerState the current controller state, not null.
+     *
+     * @throws GeneratorException if adjusting the controller state fails.
+     */
+    void beforeExecute(ControllerState controllerState)
+        throws GeneratorException;
+
+    /**
+     * Adjusts the state of the Controller after generation.
+     *
+     * @param controllerState the current controller state, not null.
+     *
+     * @throws GeneratorException if adjusting the controller state fails.
+     */
+    void afterExecute(ControllerState controllerState)
+        throws GeneratorException;
+
+    /**
+     * Generates the output for this template into the Generated object.
+     *
+     * @param controllerState the current controller state, not null.
+     *
+     * @return the output of the Generator.
+     *
+     * @throws GeneratorException if generation fails.
+     */
+    String execute(ControllerState controllerState)
+        throws GeneratorException;
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorException.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorException.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorException.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorException.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,80 @@
+package org.apache.torque.gf.generator;
+
+/*
+ * 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.
+ */
+
+/**
+ * This exception is the superclass of all Exceptions thrown in the Torque
+ * generator. It is thrown whenever an Error occurs which is specific
+ * to the Torque Generator.
+ */
+public class GeneratorException extends Exception
+{
+    /**
+     * The version of the class
+     * (for serialization and deserialization purposes).
+     */
+    private static final long serialVersionUID = 1L;
+
+    /**
+     * Constructs a GeneratorException without error message.
+     */
+    public GeneratorException()
+    {
+        super();
+    }
+
+    /**
+     * Constructs a GeneratorException with the given error message.
+     *
+     * @param message the error message
+     *
+     * @see Exception#Exception(java.lang.String)
+     */
+    public GeneratorException(String message)
+    {
+        super(message);
+    }
+
+    /**
+     * Constructs a GeneratorException which wraps another exception.
+     *
+     * @param cause The cause of the error.
+     *
+     * @see Exception#Exception(java.lang.Throwable)
+     */
+    public GeneratorException(Throwable cause)
+    {
+        super(cause);
+    }
+
+    /**
+     * Constructs a GeneratorException which wraps another exception,
+     * and which has its own error message.
+     *
+     * @param message The error message.
+     * @param cause The exception to wrap.
+     *
+     * @see Exception#Exception(java.lang.String, java.lang.Throwable)
+     */
+    public GeneratorException(String message, Throwable cause)
+    {
+        super(message, cause);
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorImpl.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorImpl.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorImpl.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/GeneratorImpl.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,350 @@
+package org.apache.torque.gf.generator;
+
+/*
+ * 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.
+ */
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.torque.gf.configuration.ConfigurationException;
+import org.apache.torque.gf.configuration.mergepoint.MergepointMapping;
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.control.action.MergepointAction;
+import org.apache.torque.gf.qname.QualifiedName;
+import org.apache.torque.gf.source.SourcePath;
+import org.apache.torque.gf.variable.Variable;
+import org.apache.torque.gf.variable.VariableStore;
+
+/**
+ * Implementation of the features in the <code>Generator<code> interface
+ * which do not depend on type of Generator.
+ */
+public abstract class GeneratorImpl implements Generator
+{
+    /**
+     * The log.
+     */
+    private static Log log = LogFactory.getLog(GeneratorImpl.class);
+
+    /**
+     * The mergepoint mappings configured for this generator.
+     */
+    private Map<String, MergepointMapping> mergepointMappings
+            = new HashMap<String, MergepointMapping>();
+
+    /**
+     * The name of the generator. Is immutable.
+     */
+    private QualifiedName name;
+
+    /**
+     * The name of the input elements to process. If null, the input
+     * elements are not checked.
+     */
+    private String inputElementName;
+
+    /**
+     * Constructs a GeneratorImpl with the given name.
+     *
+     * @param name the name of this generator, not null.
+     *
+     * @throws NullPointerException if name is null.
+     */
+    public GeneratorImpl(QualifiedName name)
+    {
+        if (name == null)
+        {
+            throw new NullPointerException("name must not be null");
+        }
+        this.name = name;
+    }
+
+    public QualifiedName getName()
+    {
+        return name;
+    }
+
+    public String getInputElementName()
+    {
+        return inputElementName;
+    }
+
+    public void setInputElementName(String inputElementName)
+    {
+        this.inputElementName = inputElementName;
+    }
+
+    /**
+     * Adds an mergepoint mapping to the generator. No mergepoint
+     * mappings must exist with the given name.
+     *
+     * @param mergepointMapping the mergepointMapping to add, not null.
+     *
+     * @throws NullPointerException if mergepointMapping is null.
+     * @throws ConfigurationException if an mergepointMapping
+     *          for the given name already exists.
+     */
+    public void addMergepointMapping(MergepointMapping mergepointMapping)
+        throws ConfigurationException
+    {
+        MergepointMapping oldMapping
+                = mergepointMappings.get(mergepointMapping.getName());
+        if (oldMapping != null)
+        {
+            throw new ConfigurationException(
+                    "Attempted to add another mergepoint mapping for the name "
+                        + mergepointMapping.getName()
+                        + " : New mapping mapped to Actions "
+                        + mergepointMapping.getActions()
+                        + ", old mapping mapped to Actions "
+                        + oldMapping.getActions());
+        }
+        mergepointMappings.put(mergepointMapping.getName(), mergepointMapping);
+    }
+
+    /**
+     * Sets an mergepoint mapping in the generator. If a mergepoint
+     * mapping with the given name already exists, it is replaced.
+     *
+     * @param mergepointMapping the mergepointMapping to add, not null.
+     *
+     * @return the replaced mergepoint mapping, not null.
+     *
+     * @throws NullPointerException if mergepointMapping is null.
+     */
+    public MergepointMapping setMergepointMapping(
+            MergepointMapping mergepointMapping)
+    {
+        return mergepointMappings.put(
+                mergepointMapping.getName(),
+                mergepointMapping);
+    }
+    /**
+     * Returns the mergepoint mapping for the given mergepoint name.
+     * @return the mergepoint mapping for the given name, or null if no
+     *          mergepoint mapping exists for this name.
+     */
+    public MergepointMapping getMergepointMapping(String name)
+    {
+        return mergepointMappings.get(name);
+    }
+
+    public Map<String, MergepointMapping> getMergepointMappings()
+    {
+        return Collections.unmodifiableMap(mergepointMappings);
+    }
+
+    public void beforeExecute(ControllerState controllerState)
+        throws GeneratorException
+    {
+        controllerState.pushGenerator(this);
+        if (log.isDebugEnabled())
+        {
+            log.debug("Executing generator "
+                    + getName()
+                    + " on element "
+                    + SourcePath.getPathAsString(
+                            controllerState.getSourceElement()));
+        }
+    }
+
+    public void afterExecute(ControllerState controllerState)
+    {
+        controllerState.popGenerator();
+    }
+
+    public abstract String execute(ControllerState controllerState)
+        throws GeneratorException;
+
+    @Override
+    public String toString()
+    {
+        StringBuffer result = new StringBuffer();
+        result.append("(name=").append(name).append(",");
+        result.append("inputElementName=").append(inputElementName);
+        result.append(")");
+        return result.toString();
+    }
+
+    /**
+     * Sets a variable. The key can be given with or without namespace;
+     * in the latter case, the variable is set in the namespace of this
+     * generator. the Scope of the variable is this generator and its children.
+     *
+     * @param key the name of the variable, not null
+     * @param value the value of the variable, may be null.
+     * @param controllerState the context of the controller, not null.
+     *
+     * @throws NullPointerException if key, scope or controllerState is null.
+     * @throws IllegalArgumentException if the key is no valid QualifiedName.
+     */
+    public void setVariable(
+            String key,
+            Object value,
+            ControllerState controllerState)
+    {
+        setVariable(key, value, Variable.Scope.CHILDREN, controllerState);
+    }
+
+    /**
+     * Sets a variable. The key can be given with or without namespace;
+     * in the latter case, the variable is set in the namespace of this
+     * generator.
+     *
+     * @param key the name of the variable, not null.
+     * @param value the value of the variable, may be null.
+     * @param scope the scope of the variable, not null.
+     * @param controllerState the context of the controller, not null.
+     *
+     * @throws NullPointerException if key or scope is null.
+     * @throws IllegalArgumentException if the key is no valid QualifiedName.
+     */
+    public void setVariable(
+            String key,
+            Object value,
+            Variable.Scope scope,
+            ControllerState controllerState)
+    {
+        QualifiedName qualifiedName
+                = controllerState.getQualifiedName(key);
+        Variable variable
+                = new Variable(
+                        qualifiedName,
+                        value,
+                        scope);
+        VariableStore variableStore = controllerState.getVariableStore();
+        variableStore.set(variable);
+    }
+    /**
+     * Returns the variable with the given key. The key can either be a name
+     * prefixed with a namespace, or a name without namespace, in which case
+     * the namespace of the generator is used.
+     *
+     * In the case that the variable is not set in this namespace, the parent
+     * namespaces are searched recursively.  If the variable is not set in any
+     * of the parent namespaces, null is returned.
+     *
+     * @param key the key for the variable to retrieve.
+     * @param controllerState the context of the controller, not null.
+     *
+     * @return the variable for the given key, or null if the variable is not
+     *         set or explicitly set to null.
+     */
+    public Object getVariable(String key, ControllerState controllerState)
+    {
+        QualifiedName qualifiedName
+                = controllerState.getQualifiedName(key);
+        VariableStore variableStore = controllerState.getVariableStore();
+        Variable variable = variableStore.getInHierarchy(qualifiedName);
+
+        Object value = null;
+        if (variable != null)
+        {
+            value = variable.getValue();
+        }
+
+        return value;
+    }
+
+    /**
+     * Processes the mergepoint with the given name.
+     *
+     * @param mergepointName the name of the mergepoint.
+     * @param controllerState the context of the controller, not null.
+     *
+     * @return the output generated by the mergepoint.
+     *
+     * @throws GeneratorException if the mergepoint could not be processed
+     *         completely.
+     */
+    public String mergepoint(
+            String mergepointName,
+            ControllerState controllerState)
+        throws GeneratorException
+    {
+        if (log.isDebugEnabled())
+        {
+            log.debug("mergepoint() : Start for mergepoint " + mergepointName);
+        }
+        MergepointMapping mergepointMapping
+                = controllerState.getGenerator().getMergepointMapping(
+                            mergepointName);
+        if (mergepointMapping == null)
+        {
+            if (log.isInfoEnabled())
+            {
+                log.info("mergepoint() : End. Mapping "
+                        + mergepointName
+                        + " not found in generator "
+                        + getName()
+                        + ", returning the empty String");
+            }
+            return "";
+        }
+        List<MergepointAction> actions = mergepointMapping.getActions();
+        if (actions.isEmpty())
+        {
+            log.debug("No actions specified for action mapping with name "
+                    + mergepointName
+                    + " in generator "
+                    + controllerState.getGenerator().getName()
+                    + " while generating to "
+                    + controllerState.getOutputFile()
+                    + " Returning the empty String.");
+            return "";
+        }
+        StringBuffer result = new StringBuffer();
+        for (MergepointAction action : actions)
+        {
+            if (log.isDebugEnabled())
+            {
+                log.debug("mergepoint() : Executing action " + action);
+            }
+
+            // velocity does not chain exceptions, so catch and log exceptions
+            // here
+            try
+            {
+                result.append(action.execute(controllerState));
+            }
+            catch (GeneratorException e)
+            {
+                log.error("mergepoint() : Error executing action " + action, e);
+                throw e;
+            }
+            catch (RuntimeException e)
+            {
+                log.error("mergepoint() : Error executing action " + action, e);
+                throw e;
+            }
+
+
+            if (log.isDebugEnabled())
+            {
+                log.debug("mergepoint() : End for mergepoint "
+                        + mergepointName);
+            }
+        }
+        return result.toString();
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Mergepoint.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Mergepoint.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Mergepoint.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/Mergepoint.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,72 @@
+package org.apache.torque.gf.generator;
+
+/*
+ * 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.
+ */
+
+/**
+ * An merge point where the output of another generator can be merged
+ * into the text generated by a generator.
+ */
+public class Mergepoint
+{
+    /**
+     * The name of the merge point.
+     */
+    private String name;
+
+    /**
+     * Constructor.
+     *
+     * @param name the name of the merge point, not null.
+     *
+     * @throws NullPointerException if the name is null.
+     */
+    public Mergepoint(String name)
+    {
+        if (name == null)
+        {
+            throw new NullPointerException("name must not be null");
+        }
+        this.name = name;
+    }
+
+    /**
+     * Returns the name of the merge point.
+     *
+     * @return the name of the merge point, never null.
+     */
+    public String getName()
+    {
+        return name;
+    }
+
+    /**
+     * Returns a String representation of the Mergepoint for debugging purposes.
+     *
+     * @return a String representation of the Mergepoint.
+     * @see Object#toString()
+     */
+    @Override
+    public String toString()
+    {
+        StringBuffer result = new StringBuffer();
+        result.append(name);
+        return result.toString();
+    }
+}

Added: db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/java/CamelbackGenerator.java
URL: http://svn.apache.org/viewvc/db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/java/CamelbackGenerator.java?rev=910600&view=auto
==============================================================================
--- db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/java/CamelbackGenerator.java (added)
+++ db/torque/torque4/trunk/torque-generator/src/main/java/org/apache/torque/gf/generator/java/CamelbackGenerator.java Tue Feb 16 17:15:43 2010
@@ -0,0 +1,199 @@
+package org.apache.torque.gf.generator.java;
+
+/*
+ * 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.
+ */
+
+import org.apache.torque.gf.control.ControllerState;
+import org.apache.torque.gf.generator.GeneratorException;
+import org.apache.torque.gf.processor.string.Camelbacker;
+import org.apache.torque.gf.processor.string.WrapReservedJavaWords;
+import org.apache.torque.gf.qname.QualifiedName;
+
+/**
+ * Transform a String to its camelback version. This is typically
+ * useful when creating java class or attribute names.
+ *
+ * The name can be truncated before/after special characters, other
+ * special characters can be removed, and still other characters can be removed
+ * plus the next character is transformed into upper case.
+ */
+public class CamelbackGenerator extends StringInputGenerator
+{
+    /**
+     * The processor which does the camelback processing.
+     */
+    private Camelbacker camelbacker = new Camelbacker();
+
+    /**
+     * The processor which wraps reserved java words.
+     */
+    private WrapReservedJavaWords reservedWordsWrapper
+        = new WrapReservedJavaWords();
+
+    /** Whether reserved java words are wrapped. */
+    private boolean wrapReservedJavaWords = true;
+
+    /**
+     * Constructor.
+     *
+     * @param qualifiedName the unique name of the generator, not null.
+     */
+    public CamelbackGenerator(QualifiedName qualifiedName)
+    {
+        super(qualifiedName);
+    }
+
+    /**
+     * Sets which characters are removed from the processed String.
+     * Default is "."
+     *
+     * @param removeWithoutUppercase a String containing all characters
+     *        which are simply removed from the input String.
+     */
+    public void setRemoveWithoutUppercase(String removeWithoutUppercase)
+    {
+        camelbacker.setRemoveWithoutUppercase(removeWithoutUppercase);
+    }
+
+    /**
+     * Sets the characters which are removed from the processed String
+     * and cause the following character to be converted to upper case.
+     * Default is "_-"
+     *
+     * @param removeWithUppercase a String containing all characters which are
+     *        removed from the input String and which cause the following
+     *        character to be converted to upper case.
+     */
+    public void setRemoveWithUppercase(String removeWithUppercase)
+    {
+        camelbacker.setRemoveWithUppercase(removeWithUppercase);
+    }
+
+    /**
+     * Sets whether all characters in the processed String should be made
+     * lower Case by default (i.e if none of the camelback rules is applicable).
+     * Default is true.
+     *
+     * @param defaultLowerCase true if all characters are converted to lower
+     *        case by default, false if not.
+     */
+    public void setDefaultLowerCase(boolean defaultLowerCase)
+    {
+        camelbacker.setDefaultLowerCase(defaultLowerCase);
+    }
+
+    /**
+     * Sets the separation characters which define the prefix to be removed.
+     * If one of the characters in this String
+     * is encountered in the processed String, the  part of the processed
+     * String before it are ignored. The character itself is retained,
+     * unless it is removed by another rule.
+     *
+     * @param ignorePartBefore the separation chars which define the suffix
+     *        to be removed.
+     */
+    public void setIgnorePartBefore(String ignorePartBefore)
+    {
+        camelbacker.setIgnorePartBefore(ignorePartBefore);
+    }
+
+    /**
+     * Sets the separation chars which define the suffix to be removed.
+     * If one of the characters in this String
+     * is encountered in the processed String, the part of the processed
+     * String after it are ignored. The character itself is retained,
+     * unless it is removed by another rule.
+     *
+     * @param ignorePartAfter the separation chars for removing the tail.
+     */
+    public void setIgnorePartAfter(String ignorePartAfter)
+    {
+        camelbacker.setIgnorePartBefore(ignorePartAfter);
+    }
+
+    /**
+     * Sets whether the first character should always be upper case.
+     * Default is true.
+     *
+     * @param firstCharUppercase true if the first character should always
+     *        be converted to upper case, false if not.
+     */
+    public void setFirstCharUppercase(boolean firstCharUppercase)
+    {
+        camelbacker.setFirstCharUppercase(firstCharUppercase);
+    }
+
+    /**
+     * Sets whether reserved java words (as output of the camelbacker)
+     * are wrapped (prepended or appended).
+     * Default is true.
+     *
+     * @param wrapReservedJavaWords true if reserved java words should be
+     *        wrapped, false if not.
+     */
+    public void setWrapReservedJavaWords(boolean wrapReservedJavaWords)
+    {
+        this.wrapReservedJavaWords = wrapReservedJavaWords;
+    }
+
+    /**
+     * Sets the prefix which is prepended to reserved java words.
+     * Default is "_".
+     *
+     * @param prefix the new prefix, not null.
+     */
+    public void setReservedJavaWordsPrefix(String prefix)
+    {
+
+        this.reservedWordsWrapper.setPrependWhenReserved(prefix);
+    }
+
+    /**
+     * Sets the suffix which is prepended to reserved java words.
+     * Default is the empty String.
+     *
+     * @param suffix the new suffix, not null.
+     */
+    public void setReservedJavaWordsSuffix(String suffix)
+    {
+
+        this.reservedWordsWrapper.setAppendWhenReserved(suffix);
+    }
+
+    /**
+     * Processes the input according to the camelback rules.
+     *
+     * @param controllerState the current state of the controller, not null.
+     *
+     * @throws GeneratorException in processing fails.
+     */
+    @Override
+    public String execute(ControllerState controllerState)
+            throws GeneratorException
+    {
+        String classnameInput = getInput(controllerState);
+
+        String result = camelbacker.process(classnameInput);
+        if (wrapReservedJavaWords)
+        {
+            result = reservedWordsWrapper.process(result);
+        }
+        return result;
+    }
+}



---------------------------------------------------------------------
To unsubscribe, e-mail: torque-dev-unsubscribe@db.apache.org
For additional commands, e-mail: torque-dev-help@db.apache.org


Mime
View raw message