/*
 * 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.lenya.modules.metadata;

import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.apache.avalon.framework.parameters.Parameters;
import org.apache.cocoon.ProcessingException;
import org.apache.cocoon.environment.ObjectModelHelper;
import org.apache.cocoon.environment.Request;
import org.apache.cocoon.environment.SourceResolver;
import org.apache.cocoon.transformation.AbstractSAXTransformer;
import org.apache.lenya.cms.metadata.MetaData;
import org.apache.lenya.cms.publication.Area;
import org.apache.lenya.cms.publication.Document;
import org.apache.lenya.cms.publication.Publication;
import org.apache.lenya.cms.publication.Repository;
import org.apache.lenya.cms.publication.Session;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.AttributesImpl;

/**
 * <p>
 * Meta data transformer.
 * </p>
 * <p>
 * Usage example:
 * </p>
 * 
 * <pre>
 * &lt;meta:value xmlns:meta=&quot;http://apache.org/lenya/meta/1.0/&quot;
 *   element=&quot;title&quot;
 *   ns=&quot;http://purl.org/dc/elements/1.1/&quot;
 *   uuid=&quot;{$uuid}&quot;
 *   lang=&quot;{$language}&quot;
 *   default=&quot;default-title&quot;
 *   i18n:attr=&quot;default&quot; /&gt;
 * </pre>
 * <p>
 * The attribute <em>default</em> is optional.
 * </p>
 */
public class MetaDataTransformer extends AbstractSAXTransformer {
    /**
     * The namespace for the meta data is http://apache.org/lenya/meta/1.0
     */
    static public final String NAMESPACE_URI = "http://apache.org/lenya/meta/1.0/";

    /**
     * The namespace prefix for this namespace.
     */
    static public final String PREFIX = "meta";

    /**
     * The value element is getting the value for a specific ns and key. It is the only method
     * implemented so far.
     */
    static public final String VALUE_ELEMENT = "value";

    /**
     * ELEMENT_ATT - which meta data key do we want to look up
     */
    static public final String ELEMENT_ATT = "element";

    /**
     * NS_ATT - in which namespace should we look
     */
    static public final String NS_ATT = "ns";

    /**
     * UUID_ATT - for which uuid?
     */
    static public final String UUID_ATT = "uuid";

    /**
     * LANG_ATT - in which language this is optional (when not found use publication default)
     */
    static public final String LANG_ATT = "lang";

    /**
     * Use this attribute to provide a default value to be used if the document doesn't exist.
     */
    static public final String DEFAULT_ATT = "default";

    /** Helper for lenya document retrival */
    protected String publicationId = null;
    protected String area = null;
    protected String language = null;
    protected String uuid = null;
    protected Publication pub;
    protected Repository repository;

    /**
     * Setup the MetaDataTransformer.
     */
    public void setup(SourceResolver resolver, Map objectModel, String src, Parameters par)
            throws ProcessingException, SAXException, IOException {
        super.setup(resolver, objectModel, src, par);
        this.publicationId = par.getParameter("pubid", null);
        if (this.publicationId == null) {
            throw new ProcessingException(
                    "The pubid is not set! Please set like e.g. <map:parameter name='pubid' value='{request-param:pubid}'/>");
        }

        this.area = par.getParameter("area", null);
        if (this.area == null) {
            throw new ProcessingException(
                    "The area is not set! Please set like e.g. <map:parameter name='area' value='{request-param:area}'/>");
        }
        Request request = ObjectModelHelper.getRequest(objectModel);
        try {
            Session session = this.repository.getSession(request);
            pub = session.getPublication(this.publicationId);
        } catch (Exception e) {
            throw new ProcessingException("Error geting publication id / area from page envelope",
                    e);
        }
    }

    public void startElement(String uri, String name, String raw, Attributes attr)
            throws SAXException {
        if (NAMESPACE_URI.equals(uri)) {
            if (VALUE_ELEMENT.equals(name)) {
                String lang = null, uuid = null, ns = null, key = null, defaultValue = null;
                for (int i = 0; i < attr.getLength(); i++) {
                    String localName = attr.getLocalName(i);
                    String value = attr.getValue(i);
                    if (ELEMENT_ATT.equals(localName))
                        key = value;
                    else if (NS_ATT.equals(localName))
                        ns = value;
                    else if (UUID_ATT.equals(localName))
                        uuid = value;
                    else if (LANG_ATT.equals(localName))
                        lang = value;
                    else if (DEFAULT_ATT.equals(localName))
                        defaultValue = value;
                }// end for
                if (uuid == null || ns == null || key == null)
                    throw new SAXException(
                            "Error by setting up the transformation. Please fix the calling code.");
                if (lang == null)
                    lang = pub.getDefaultLanguage();
                List returnValues = new ArrayList();
                try {
                    Area areaObj = pub.getArea(this.area);
                    if (areaObj.contains(uuid, lang)) {
                        Document document = areaObj.getDocument(uuid, lang);
                        MetaData metaData = document.getMetaData(ns);
                        returnValues.addAll(Arrays.asList(metaData.getValues(key)));
                    } else if (defaultValue != null) {
                        returnValues.add(defaultValue);
                    } else {
                        String doc = this.publicationId + ":" + this.area + ":" + uuid + ":" + lang;
                        throw new SAXException("The document [" + doc
                                + "] does not exist and no default value is provided.");
                    }
                } catch (Exception e) {
                    throw new SAXException(e);
                }
                if (returnValues.size() > 1) {
                    for (Iterator i = returnValues.iterator(); i.hasNext();) {
                        String value = (String) i.next();
                        AttributesImpl attributes = new AttributesImpl();
                        attributes.addAttribute("", VALUE_ELEMENT, VALUE_ELEMENT, "CDATA", value);
                        attributes.addAttribute("", ELEMENT_ATT, ELEMENT_ATT, "CDATA", key);
                        this.contentHandler.startElement(ns, VALUE_ELEMENT, PREFIX + ":"
                                + VALUE_ELEMENT, attributes);
                        this.contentHandler.endElement(ns, VALUE_ELEMENT, PREFIX + ":"
                                + VALUE_ELEMENT);
                    }
                } else if (returnValues.size() == 1) {
                    String value = (String) returnValues.get(0);
                    this.contentHandler.characters(value.toCharArray(), 0,
                            value.toCharArray().length);
                }

            } else {
                String warn = "Could not find method for " + name + ". Ignoring.";
                getLogger().warn(warn);
            }
        } else {
            super.startElement(uri, name, raw, attr);
        }
    }

    public void endElement(String uri, String name, String raw) throws SAXException {
        if (!NAMESPACE_URI.equals(uri)) {
            super.endElement(uri, name, raw);
        }
    }

    public void recycle() {
        super.recycle();
        this.publicationId = null;
        this.area = null;
        this.language = null;
        this.uuid = null;
        this.pub = null;
    }

    public void setRepository(Repository repository) {
        this.repository = repository;
    }

}
