/*
 * 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.chain2.config.xml;

import org.apache.commons.chain2.CatalogFactory;
import org.apache.commons.chain2.config.ChainConfigurationException;
import org.apache.commons.chain2.config.ConfigParser;
import org.apache.commons.chain2.impl.CatalogFactoryBase;
import org.apache.commons.digester3.Digester;
import org.apache.commons.digester3.RuleSet;

import java.net.URL;
import java.util.Map;

/**
 * <p>Class to parse the contents of an XML configuration file (using
 * Commons Digester) that defines and configures commands and command chains
 * to be registered in a {@link org.apache.commons.chain2.Catalog}.  Advanced users can configure the
 * detailed parsing behavior by configuring the properties of an instance
 * of this class prior to calling the <code>parse()</code> method.  It
 * is legal to call the <code>parse()</code> method more than once, in order
 * to parse more than one configuration document.</p>
 *
 * @version $Id: ConfigParser.java 1364104 2012-07-21 14:25:54Z elijah $
 */
public class XmlConfigParser implements ConfigParser {
    // ----------------------------------------------------- Instance Variables

    /**
     * <p>The <code>RuleSet</code> to be used for configuring our Digester
     * parsing rules.</p>
     */
    private RuleSet ruleSet = new ConfigRuleSet();

    /**
     * <p>Should Digester use the context class loader?
     */
    private boolean useContextClassLoader = true;

    // ------------------------------------------------------------- Constructor

    public XmlConfigParser() {
    }

    public XmlConfigParser(String ruleSet, ClassLoader loader) {
        if (ruleSet == null) {
            throw new IllegalArgumentException("ConfigParser can't be " +
                    "instantiated with a null ruleSet class name");
        }
        if (loader == null) {
            throw new IllegalArgumentException("ConfigParser can't be " +
                    "instantiated with a null class loader reference");
        }

        try {
            Class<?> clazz = loader.loadClass(ruleSet);
            setRuleSet((RuleSet) clazz.newInstance());
        } catch (Exception e) {
            throw new RuntimeException("Exception initializing RuleSet '"
                    + ruleSet + "' instance: "
                    + e.getMessage());
        }
    }

    // ------------------------------------------------------------- Properties

    /**
     * <p>Return the <code>Digester</code> instance to be used for
     * parsing, creating one if necessary.</p>
     * @return A Digester instance.
     */
    public Digester getDigester() {
        Digester digester = new Digester();
        RuleSet ruleSet = getRuleSet();
        digester.setNamespaceAware(ruleSet.getNamespaceURI() != null);
        digester.setUseContextClassLoader(getUseContextClassLoader());
        digester.setValidating(false);
        digester.addRuleSet(ruleSet);
        return digester;
    }

    /**
     * <p>Return the <code>RuleSet</code> to be used for configuring
     * our <code>Digester</code> parsing rules, creating one if necessary.</p>
     * @return The RuleSet for configuring a Digester instance.
     */
    public RuleSet getRuleSet() {
        return ruleSet;
    }

    /**
     * <p>Set the <code>RuleSet</code> to be used for configuring
     * our <code>Digester</code> parsing rules.</p>
     *
     * @param ruleSet The new RuleSet to use
     */
    public void setRuleSet(RuleSet ruleSet) {
        this.ruleSet = ruleSet;
    }

    /**
     * <p>Return the "use context class loader" flag.  If set to
     * <code>true</code>, Digester will attempt to instantiate new
     * command and chain instances from the context class loader.</p>
     * @return <code>true</code> if Digester should use the context class loader.
     */
    public boolean getUseContextClassLoader() {
        return this.useContextClassLoader;
    }

    /**
     * <p>Set the "use context class loader" flag.</p>
     *
     * @param useContextClassLoader The new flag value
     */
    public void setUseContextClassLoader(boolean useContextClassLoader) {
        this.useContextClassLoader = useContextClassLoader;
    }

    // --------------------------------------------------------- Public Methods

    /**
     * <p>Parse the XML document at the specified URL using the configured
     * <code>RuleSet</code>, registering catalogs with nested chains and
     * commands as they are encountered.  Use this method <strong>only</strong>
     * if you have included one or more <code>factory</code> elements in your
     * configuration resource.</p>
     *
     * @param <K> the type of keys maintained by the context associated with this command
     * @param <V> the type of mapped values
     * @param <C> Type of the context associated with this command
     * @param url <code>URL</code> of the XML document to be parsed
     * @return a CatalogFactory instance parsed from the given location
     * @throws ChainConfigurationException if a parsing error occurs
     */
    public <K, V, C extends Map<K, V>> CatalogFactory<K, V, C> parse(URL url) {
        // Prepare our Digester instance
        Digester digester = getDigester();
        digester.clear();

        // Parse the configuration document
        try {
            digester.parse(url);
        } catch (Exception e) {
            String msg = String.format(
                    "Error parsing digester configuration at url: %s",
                    url);
            throw new ChainConfigurationException(msg, e);
        }
        // FIXME get rid of singleton pattern and create a new instance here
        return CatalogFactoryBase.getInstance();
    }

}
