001    package org.apache.turbine.services.template.mapper;
002    
003    
004    /*
005     * Licensed to the Apache Software Foundation (ASF) under one
006     * or more contributor license agreements.  See the NOTICE file
007     * distributed with this work for additional information
008     * regarding copyright ownership.  The ASF licenses this file
009     * to you under the Apache License, Version 2.0 (the
010     * "License"); you may not use this file except in compliance
011     * with the License.  You may obtain a copy of the License at
012     *
013     *   http://www.apache.org/licenses/LICENSE-2.0
014     *
015     * Unless required by applicable law or agreed to in writing,
016     * software distributed under the License is distributed on an
017     * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
018     * KIND, either express or implied.  See the License for the
019     * specific language governing permissions and limitations
020     * under the License.
021     */
022    
023    
024    import java.util.ArrayList;
025    import java.util.Arrays;
026    import java.util.List;
027    
028    import org.apache.commons.lang.StringUtils;
029    import org.apache.commons.logging.Log;
030    import org.apache.commons.logging.LogFactory;
031    import org.apache.turbine.services.template.TemplateEngineService;
032    import org.apache.turbine.services.template.TemplateService;
033    import org.apache.turbine.services.template.TurbineTemplate;
034    
035    /**
036     * This is a pretty simple mapper which returns template pathes for
037     * a supplied template name. If the path does not exist, it looks for
038     * a templated called "Default" in the same package.
039     * This path can be used by the TemplateEngine to access
040     * a certain resource to actually render the template.
041     *
042     * @author <a href="mailto:hps@intermeta.de">Henning P. Schmiedehausen</a>
043     * @version $Id: ScreenDefaultTemplateMapper.java 1071091 2011-02-15 22:06:55Z tv $
044     */
045    
046    public class ScreenDefaultTemplateMapper
047        extends BaseTemplateMapper
048        implements Mapper
049    {
050        /** Logging */
051        private static Log log = LogFactory.getLog(ScreenDefaultTemplateMapper.class);
052    
053        /**
054         * Default C'tor. If you use this C'tor, you must use
055         * the bean setter to set the various properties needed for
056         * this mapper before first usage.
057         */
058        public ScreenDefaultTemplateMapper()
059        {
060            // empty
061        }
062    
063        /**
064         * Look for a given Template, then try the
065         * default.
066         *
067         * @param template The template name.
068         * @return The parsed module name.
069         */
070        public String doMapping(String template)
071        {
072            log.debug("doMapping(" + template + ")");
073            // Copy our elements into an array
074            List<String> components
075                = new ArrayList<String>(Arrays.asList(StringUtils.split(
076                                                  template,
077                                                  String.valueOf(TemplateService.TEMPLATE_PARTS_SEPARATOR))));
078            int componentSize = components.size() - 1 ;
079    
080            // This method never gets an empty string passed.
081            // So this is never < 0
082            String templateName = components.get(componentSize);
083            components.remove(componentSize--);
084    
085            log.debug("templateName is " + templateName);
086    
087            // Last element decides, which template Service to use...
088            TemplateEngineService tes = TurbineTemplate.getTemplateEngineService(templateName);
089    
090            if (tes == null)
091            {
092                return null;
093            }
094    
095            String defaultName = "Default.vm";
096    
097            // This is an optimization. If the name we're looking for is
098            // already the default name for the template, don't do a "first run"
099            // which looks for an exact match.
100            boolean firstRun = !templateName.equals(defaultName);
101    
102            for(;;)
103            {
104                String templatePackage = StringUtils.join(components.iterator(), String.valueOf(separator));
105    
106                log.debug("templatePackage is now: " + templatePackage);
107    
108                StringBuffer testName = new StringBuffer();
109    
110                if (!components.isEmpty())
111                {
112                    testName.append(templatePackage);
113                    testName.append(separator);
114                }
115    
116                testName.append((firstRun)
117                    ? templateName
118                    : defaultName);
119    
120                // But the Templating service must look for the name with prefix
121                StringBuffer templatePath = new StringBuffer();
122                if (StringUtils.isNotEmpty(prefix))
123                {
124                    templatePath.append(prefix);
125                    templatePath.append(separator);
126                }
127                templatePath.append(testName);
128    
129                log.debug("Looking for " + templatePath);
130    
131                if (tes.templateExists(templatePath.toString()))
132                {
133                    log.debug("Found it, returning " + testName);
134                    return testName.toString();
135                }
136    
137                if (firstRun)
138                {
139                    firstRun = false;
140                }
141                else
142                {
143                    // We run this loop only two times. The
144                    // first time with the 'real' name and the
145                    // second time with "Default". The second time
146                    // we will end up here and break the for(;;) loop.
147                    break;
148                }
149            }
150    
151            log.debug("Returning default");
152            return getDefaultName(template);
153        }
154    }