/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.apache.commons.jelly;

import java.io.FileInputStream;
import java.io.InputStream;
import java.io.StringWriter;

import junit.framework.Test;
import junit.framework.TestCase;
import junit.framework.TestSuite;
import junit.textui.TestRunner;

import org.apache.commons.jelly.impl.TextScript;
import org.apache.commons.jelly.parser.XMLParser;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

/** Tests the core tags
  *
  * @author <a href="mailto:jstrachan@apache.org">James Strachan</a>
  * @version $Revision$
  */
public class TestCoreTags extends TestCase {

    /** The Log to which logging calls will be made. */
    private static final Log log = LogFactory.getLog(TestCoreTags.class);

    public static void main(String[] args) {
        TestRunner.run(suite());
    }

    public static Test suite() {
        return new TestSuite(TestCoreTags.class);
    }

    public TestCoreTags(String testName) {
        super(testName);
    }

    public void testArgs() throws Exception {
        InputStream in = new FileInputStream("src/test/org/apache/commons/jelly/test_args.jelly");
        XMLParser parser = new XMLParser();
        Script script = parser.parse(in);
        script = script.compile();
        log.debug("Found: " + script);
        String[] args = { "one", "two", "three" };
        JellyContext context = new JellyContext();
        context.setVariable("args", args);
        StringWriter buffer = new StringWriter();
        script.run(context, XMLOutput.createXMLOutput(buffer));
        String text = buffer.toString().trim();
        if (log.isDebugEnabled()) {
            log.debug("Evaluated script as...");
            log.debug(text);
        }
        assertEquals("Produces the correct output", "one two three", text);
    }

    public void testTrimEndWhitespace() throws Exception {
        TextScript textScript = new TextScript(" ");
        textScript.trimEndWhitespace();
        assertEquals("", textScript.getText());

        textScript = new TextScript("");
        textScript.trimEndWhitespace();
        assertEquals("", textScript.getText());

        textScript = new TextScript(" foo ");
        textScript.trimEndWhitespace();
        assertEquals(" foo", textScript.getText());

        textScript = new TextScript("foo");
        textScript.trimEndWhitespace();
        assertEquals("foo", textScript.getText());
    }

    public void testTrimStartWhitespace() throws Exception {
        TextScript textScript = new TextScript(" ");
        textScript.trimStartWhitespace();
        assertEquals("", textScript.getText());

        textScript = new TextScript("");
        textScript.trimStartWhitespace();
        assertEquals("", textScript.getText());

        textScript = new TextScript(" foo ");
        textScript.trimStartWhitespace();
        assertEquals("foo ", textScript.getText());

        textScript = new TextScript("foo");
        textScript.trimStartWhitespace();
        assertEquals("foo", textScript.getText());
    }


    public void testStaticNamespacedAttributes() throws Exception {
        InputStream in = new FileInputStream("src/test/org/apache/commons/jelly/testStaticNamespacedAttributes.jelly");
        XMLParser parser = new XMLParser();
        Script script = parser.parse(in);
        script = script.compile();
        log.debug("Found: " + script);
        JellyContext context = new JellyContext();
        StringWriter buffer = new StringWriter();
        script.run(context, XMLOutput.createXMLOutput(buffer));
        String text = buffer.toString().trim();
        if (log.isDebugEnabled()) {
            log.debug("Evaluated script as...");
            log.debug(text);
        }
        assertEquals("Should produces the correct output",
                "<blip xmlns:blop=\"blop\" blop:x=\"blip\"></blip>",
                text);
    }
}
