/*
 * 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 freemarker.cache;

import java.io.IOException;

import freemarker.core.TemplateConfiguration;
import freemarker.template.Configuration;
import freemarker.template.utility.StringUtil;

/**
 * Returns the first non-{@code null} result of the child factories, ignoring all further child factories. The child
 * factories are called in the order as they were added.
 */
public class FirstMatchTemplateConfigurationFactory extends TemplateConfigurationFactory {
    
    private final TemplateConfigurationFactory[] templateConfigurationFactories;
    private boolean allowNoMatch;
    private String noMatchErrorDetails;
    
    public FirstMatchTemplateConfigurationFactory(TemplateConfigurationFactory... templateConfigurationFactories) {
        this.templateConfigurationFactories = templateConfigurationFactories;
    }

    @Override
    public TemplateConfiguration get(String sourceName, Object templateSource)
            throws IOException, TemplateConfigurationFactoryException {
        for (TemplateConfigurationFactory tcf : templateConfigurationFactories) {
            TemplateConfiguration tc = tcf.get(sourceName, templateSource); 
            if (tc != null) {
                return tc;
            }
        }
        if (!allowNoMatch) {
            throw new TemplateConfigurationFactoryException(
                    FirstMatchTemplateConfigurationFactory.class.getSimpleName()
                    + " has found no matching choice for source name "
                    + StringUtil.jQuote(sourceName) + ". "
                    + (noMatchErrorDetails != null
                            ? "Error details: " + noMatchErrorDetails 
                            : "(Set the noMatchErrorDetails property of the factory bean to give a more specific error "
                                    + "message. Set allowNoMatch to true if this shouldn't be an error.)"));
        }
        return null;
    }

    /**
     * Getter pair of {@link #setAllowNoMatch(boolean)}.
     */
    public boolean getAllowNoMatch() {
        return allowNoMatch;
    }

    /**
     * Use this to specify if having no matching choice is an error. The default is {@code false}, that is, it's an
     * error if there was no matching choice.
     * 
     * @see #setNoMatchErrorDetails(String)
     */
    public void setAllowNoMatch(boolean allowNoMatch) {
        this.allowNoMatch = allowNoMatch;
    }

    /**
     * Use this to specify the text added to the exception error message when there was no matching choice.
     * The default is {@code null} (no error details).
     * 
     * @see #setAllowNoMatch(boolean)
     */
    public String getNoMatchErrorDetails() {
        return noMatchErrorDetails;
    }

    
    public void setNoMatchErrorDetails(String noMatchErrorDetails) {
        this.noMatchErrorDetails = noMatchErrorDetails;
    }
    
    /**
     * Same as {@link #setAllowNoMatch(boolean)}, but return this object to support "fluent API" style. 
     */
    public FirstMatchTemplateConfigurationFactory allowNoMatch(boolean allow) {
        setAllowNoMatch(allow);
        return this;
    }

    /**
     * Same as {@link #setNoMatchErrorDetails(String)}, but return this object to support "fluent API" style. 
     */
    public FirstMatchTemplateConfigurationFactory noMatchErrorDetails(String message) {
        setNoMatchErrorDetails(message);
        return this;
    }

    @Override
    protected void setConfigurationOfChildren(Configuration cfg) {
        for (TemplateConfigurationFactory templateConfigurationFactory : templateConfigurationFactories) {
            templateConfigurationFactory.setConfiguration(cfg);
        }
    }
    
}
