View Javadoc

    1   /*
    2    * Copyright 2002,2004 The Apache Software Foundation.
    3    *
    4    * Licensed under the Apache License, Version 2.0 (the "License");
    5    * you may not use this file except in compliance with the License.
    6    * You may obtain a copy of the License at
    7    *
    8    *      http://www.apache.org/licenses/LICENSE-2.0
    9    *
    10   * Unless required by applicable law or agreed to in writing, software
    11   * distributed under the License is distributed on an "AS IS" BASIS,
    12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13   * See the License for the specific language governing permissions and
    14   * limitations under the License.
    15   */
    16  package org.apache.commons.jelly.tags.core;
    17
    18  import java.io.StringReader;
    19
    20  import javax.xml.parsers.ParserConfigurationException;
    21  import javax.xml.parsers.SAXParser;
    22  import javax.xml.parsers.SAXParserFactory;
    23
    24  import org.apache.commons.jelly.JellyTagException;
    25  import org.apache.commons.jelly.MissingAttributeException;
    26  import org.apache.commons.jelly.Script;
    27  import org.apache.commons.jelly.TagSupport;
    28  import org.apache.commons.jelly.XMLOutput;
    29  import org.apache.commons.jelly.parser.XMLParser;
    30  import org.apache.commons.logging.Log;
    31  import org.apache.commons.logging.LogFactory;
    32  import org.xml.sax.ContentHandler;
    33  import org.xml.sax.InputSource;
    34  import org.xml.sax.SAXException;
    35  import org.xml.sax.XMLReader;
    36
    37  /***
    38   * Parses the output of this tags body or of a given String as a Jelly script
    39   * then either outputting the Script as a variable or executing the script.
    40   *
    41   * @author <a href="mailto:jstrachan@apache.org">James Strachan</a>
    42   * @version $Revision: 155420 $
    43   */
    44  public class ParseTag extends TagSupport {
    45
    46      /*** The Log to which logging calls will be made. */
    47      private static final Log log = LogFactory.getLog(ParseTag.class);
    48
    49      /*** The variable that will be generated for the document */
    50      private String var;
    51
    52      /*** The markup text to be parsed */
    53      private String text;
    54
    55      /*** The XMLReader used to parser the document */
    56      private XMLReader xmlReader;
    57
    58      /*** The Jelly parser */
    59      private XMLParser jellyParser;
    60
    61      public ParseTag() {
    62      }
    63
    64      // Tag interface
    65      //-------------------------------------------------------------------------
    66
    67      /* (non-Javadoc)
    68       * @see org.apache.commons.jelly.Tag#doTag(org.apache.commons.jelly.XMLOutput)
    69       */
    70      public void doTag(XMLOutput output)
    71          throws MissingAttributeException, JellyTagException {
    72
    73          String text = getText();
    74          if (text != null) {
    75              parseText(text);
    76          }
    77          else {
    78              parseBody(output);
    79          }
    80
    81          Script script = getJellyParser().getScript();
    82          if (var != null) {
    83              context.setVariable(var, script);
    84          }
    85          else {
    86              // invoke the script
    87              script.run(context, output);
    88          }
    89      }
    90
    91      // Properties
    92      //-------------------------------------------------------------------------
    93      /*** The variable name that will be used for the Document variable created
    94       */
    95      public String getVar() {
    96          return var;
    97      }
    98
    99      /*** Sets the variable name that will be used for the Document variable created
    100      */
    101     public void setVar(String var) {
    102         this.var = var;
    103     }
    104
    105     /***
    106      * Returns the text to be parsed
    107      * @return String
    108      */
    109     public String getText() {
    110         return text;
    111     }
    112
    113     /***
    114      * Sets the text to be parsed by this parser
    115      * @param text The text to be parsed by this parser
    116      */
    117     public void setText(String text) {
    118         this.text = text;
    119     }
    120
    121
    122     /*** @return the XMLReader used for parsing, creating one lazily if need be  */
    123     public XMLReader getXMLReader() throws ParserConfigurationException, SAXException {
    124         if (xmlReader == null) {
    125             xmlReader = createXMLReader();
    126         }
    127         return xmlReader;
    128     }
    129
    130     /*** Sets the XMLReader used for parsing */
    131     public void setXMLReader(XMLReader xmlReader) {
    132         this.xmlReader = xmlReader;
    133     }
    134
    135
    136     /***
    137      * @return XMLParser
    138      */
    139     public XMLParser getJellyParser() {
    140         if (jellyParser == null) {
    141             jellyParser = createJellyParser();
    142         }
    143         return jellyParser;
    144     }
    145
    146     /***
    147      * Sets the jellyParser.
    148      * @param jellyParser The jellyParser to set
    149      */
    150     public void setJellyParser(XMLParser jellyParser) {
    151         this.jellyParser = jellyParser;
    152     }
    153
    154
    155     // Implementation methods
    156     //-------------------------------------------------------------------------
    157
    158     /***
    159      * Factory method to create a new XMLReader
    160      */
    161     protected XMLReader createXMLReader() throws ParserConfigurationException, SAXException {
    162         SAXParserFactory factory = SAXParserFactory.newInstance();
    163         factory.setNamespaceAware(true);
    164         SAXParser parser = factory.newSAXParser();
    165         return parser.getXMLReader();
    166     }
    167
    168
    169     /***
    170      * Parses the body of this tag and returns the parsed document
    171      */
    172     protected void parseBody(XMLOutput output) throws JellyTagException {
    173         ContentHandler handler = getJellyParser();
    174         XMLOutput newOutput = new XMLOutput(handler);
    175
    176         try {
    177             handler.startDocument();
    178             invokeBody(newOutput);
    179             handler.endDocument();
    180         }
    181         catch (SAXException e) {
    182             throw new JellyTagException(e);
    183         }
    184     }
    185
    186     /***
    187      * Parses the give piece of text as being markup
    188      */
    189     protected void parseText(String text) throws JellyTagException {
    190         if ( log.isDebugEnabled() ) {
    191             log.debug( "About to parse: " + text );
    192         }
    193
    194         try {
    195             getXMLReader().parse( new InputSource( new StringReader( text ) ) );
    196         }
    197         catch (Exception e) {
    198             throw new JellyTagException(e);
    199         }
    200     }
    201
    202     /***
    203      * Factory method to create a new Jelly parser
    204      * @return XMLParser
    205      */
    206     protected XMLParser createJellyParser() {
    207         XMLParser answer = new XMLParser();
    208         answer.setContext(context);
    209         return answer;
    210     }
    211 }