001: /*
002: * Licensed to the Apache Software Foundation (ASF) under one or more
003: * contributor license agreements. See the NOTICE file distributed with
004: * this work for additional information regarding copyright ownership.
005: * The ASF licenses this file to You under the Apache License, Version 2.0
006: * (the "License"); you may not use this file except in compliance with
007: * the License. You may obtain a copy of the License at
008: *
009: * http://www.apache.org/licenses/LICENSE-2.0
010: *
011: * Unless required by applicable law or agreed to in writing, software
012: * distributed under the License is distributed on an "AS IS" BASIS,
013: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014: * See the License for the specific language governing permissions and
015: * limitations under the License.
016: */
017: package org.apache.cocoon.template.instruction;
018:
019: import java.io.ByteArrayInputStream;
020: import java.util.Stack;
021:
022: import org.apache.avalon.framework.service.ServiceManager;
023: import org.apache.cocoon.components.expression.ExpressionContext;
024: import org.apache.cocoon.template.environment.ExecutionContext;
025: import org.apache.cocoon.template.environment.ParsingContext;
026: import org.apache.cocoon.template.expression.JXTExpression;
027: import org.apache.cocoon.template.script.Invoker;
028: import org.apache.cocoon.template.script.event.Event;
029: import org.apache.cocoon.template.script.event.StartElement;
030: import org.apache.cocoon.xml.IncludeXMLConsumer;
031: import org.apache.cocoon.xml.XMLConsumer;
032: import org.apache.commons.lang.BooleanUtils;
033: import org.apache.excalibur.xml.sax.SAXParser;
034: import org.apache.excalibur.xml.sax.XMLizable;
035: import org.w3c.dom.Node;
036: import org.xml.sax.Attributes;
037: import org.xml.sax.InputSource;
038: import org.xml.sax.Locator;
039: import org.xml.sax.SAXException;
040: import org.xml.sax.SAXParseException;
041:
042: /**
043: * @version SVN $Id: Out.java 449189 2006-09-23 06:52:29Z crossley $
044: */
045: public class Out extends Instruction {
046: private final JXTExpression compiledExpression;
047: private Boolean xmlize;
048: private Boolean stripRoot;
049:
050: public Out(ParsingContext parsingContext, StartElement raw,
051: Attributes attrs, Stack stack) throws SAXException {
052:
053: super (raw);
054: Locator locator = getLocation();
055: String value = attrs.getValue("value");
056: if (value == null)
057: throw new SAXParseException("out: \"value\" is required",
058: locator, null);
059:
060: this .compiledExpression = parsingContext
061: .getStringTemplateParser().compileExpr(value,
062: "out: \"value\": ", locator);
063: String lenientValue = attrs.getValue("lenient");
064: Boolean lenient = lenientValue == null ? null : Boolean
065: .valueOf(lenientValue);
066:
067: // Why can out be lenient?
068: if (lenient != null)
069: this .compiledExpression.setLenient(lenient);
070:
071: String xmlize = attrs.getValue("xmlize");
072: this .xmlize = (xmlize == null) ? null : Boolean.valueOf(xmlize);
073:
074: String stripRoot = attrs.getValue("strip-root");
075: this .stripRoot = (stripRoot == null) ? null : Boolean
076: .valueOf(stripRoot);
077: }
078:
079: public Event execute(final XMLConsumer consumer,
080: ExpressionContext expressionContext,
081: ExecutionContext executionContext,
082: MacroContext macroContext, Event startEvent, Event endEvent)
083: throws SAXException {
084: Object val;
085: try {
086: val = this .compiledExpression.getNode(expressionContext);
087:
088: boolean stripRoot = BooleanUtils.toBoolean(this .stripRoot);
089: //TODO: LG, I do not see a good way to do this.
090: if (BooleanUtils.isTrue(this .xmlize)) {
091: if (val instanceof Node || val instanceof Node[]
092: || val instanceof XMLizable)
093: Invoker.executeNode(consumer, val, stripRoot);
094: else {
095: ServiceManager serviceManager = executionContext
096: .getServiceManager();
097: SAXParser parser = null;
098: try {
099: parser = (SAXParser) serviceManager
100: .lookup(SAXParser.ROLE);
101: InputSource source = new InputSource(
102: new ByteArrayInputStream(val.toString()
103: .getBytes()));
104: IncludeXMLConsumer includeConsumer = new IncludeXMLConsumer(
105: consumer);
106: includeConsumer.setIgnoreRootElement(stripRoot);
107: parser.parse(source, includeConsumer);
108: } finally {
109: serviceManager.release(parser);
110: }
111: }
112: } else
113: Invoker.executeNode(consumer, val, stripRoot);
114: } catch (Exception e) {
115: throw new SAXParseException(e.getMessage(), getLocation(),
116: e);
117: }
118: return getNext();
119: }
120: }
|