001    package org.apache.commons.digester3.substitution;
002    
003    /*
004     * Licensed to the Apache Software Foundation (ASF) under one
005     * or more contributor license agreements.  See the NOTICE file
006     * distributed with this work for additional information
007     * regarding copyright ownership.  The ASF licenses this file
008     * to you under the Apache License, Version 2.0 (the
009     * "License"); you may not use this file except in compliance
010     * with the License.  You may obtain a copy of the License at
011     *
012     *   http://www.apache.org/licenses/LICENSE-2.0
013     *
014     * Unless required by applicable law or agreed to in writing,
015     * software distributed under the License is distributed on an
016     * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
017     * KIND, either express or implied.  See the License for the
018     * specific language governing permissions and limitations
019     * under the License.
020     */
021    
022    import org.apache.commons.digester3.Substitutor;
023    
024    import org.xml.sax.Attributes;
025    
026    /**
027     * Substitutor implementation that support variable replacement for both attributes and body text. The actual expansion
028     * of variables into text is delegated to {@link VariableExpander} implementations. Supports setting an expander just
029     * for body text or just for attributes. Also supported is setting no expanders for body text and for attributes.
030     * 
031     * @since 1.6
032     */
033    public class VariableSubstitutor
034        extends Substitutor
035    {
036    
037        /**
038         * The expander to be used to expand variables in the attributes. Null when no expansion should be performed.
039         */
040        private final VariableExpander attributesExpander;
041    
042        /**
043         * Attributes implementation that (lazily) performs variable substitution. Will be lazily created when needed then
044         * reused.
045         */
046        private final VariableAttributes variableAttributes;
047    
048        /**
049         * The expander to be used to expand variables in the body text. Null when no expansion should be performed.
050         */
051        private final VariableExpander bodyTextExpander;
052    
053        /**
054         * Constructs a Substitutor which uses the same VariableExpander for both body text and attibutes.
055         * 
056         * @param expander VariableExpander implementation, null if no substitutions are to be performed
057         */
058        public VariableSubstitutor( VariableExpander expander )
059        {
060            this( expander, expander );
061        }
062    
063        /**
064         * Constructs a Substitutor.
065         * 
066         * @param attributesExpander VariableExpander implementation to be used for attributes, null if no attribute
067         *            substitutions are to be performed
068         * @param bodyTextExpander VariableExpander implementation to be used for bodyTextExpander, null if no attribute
069         *            substitutions are to be performed
070         */
071        public VariableSubstitutor( VariableExpander attributesExpander, VariableExpander bodyTextExpander )
072        {
073            this.attributesExpander = attributesExpander;
074            this.bodyTextExpander = bodyTextExpander;
075            variableAttributes = new VariableAttributes();
076        }
077    
078        /**
079         * {@inheritDoc}
080         */
081        @Override
082        public Attributes substitute( Attributes attributes )
083        {
084            Attributes results = attributes;
085            if ( attributesExpander != null )
086            {
087                variableAttributes.init( attributes, attributesExpander );
088                results = variableAttributes;
089            }
090            return results;
091        }
092    
093        /**
094         * {@inheritDoc}
095         */
096        @Override
097        public String substitute( String bodyText )
098        {
099            String result = bodyText;
100            if ( bodyTextExpander != null )
101            {
102                result = bodyTextExpander.expand( bodyText );
103            }
104            return result;
105        }
106    
107    }