You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tiles.apache.org by ap...@apache.org on 2008/06/19 21:03:10 UTC

svn commit: r669653 - in /tiles/framework/trunk/tiles-core/src: main/java/org/apache/tiles/definition/ main/java/org/apache/tiles/definition/dao/ main/java/org/apache/tiles/definition/util/ test/java/org/apache/tiles/definition/

Author: apetrelli
Date: Thu Jun 19 12:03:10 2008
New Revision: 669653

URL: http://svn.apache.org/viewvc?rev=669653&view=rev
Log:
TILES-256
Added test cases for the new LocaleDefinitionsFactory.
Refactoring of base interfaces and of UrlDefinitionsFactory.

Added:
    tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/LocaleDefinitionsFactory.java   (with props)
    tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/Refreshable.java
      - copied, changed from r667964, tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/ReloadableDefinitionsFactory.java
    tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/LocaleDefinitionsFactoryTest.java   (with props)
Modified:
    tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/UrlDefinitionsFactory.java
    tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/CachingLocaleUrlDefinitionDAO.java
    tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/LocaleUrlDefinitionDAO.java
    tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/util/DefinitionsFactoryUtil.java
    tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/TestReloadableDefinitionsFactory.java

Added: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/LocaleDefinitionsFactory.java
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/LocaleDefinitionsFactory.java?rev=669653&view=auto
==============================================================================
--- tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/LocaleDefinitionsFactory.java (added)
+++ tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/LocaleDefinitionsFactory.java Thu Jun 19 12:03:10 2008
@@ -0,0 +1,199 @@
+/*
+ * $Id$
+ *
+ * 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.tiles.definition;
+
+import java.util.Locale;
+import java.util.Map;
+
+import org.apache.tiles.Definition;
+import org.apache.tiles.Initializable;
+import org.apache.tiles.TilesApplicationContext;
+import org.apache.tiles.awareness.TilesApplicationContextAware;
+import org.apache.tiles.context.TilesRequestContext;
+import org.apache.tiles.definition.dao.CachingLocaleUrlDefinitionDAO;
+import org.apache.tiles.definition.dao.DefinitionDAO;
+import org.apache.tiles.locale.LocaleResolver;
+import org.apache.tiles.locale.impl.DefaultLocaleResolver;
+import org.apache.tiles.util.ClassUtil;
+
+/**
+ * {@link DefinitionsFactory DefinitionsFactory} implementation that manages
+ * Definitions configuration data from URLs, but resolving definition
+ * inheritance when a definition is returned.. <p/>
+ * <p>
+ * The Definition objects are read from the
+ * {@link org.apache.tiles.definition.digester.DigesterDefinitionsReader DigesterDefinitionsReader}
+ * class unless another implementation is specified.
+ * </p>
+ *
+ * @version $Rev$ $Date$
+ * @since 2.1.0
+ */
+public class LocaleDefinitionsFactory implements DefinitionsFactory,
+        TilesApplicationContextAware, Initializable {
+
+    /**
+     * The definition DAO that extracts the definitions from the sources.
+     *
+     * @since 2.1.0
+     */
+    protected DefinitionDAO<Locale> definitionDao;
+
+    /**
+     * The application context.
+     *
+     * @since 2.1.0
+     */
+    protected TilesApplicationContext applicationContext;
+
+    /**
+     * The locale resolver object.
+     */
+    protected LocaleResolver localeResolver;
+
+    /** {@inheritDoc} */
+    public void setApplicationContext(TilesApplicationContext applicationContext) {
+        this.applicationContext = applicationContext;
+    }
+
+    /**
+     * Sets the locale resolver to use.
+     *
+     * @param localeResolver The locale resolver.
+     * @since 2.1.0
+     */
+    public void setLocaleResolver(LocaleResolver localeResolver) {
+        this.localeResolver = localeResolver;
+    }
+
+    /**
+     * Sets the definition DAO to use. It must be locale-based.
+     *
+     * @param definitionDao The definition DAO.
+     * @since 2.1.0
+     */
+    public void setDefinitionDAO(DefinitionDAO<Locale> definitionDao) {
+        this.definitionDao = definitionDao;
+    }
+
+    /**
+     * Initializes the DefinitionsFactory and its subcomponents.
+     * <p/>
+     * Implementations may support configuration properties to be passed in via
+     * the params Map.
+     *
+     * @param params The Map of configuration properties.
+     * @throws DefinitionsFactoryException if an initialization error occurs.
+     */
+    @SuppressWarnings("unchecked")
+    public void init(Map<String, String> params) {
+        String definitionDaoClassName = params
+                .get(DefinitionsFactory.DEFINITION_DAO_INIT_PARAM);
+        if (definitionDaoClassName != null) {
+            definitionDao = (DefinitionDAO<Locale>) ClassUtil
+                    .instantiate(definitionDaoClassName);
+        } else {
+            definitionDao = createDefaultDefinitionDAO();
+        }
+        if (definitionDao instanceof TilesApplicationContextAware) {
+            ((TilesApplicationContextAware) definitionDao)
+                    .setApplicationContext(applicationContext);
+        }
+        if (definitionDao instanceof Initializable) {
+            ((Initializable) definitionDao).init(params);
+        }
+
+        String resolverClassName = params
+                .get(DefinitionsFactory.LOCALE_RESOLVER_IMPL_PROPERTY);
+        if (resolverClassName != null) {
+            localeResolver = (LocaleResolver) ClassUtil.instantiate(resolverClassName);
+        } else {
+            localeResolver = createDefaultLocaleResolver();
+        }
+        localeResolver.init(params);
+    }
+
+    /** {@inheritDoc} */
+    public Definition getDefinition(String name,
+            TilesRequestContext tilesContext) {
+        Definition retValue;
+        Locale locale = null;
+
+        if (tilesContext != null) {
+            locale = localeResolver.resolveLocale(tilesContext);
+        }
+
+        retValue = definitionDao.getDefinition(name, locale);
+        if (retValue != null) {
+            retValue = new Definition(retValue);
+            String parentDefinitionName = retValue.getExtends();
+            while (parentDefinitionName != null) {
+                Definition parent = definitionDao.getDefinition(
+                        parentDefinitionName, locale);
+                if (parent == null) {
+                    throw new NoSuchDefinitionException("Cannot find definition '"
+                            + parentDefinitionName + "' ancestor of '"
+                            + retValue.getName() + "'");
+                }
+                retValue.inherit(parent);
+                parentDefinitionName = parent.getExtends();
+            }
+        }
+
+        return retValue;
+    }
+
+    /** {@inheritDoc} */
+    @Deprecated
+    public void addSource(Object source) {
+        throw new UnsupportedOperationException(
+                "The addSource method is not supported");
+    }
+
+    /** {@inheritDoc} */
+    @Deprecated
+    public Definitions readDefinitions() {
+        throw new UnsupportedOperationException(
+            "The readDefinitions method is not supported");
+    }
+
+    /**
+     * Creates the default locale resolver, if it has not been specified
+     * outside.
+     *
+     * @return The default locale resolver.
+     * @since 2.1.0
+     */
+    protected LocaleResolver createDefaultLocaleResolver() {
+        return new DefaultLocaleResolver();
+    }
+
+    /**
+     * Creates the default definition DAO, if it has not been specified outside.
+     *
+     * @return The default definition DAO.
+     * @since 2.1.0
+     */
+    protected DefinitionDAO<Locale> createDefaultDefinitionDAO() {
+        return new CachingLocaleUrlDefinitionDAO();
+    }
+}

Propchange: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/LocaleDefinitionsFactory.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/LocaleDefinitionsFactory.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Copied: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/Refreshable.java (from r667964, tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/ReloadableDefinitionsFactory.java)
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/Refreshable.java?p2=tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/Refreshable.java&p1=tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/ReloadableDefinitionsFactory.java&r1=667964&r2=669653&rev=669653&view=diff
==============================================================================
--- tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/ReloadableDefinitionsFactory.java (original)
+++ tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/Refreshable.java Thu Jun 19 12:03:10 2008
@@ -27,19 +27,14 @@
  * Indicates support for reloading Tiles configuration when it changes.
  *
  * @version $Rev$ $Date$
+ * @since 2.1.0
  */
-public interface ReloadableDefinitionsFactory extends RefreshMonitor {
-
-    /**
-     * Indicates whether the DefinitionsFactory is out of date and needs to be
-     * reloaded.
-     *
-     * @return <code>true</code> if the definitions need to be refreshed.
-     */
-    boolean refreshRequired();
+public interface Refreshable extends RefreshMonitor {
 
     /**
      * Refreshes the stored definitions, reloading them.
+     *
+     * @since 2.1.0
      */
     void refresh();
 }

Modified: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/UrlDefinitionsFactory.java
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/UrlDefinitionsFactory.java?rev=669653&r1=669652&r2=669653&view=diff
==============================================================================
--- tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/UrlDefinitionsFactory.java (original)
+++ tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/UrlDefinitionsFactory.java Thu Jun 19 12:03:10 2008
@@ -24,16 +24,12 @@
 import org.apache.commons.logging.LogFactory;
 import org.apache.tiles.Definition;
 import org.apache.tiles.Initializable;
-import org.apache.tiles.TilesApplicationContext;
 import org.apache.tiles.awareness.TilesApplicationContextAware;
 import org.apache.tiles.context.TilesRequestContext;
 import org.apache.tiles.definition.dao.DefinitionDAO;
 import org.apache.tiles.definition.dao.LocaleUrlDefinitionDAO;
 import org.apache.tiles.definition.dao.URLReader;
 import org.apache.tiles.impl.BasicTilesContainer;
-import org.apache.tiles.locale.LocaleResolver;
-import org.apache.tiles.locale.impl.DefaultLocaleResolver;
-import org.apache.tiles.util.ClassUtil;
 import org.apache.tiles.util.LocaleUtil;
 
 import java.net.URL;
@@ -47,17 +43,19 @@
 import java.util.StringTokenizer;
 
 /**
- * {@link DefinitionsFactory DefinitionsFactory} implementation
- * that manages Definitions configuration data from URLs.
- * <p/>
- * <p>The Definition objects are read from the
+ * {@link DefinitionsFactory DefinitionsFactory} implementation that manages
+ * Definitions configuration data from URLs, resolving inheritance when the URL
+ * is loaded. <p/>
+ * <p>
+ * The Definition objects are read from the
  * {@link org.apache.tiles.definition.digester.DigesterDefinitionsReader DigesterDefinitionsReader}
- * class unless another implementation is specified.</p>
+ * class unless another implementation is specified.
+ * </p>
  *
  * @version $Rev$ $Date$
  */
-public class UrlDefinitionsFactory implements DefinitionsFactory,
-        ReloadableDefinitionsFactory, TilesApplicationContextAware,
+public class UrlDefinitionsFactory extends LocaleDefinitionsFactory implements DefinitionsFactory,
+        Refreshable, TilesApplicationContextAware,
         Initializable {
 
     /**
@@ -73,11 +71,20 @@
     private static final Log LOG = LogFactory.getLog(UrlDefinitionsFactory.class);
 
     /**
-     * The definition DAO that extracts the definitions from the sources.
-     *
-     * @since 2.1.0
+     * Contains a list of locales that have been processed.
      */
-    protected DefinitionDAO<Locale> definitionDao;
+    private List<Locale> processedLocales;
+
+
+    /**
+     * The base set of Definition objects not discriminated by locale.
+     */
+    private Map<String, Definition> baseDefinitions;
+
+    /**
+     * The locale-specific set of definitions objects.
+     */
+    private Map<Locale, Map<String, Definition>> localeSpecificDefinitions;
 
     /**
      * Contains the URL objects identifying where configuration data is found.
@@ -101,34 +108,6 @@
     protected Map<String, Long> lastModifiedDates;
 
     /**
-     * The application context.
-     *
-     * @since 2.1.0
-     */
-    protected TilesApplicationContext applicationContext;
-
-    /**
-     * Contains a list of locales that have been processed.
-     */
-    private List<Locale> processedLocales;
-
-
-    /**
-     * The base set of Definition objects not discriminated by locale.
-     */
-    private Map<String, Definition> baseDefinitions;
-
-    /**
-     * The locale-specific set of definitions objects.
-     */
-    private Map<Locale, Map<String, Definition>> localeSpecificDefinitions;
-
-    /**
-     * The locale resolver object.
-     */
-    private LocaleResolver localeResolver;
-
-    /**
      * Creates a new instance of UrlDefinitionsFactory.
      */
     public UrlDefinitionsFactory() {
@@ -136,30 +115,6 @@
         processedLocales = new ArrayList<Locale>();
     }
 
-    /** {@inheritDoc} */
-    public void setApplicationContext(TilesApplicationContext applicationContext) {
-        this.applicationContext = applicationContext;
-    }
-
-    /**
-     * Sets the locale resolver to use.
-     *
-     * @param localeResolver The locale resolver.
-     * @since 2.1.0
-     */
-    public void setLocaleResolver(LocaleResolver localeResolver) {
-        this.localeResolver = localeResolver;
-    }
-
-    /**
-     * Sets the definition DAO to use. It must be locale-based.
-     *
-     * @param definitionDao The definition DAO.
-     */
-    public void setDefinitionDAO(DefinitionDAO<Locale> definitionDao) {
-        this.definitionDao = definitionDao;
-    }
-
     /**
      * Initializes the DefinitionsFactory and its subcomponents.
      * <p/>
@@ -171,46 +126,11 @@
      */
     @SuppressWarnings("unchecked")
     public void init(Map<String, String> params) {
-        String definitionDaoClassName = params
-                .get(DefinitionsFactory.DEFINITION_DAO_INIT_PARAM);
-        if (definitionDaoClassName != null) {
-            definitionDao = (DefinitionDAO<Locale>) ClassUtil
-                    .instantiate(definitionDaoClassName);
-        } else {
-            definitionDao = new LocaleUrlDefinitionDAO();
-        }
-        if (definitionDao instanceof TilesApplicationContextAware) {
-            ((TilesApplicationContextAware) definitionDao)
-                    .setApplicationContext(applicationContext);
-        }
-        if (definitionDao instanceof Initializable) {
-            ((Initializable) definitionDao).init(params);
-        }
-
-        String resolverClassName = params
-                .get(DefinitionsFactory.LOCALE_RESOLVER_IMPL_PROPERTY);
-        if (resolverClassName != null) {
-            localeResolver = (LocaleResolver) ClassUtil.instantiate(resolverClassName);
-        } else {
-            localeResolver = new DefaultLocaleResolver();
-        }
-        localeResolver.init(params);
+        super.init(params);
         loadDefinitions();
     }
 
     /**
-     * Returns the definitions holder object.
-     *
-     * @return The definitions holder.
-     * @deprecated Do not use! Deprecated with no replacement.
-     */
-    @Deprecated
-    protected Definitions getDefinitions() {
-        return new DefinitionsImpl(baseDefinitions, localeSpecificDefinitions);
-    }
-
-
-    /**
      * Returns a Definition object that matches the given name and
      * Tiles context.
      *
@@ -220,6 +140,7 @@
      *         is found.
      * @throws DefinitionsFactoryException if an error occurs reading definitions.
      */
+    @Override
     public Definition getDefinition(String name,
             TilesRequestContext tilesContext) {
 
@@ -235,50 +156,23 @@
         return getDefinition(name, locale);
     }
 
-    /**
-     * Adds a source where Definition objects are stored.
-     * <p/>
-     * Implementations should publish what type of source object they expect.
-     * The source should contain enough information to resolve a configuration
-     * source containing definitions.  The source should be a "base" source for
-     * configurations.  Internationalization and Localization properties will be
-     * applied by implementations to discriminate the correct data sources based
-     * on locale.
-     *
-     * @param source The configuration source for definitions.
-     * @throws DefinitionsFactoryException if an invalid source is passed in or
-     *                                     an error occurs resolving the source to an actual data store.
-     * @deprecated Use {@link URLReader#addSourceURL(URL)}.
-     */
-    public void addSource(Object source) {
-        if (source == null) {
-            throw new DefinitionsFactoryException(
-                "Source object must not be null");
-        }
-
-        if (!(source instanceof URL)) {
-            throw new DefinitionsFactoryException(
-                "Source object must be an URL");
-        }
-
-        if (definitionDao instanceof URLReader) {
-            ((URLReader) definitionDao).addSourceURL((URL) source);
-        }
+    /** {@inheritDoc} */
+    public synchronized void refresh() {
+        LOG.debug("Updating Tiles definitions. . .");
+        processedLocales.clear();
+        loadDefinitions();
     }
 
+
     /**
-     * Appends locale-specific {@link Definition} objects to an existing
-     * {@link Definitions} set by reading locale-specific versions of
-     * the applied sources.
+     * Indicates whether the DefinitionsFactory is out of date and needs to be
+     * reloaded.
      *
-     * @param definitions  The Definitions object to append to.
-     * @param tilesContext The requested locale.
-     * @throws DefinitionsFactoryException if an error occurs reading definitions.
-     * @deprecated Use {@link #addDefinitions(TilesRequestContext)}.
+     * @return If the factory needs refresh.
      */
-    protected void addDefinitions(Definitions definitions,
-            TilesRequestContext tilesContext) {
-        addDefinitions(tilesContext);
+    public boolean refreshRequired() {
+        return (definitionDao instanceof RefreshMonitor)
+                && ((RefreshMonitor) definitionDao).refreshRequired();
     }
 
     /**
@@ -313,21 +207,6 @@
     }
 
     /**
-     * Creates and returns a {@link Definitions} set by reading
-     * configuration data from the applied sources.
-     *
-     * @return The definitions holder object, filled with base definitions.
-     * @throws DefinitionsFactoryException if an error occurs reading the
-     * sources.
-     * @deprecated Let the Definitions Factory use it.
-     */
-    @Deprecated
-    public Definitions readDefinitions() {
-        loadDefinitions();
-        return new DefinitionsImpl(baseDefinitions, localeSpecificDefinitions);
-    }
-
-    /**
      * Indicates whether a given context has been processed or not.
      * <p/>
      * This method can be used to avoid unnecessary synchronization of the
@@ -344,32 +223,6 @@
     }
 
     /**
-     * Creates a new instance of <code>Definitions</code>. Override this method
-     * to provide your custom instance of Definitions.
-     *
-     * @return A new instance of <code>Definitions</code>.
-     * @deprecated Do not use! Deprecated with no replacement.
-     */
-    @Deprecated
-    protected Definitions createDefinitions() {
-        return new DefinitionsImpl();
-    }
-
-    /**
-     * Concat postfix to the name. Take care of existing filename extension.
-     * Transform the given name "name.ext" to have "name" + "postfix" + "ext".
-     * If there is no ext, return "name" + "postfix".
-     *
-     * @param name    Filename.
-     * @param postfix Postfix to add.
-     * @return Concatenated filename.
-     * @deprecated Use {@link LocaleUtil#concatPostfix(String,String)} instead
-     */
-    protected static String concatPostfix(String name, String postfix) {
-        return LocaleUtil.concatPostfix(name, postfix);
-    }
-
-    /**
      * Creates a base set by reading configuration data from the applied
      * sources.
      *
@@ -384,83 +237,6 @@
     }
 
     /**
-     * Calculate the postfixes along the search path from the base bundle to the
-     * bundle specified by baseName and locale.
-     * Method copied from java.util.ResourceBundle
-     *
-     * @param locale the locale
-     * @return a list of
-     * @deprecated Use {@link LocaleUtil#calculatePostfixes(Locale)} instead.
-     */
-    protected static List<String> calculatePostfixes(Locale locale) {
-        return LocaleUtil.calculatePostfixes(locale);
-    }
-
-
-    /** {@inheritDoc} */
-    public synchronized void refresh() {
-        LOG.debug("Updating Tiles definitions. . .");
-        processedLocales.clear();
-        loadDefinitions();
-    }
-
-
-    /**
-     * Indicates whether the DefinitionsFactory is out of date and needs to be
-     * reloaded.
-     *
-     * @return If the factory needs refresh.
-     */
-    public boolean refreshRequired() {
-        return (definitionDao instanceof RefreshMonitor)
-                && ((RefreshMonitor) definitionDao).refreshRequired();
-    }
-
-    /**
-     * Derive the resource string from the initialization parameters. If no
-     * parameter {@link DefinitionsFactory#DEFINITIONS_CONFIG} is available,
-     * attempts to retrieve {@link BasicTilesContainer#DEFINITIONS_CONFIG} and
-     * {@link UrlDefinitionsFactory#LEGACY_DEFINITIONS_CONFIG}. If neither are
-     * available, returns "/WEB-INF/tiles.xml".
-     *
-     * @param parms The initialization parameters.
-     * @return resource string to be parsed.
-     * @deprecated Deprecated without replacement.
-     */
-    @Deprecated
-    protected String getResourceString(Map<String, String> parms) {
-        String resourceStr = parms.get(DefinitionsFactory.DEFINITIONS_CONFIG);
-        if (resourceStr == null) {
-            resourceStr = parms.get(BasicTilesContainer.DEFINITIONS_CONFIG);
-        }
-        if (resourceStr == null) {
-            resourceStr = parms.get(UrlDefinitionsFactory.LEGACY_DEFINITIONS_CONFIG);
-        }
-        if (resourceStr == null) {
-            resourceStr = "/WEB-INF/tiles.xml";
-        }
-        return resourceStr;
-    }
-
-    /**
-     * Parse the resourceString into a list of resource paths
-     * which can be loaded by the application context.
-     *
-     * @param resourceString comma seperated resources
-     * @return parsed resources
-     * @deprecated Deprecated without replacement.
-     */
-    @Deprecated
-    protected List<String> getResourceNames(String resourceString) {
-        StringTokenizer tokenizer = new StringTokenizer(resourceString, ",");
-        List<String> filenames = new ArrayList<String>(tokenizer.countTokens());
-        while (tokenizer.hasMoreTokens()) {
-            filenames.add(tokenizer.nextToken().trim());
-        }
-        return filenames;
-    }
-
-    /**
      * Clears definitions.
      *
      * @since 2.1.0
@@ -579,4 +355,166 @@
 
         return definition;
     }
+
+    /**
+     * Adds a source where Definition objects are stored.
+     * <p/>
+     * Implementations should publish what type of source object they expect.
+     * The source should contain enough information to resolve a configuration
+     * source containing definitions.  The source should be a "base" source for
+     * configurations.  Internationalization and Localization properties will be
+     * applied by implementations to discriminate the correct data sources based
+     * on locale.
+     *
+     * @param source The configuration source for definitions.
+     * @throws DefinitionsFactoryException if an invalid source is passed in or
+     *                                     an error occurs resolving the source to an actual data store.
+     * @deprecated Use {@link URLReader#addSourceURL(URL)}.
+     */
+    public void addSource(Object source) {
+        if (source == null) {
+            throw new DefinitionsFactoryException(
+                "Source object must not be null");
+        }
+
+        if (!(source instanceof URL)) {
+            throw new DefinitionsFactoryException(
+                "Source object must be an URL");
+        }
+
+        if (definitionDao instanceof URLReader) {
+            ((URLReader) definitionDao).addSourceURL((URL) source);
+        }
+    }
+
+    /** {@inheritDoc} */
+    @Override
+    protected DefinitionDAO<Locale> createDefaultDefinitionDAO() {
+        return new LocaleUrlDefinitionDAO();
+    }
+
+    /**
+     * Creates and returns a {@link Definitions} set by reading
+     * configuration data from the applied sources.
+     *
+     * @return The definitions holder object, filled with base definitions.
+     * @throws DefinitionsFactoryException if an error occurs reading the
+     * sources.
+     * @deprecated Let the Definitions Factory use it.
+     */
+    @Deprecated
+    public Definitions readDefinitions() {
+        loadDefinitions();
+        return new DefinitionsImpl(baseDefinitions, localeSpecificDefinitions);
+    }
+
+    /**
+     * Returns the definitions holder object.
+     *
+     * @return The definitions holder.
+     * @deprecated Do not use! Deprecated with no replacement.
+     */
+    @Deprecated
+    protected Definitions getDefinitions() {
+        return new DefinitionsImpl(baseDefinitions, localeSpecificDefinitions);
+    }
+
+    /**
+     * Appends locale-specific {@link Definition} objects to an existing
+     * {@link Definitions} set by reading locale-specific versions of
+     * the applied sources.
+     *
+     * @param definitions  The Definitions object to append to.
+     * @param tilesContext The requested locale.
+     * @throws DefinitionsFactoryException if an error occurs reading definitions.
+     * @deprecated Use {@link #addDefinitions(TilesRequestContext)}.
+     */
+    @Deprecated
+    protected void addDefinitions(Definitions definitions,
+            TilesRequestContext tilesContext) {
+        addDefinitions(tilesContext);
+    }
+
+    /**
+     * Creates a new instance of <code>Definitions</code>. Override this method
+     * to provide your custom instance of Definitions.
+     *
+     * @return A new instance of <code>Definitions</code>.
+     * @deprecated Do not use! Deprecated with no replacement.
+     */
+    @Deprecated
+    protected Definitions createDefinitions() {
+        return new DefinitionsImpl();
+    }
+
+    /**
+     * Concat postfix to the name. Take care of existing filename extension.
+     * Transform the given name "name.ext" to have "name" + "postfix" + "ext".
+     * If there is no ext, return "name" + "postfix".
+     *
+     * @param name    Filename.
+     * @param postfix Postfix to add.
+     * @return Concatenated filename.
+     * @deprecated Use {@link LocaleUtil#concatPostfix(String,String)} instead
+     */
+    protected static String concatPostfix(String name, String postfix) {
+        return LocaleUtil.concatPostfix(name, postfix);
+    }
+
+    /**
+     * Calculate the postfixes along the search path from the base bundle to the
+     * bundle specified by baseName and locale.
+     * Method copied from java.util.ResourceBundle
+     *
+     * @param locale the locale
+     * @return a list of
+     * @deprecated Use {@link LocaleUtil#calculatePostfixes(Locale)} instead.
+     */
+    protected static List<String> calculatePostfixes(Locale locale) {
+        return LocaleUtil.calculatePostfixes(locale);
+    }
+
+    /**
+     * Derive the resource string from the initialization parameters. If no
+     * parameter {@link DefinitionsFactory#DEFINITIONS_CONFIG} is available,
+     * attempts to retrieve {@link BasicTilesContainer#DEFINITIONS_CONFIG} and
+     * {@link UrlDefinitionsFactory#LEGACY_DEFINITIONS_CONFIG}. If neither are
+     * available, returns "/WEB-INF/tiles.xml".
+     *
+     * @param parms The initialization parameters.
+     * @return resource string to be parsed.
+     * @deprecated Deprecated without replacement.
+     */
+    @Deprecated
+    protected String getResourceString(Map<String, String> parms) {
+        String resourceStr = parms.get(DefinitionsFactory.DEFINITIONS_CONFIG);
+        if (resourceStr == null) {
+            resourceStr = parms.get(BasicTilesContainer.DEFINITIONS_CONFIG);
+        }
+        if (resourceStr == null) {
+            resourceStr = parms.get(UrlDefinitionsFactory.LEGACY_DEFINITIONS_CONFIG);
+        }
+        if (resourceStr == null) {
+            resourceStr = "/WEB-INF/tiles.xml";
+        }
+        return resourceStr;
+    }
+
+    /**
+     * Parse the resourceString into a list of resource paths
+     * which can be loaded by the application context.
+     *
+     * @param resourceString comma seperated resources
+     * @return parsed resources
+     * @deprecated Deprecated without replacement.
+     */
+    @Deprecated
+    protected List<String> getResourceNames(String resourceString) {
+        StringTokenizer tokenizer = new StringTokenizer(resourceString, ",");
+        List<String> filenames = new ArrayList<String>(tokenizer.countTokens());
+        while (tokenizer.hasMoreTokens()) {
+            filenames.add(tokenizer.nextToken().trim());
+        }
+        return filenames;
+    }
 }

Modified: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/CachingLocaleUrlDefinitionDAO.java
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/CachingLocaleUrlDefinitionDAO.java?rev=669653&r1=669652&r2=669653&view=diff
==============================================================================
--- tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/CachingLocaleUrlDefinitionDAO.java (original)
+++ tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/CachingLocaleUrlDefinitionDAO.java Thu Jun 19 12:03:10 2008
@@ -29,24 +29,50 @@
 
 import org.apache.tiles.Definition;
 import org.apache.tiles.definition.DefinitionsFactoryException;
+import org.apache.tiles.definition.Refreshable;
 import org.apache.tiles.util.LocaleUtil;
 
 /**
+ * <p>
  * A definitions DAO (loading URLs and using Locale as a customization key) that
  * caches definitions that have been loaded in a raw way (i.e. with inheritance
  * that is not resolved).
+ * </p>
+ * <p>
+ * It can check if the URLs change, but by default this feature is turned off.
+ * </p>
  *
  * @version $Rev$ $Date$
  * @since 2.1.0
  */
-public class CachingLocaleUrlDefinitionDAO extends BaseLocaleUrlDefinitionDAO {
+public class CachingLocaleUrlDefinitionDAO extends BaseLocaleUrlDefinitionDAO
+        implements Refreshable {
+
+    /**
+     * Initialization parameter to set whether we want to refresh URLs when they
+     * change.
+     *
+     * @since 2.1.0
+     */
+    public static final String CHECK_REFRESH_INIT_PARAMETER =
+        "org.apache.tiles.definition.dao.LocaleUrlDefinitionDAO.CHECK_REFRESH";
 
     /**
      * The locale-specific set of definitions objects.
+     *
+     * @since 2.1.0
      */
     private Map<Locale, Map<String, Definition>> locale2definitionMap;
 
     /**
+     * Flag that, when <code>true</code>, enables automatic checking of URLs
+     * changing.
+     *
+     * @since 2.1.0
+     */
+    private boolean checkRefresh = false;
+
+    /**
      * Constructor.
      *
      * @since 2.1.0
@@ -56,6 +82,15 @@
     }
 
     /** {@inheritDoc} */
+    @Override
+    public void init(Map<String, String> params) {
+        super.init(params);
+
+        String param = params.get(CHECK_REFRESH_INIT_PARAMETER);
+        checkRefresh = "true".equals(param);
+    }
+
+    /** {@inheritDoc} */
     public Definition getDefinition(String name, Locale customizationKey) {
         Definition retValue = null;
         Map<String, Definition> definitions = getDefinitions(customizationKey);
@@ -73,12 +108,30 @@
         }
         Map<String, Definition> retValue = locale2definitionMap
                 .get(customizationKey);
-        if (retValue == null || refreshRequired()) {
+        if (retValue == null || (checkRefresh && refreshRequired())) {
             retValue = checkAndloadDefinitions(customizationKey);
         }
         return retValue;
     }
 
+    /** {@inheritDoc} */
+    public synchronized void refresh() {
+        if (refreshRequired()) {
+            locale2definitionMap.clear();
+        }
+    }
+
+    /**
+     * Sets the flag to check URL refresh. If not called, the default is
+     * <code>false</code>.
+     *
+     * @param checkRefresh When <code>true</code>, enables automatic checking
+     * of URLs changing.
+     */
+    public void setCheckRefresh(boolean checkRefresh) {
+        this.checkRefresh = checkRefresh;
+    }
+
     /**
      * Checks if URLs have changed. If yes, it clears the cache. Then continues
      * loading definitions.
@@ -89,7 +142,7 @@
      */
     protected synchronized Map<String, Definition> checkAndloadDefinitions(
             Locale customizationKey) {
-        if (refreshRequired()) {
+        if (checkRefresh && refreshRequired()) {
             locale2definitionMap.clear();
         }
         return loadDefinitions(customizationKey);

Modified: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/LocaleUrlDefinitionDAO.java
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/LocaleUrlDefinitionDAO.java?rev=669653&r1=669652&r2=669653&view=diff
==============================================================================
--- tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/LocaleUrlDefinitionDAO.java (original)
+++ tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/dao/LocaleUrlDefinitionDAO.java Thu Jun 19 12:03:10 2008
@@ -43,6 +43,8 @@
 
     /**
      * Constructor.
+     *
+     * @since 2.1.0
      */
     public LocaleUrlDefinitionDAO() {
         sourceURLs = new ArrayList<URL>();

Modified: tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/util/DefinitionsFactoryUtil.java
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/util/DefinitionsFactoryUtil.java?rev=669653&r1=669652&r2=669653&view=diff
==============================================================================
--- tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/util/DefinitionsFactoryUtil.java (original)
+++ tiles/framework/trunk/tiles-core/src/main/java/org/apache/tiles/definition/util/DefinitionsFactoryUtil.java Thu Jun 19 12:03:10 2008
@@ -24,7 +24,7 @@
 import org.apache.tiles.TilesContainer;
 import org.apache.tiles.access.TilesAccess;
 import org.apache.tiles.definition.DefinitionsFactory;
-import org.apache.tiles.definition.ReloadableDefinitionsFactory;
+import org.apache.tiles.definition.Refreshable;
 import org.apache.tiles.impl.BasicTilesContainer;
 
 /**
@@ -67,8 +67,8 @@
         if (container instanceof BasicTilesContainer) {
             BasicTilesContainer basic = (BasicTilesContainer) container;
             DefinitionsFactory factory = basic.getDefinitionsFactory();
-            if (factory instanceof ReloadableDefinitionsFactory) {
-                ReloadableDefinitionsFactory rFactory = (ReloadableDefinitionsFactory) factory;
+            if (factory instanceof Refreshable) {
+                Refreshable rFactory = (Refreshable) factory;
                 if (rFactory.refreshRequired()) {
                     rFactory.refresh();
                 }

Added: tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/LocaleDefinitionsFactoryTest.java
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/LocaleDefinitionsFactoryTest.java?rev=669653&view=auto
==============================================================================
--- tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/LocaleDefinitionsFactoryTest.java (added)
+++ tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/LocaleDefinitionsFactoryTest.java Thu Jun 19 12:03:10 2008
@@ -0,0 +1,327 @@
+/*
+ * $Id$
+ *
+ * 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.tiles.definition;
+
+import java.net.URL;
+import java.util.HashMap;
+import java.util.Locale;
+import java.util.Map;
+
+import junit.framework.Test;
+import junit.framework.TestCase;
+import junit.framework.TestSuite;
+
+import org.apache.tiles.TilesApplicationContext;
+import org.apache.tiles.context.TilesRequestContext;
+import org.easymock.EasyMock;
+
+/**
+ * Tests {@link LocaleDefinitionsFactory}.
+ *
+ * @version $Rev$ $Date$
+ */
+public class LocaleDefinitionsFactoryTest extends TestCase {
+
+    /**
+     * The definitions factory.
+     */
+    private LocaleDefinitionsFactory factory;
+
+    /** {@inheritDoc} */
+    @Override
+    protected void setUp() throws Exception {
+        super.setUp();
+        factory = new LocaleDefinitionsFactory();
+    }
+
+    /**
+     * Creates a new instance of TestUrlDefinitionsFactory.
+     *
+     * @param name The name of the test.
+     */
+    public LocaleDefinitionsFactoryTest(String name) {
+        super(name);
+    }
+
+    /**
+     * Start the tests.
+     *
+     * @param theArgs the arguments. Not used
+     */
+    public static void main(String[] theArgs) {
+        junit.textui.TestRunner.main(
+                new String[]{LocaleDefinitionsFactoryTest.class.getName()});
+    }
+
+    /**
+     * @return a test suite (<code>TestSuite</code>) that includes all methods
+     *         starting with "test"
+     */
+    public static Test suite() {
+        return new TestSuite(LocaleDefinitionsFactoryTest.class);
+    }
+
+    /**
+     * Tests the readDefinitions method under normal conditions.
+     *
+     * @throws Exception If something goes wrong.
+     */
+    @SuppressWarnings("unchecked")
+    public void testReadDefinitions() throws Exception {
+        // Set up multiple data sources.
+        URL url1 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs1.xml");
+        assertNotNull("Could not load defs1 file.", url1);
+        URL url2 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs2.xml");
+        assertNotNull("Could not load defs2 file.", url2);
+        URL url3 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs3.xml");
+        assertNotNull("Could not load defs3 file.", url3);
+
+        TilesApplicationContext applicationContext = EasyMock
+                .createMock(TilesApplicationContext.class);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs1.xml"))
+                .andReturn(url1);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs2.xml"))
+                .andReturn(url2);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs3.xml"))
+                .andReturn(url3);
+        EasyMock.replay(applicationContext);
+        factory.setApplicationContext(applicationContext);
+
+        Map<String, String> params = new HashMap<String, String>();
+        params.put(DefinitionsFactory.DEFINITIONS_CONFIG,
+                "org/apache/tiles/config/defs1.xml,org/apache/tiles/config/defs2.xml,"
+                + "org/apache/tiles/config/defs3.xml");
+        factory.init(params);
+
+        assertNotNull("test.def1 definition not found.", factory.getDefinition(
+                "test.def1", (TilesRequestContext) null));
+        assertNotNull("test.def2 definition not found.", factory.getDefinition(
+                "test.def2", (TilesRequestContext) null));
+        assertNotNull("test.def3 definition not found.", factory.getDefinition(
+                "test.def3", (TilesRequestContext) null));
+    }
+
+    /**
+     * Tests the getDefinition method.
+     *
+     * @throws Exception If something goes wrong.
+     */
+    @SuppressWarnings("unchecked")
+    public void testGetDefinition() throws Exception {
+        // Set up multiple data sources.
+        URL url1 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs1.xml");
+        assertNotNull("Could not load defs1 file.", url1);
+        URL url2 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs2.xml");
+        assertNotNull("Could not load defs2 file.", url2);
+        URL url3 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs3.xml");
+        assertNotNull("Could not load defs3 file.", url3);
+
+        TilesApplicationContext applicationContext = EasyMock
+                .createMock(TilesApplicationContext.class);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs1.xml"))
+                .andReturn(url1);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs2.xml"))
+                .andReturn(url2);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs3.xml"))
+                .andReturn(url3);
+        EasyMock.replay(applicationContext);
+        factory.setApplicationContext(applicationContext);
+
+        Map<String, String> params = new HashMap<String, String>();
+        params.put(DefinitionsFactory.DEFINITIONS_CONFIG,
+                "org/apache/tiles/config/defs1.xml,org/apache/tiles/config/defs2.xml,"
+                + "org/apache/tiles/config/defs3.xml");
+        factory.init(params);
+
+        TilesRequestContext emptyContext = new MockOnlyLocaleTilesContext(null);
+        TilesRequestContext usContext = new MockOnlyLocaleTilesContext(Locale.US);
+        TilesRequestContext frenchContext = new MockOnlyLocaleTilesContext(Locale.FRENCH);
+        TilesRequestContext chinaContext = new MockOnlyLocaleTilesContext(Locale.CHINA);
+        TilesRequestContext canadaFrenchContext = new MockOnlyLocaleTilesContext(Locale.CANADA_FRENCH);
+
+        assertNotNull("test.def1 definition not found.", factory.getDefinition("test.def1", emptyContext));
+        assertNotNull("test.def2 definition not found.", factory.getDefinition("test.def2", emptyContext));
+        assertNotNull("test.def3 definition not found.", factory.getDefinition("test.def3", emptyContext));
+        assertNotNull("test.common definition not found.", factory.getDefinition("test.common", emptyContext));
+        assertNotNull("test.common definition in US locale not found.", factory
+                .getDefinition("test.common", usContext));
+        assertNotNull("test.common definition in FRENCH locale not found.",
+                factory.getDefinition("test.common", frenchContext));
+        assertNotNull("test.common definition in CHINA locale not found.",
+                factory.getDefinition("test.common", chinaContext));
+        assertNotNull(
+                "test.common.french definition in FRENCH locale not found.",
+                factory.getDefinition("test.common.french", frenchContext));
+        assertNotNull(
+                "test.common.french definition in CANADA_FRENCH locale not found.",
+                factory
+                        .getDefinition("test.common.french",
+                                canadaFrenchContext));
+        assertNotNull("test.def.toextend definition not found.", factory
+                .getDefinition("test.def.toextend", emptyContext));
+        assertNotNull("test.def.overridden definition not found.", factory
+                .getDefinition("test.def.overridden", emptyContext));
+        assertNotNull(
+                "test.def.overridden definition in FRENCH locale not found.",
+                factory.getDefinition("test.def.overridden", frenchContext));
+
+        assertEquals("Incorrect default country value", "default", factory
+                .getDefinition("test.def1", emptyContext).getAttribute(
+                        "country").getValue());
+        assertEquals("Incorrect US country value", "US", factory.getDefinition(
+                "test.def1", usContext).getAttribute("country").getValue());
+        assertEquals("Incorrect France country value", "France", factory
+                .getDefinition("test.def1", frenchContext).getAttribute(
+                        "country").getValue());
+        assertEquals("Incorrect Chinese country value (should be default)",
+                "default", factory.getDefinition("test.def1", chinaContext)
+                        .getAttribute("country").getValue());
+        assertEquals("Incorrect default country value", "default", factory
+                .getDefinition("test.def.overridden", emptyContext)
+                .getAttribute("country").getValue());
+        assertEquals("Incorrect default title value",
+                "Definition to be overridden", factory.getDefinition(
+                        "test.def.overridden", emptyContext).getAttribute(
+                        "title").getValue());
+        assertEquals("Incorrect France country value", "France", factory
+                .getDefinition("test.def.overridden", frenchContext)
+                .getAttribute("country").getValue());
+        assertEquals("Incorrect France title value",
+                "Definition to be extended", factory.getDefinition(
+                        "test.def.overridden", frenchContext).getAttribute(
+                        "title").getValue());
+    }
+
+    /**
+     * Tests the addDefinitions method under normal
+     * circumstances.
+     *
+     * @throws Exception If something goes wrong.
+     */
+    @SuppressWarnings("unchecked")
+    public void testReadByLocale() throws Exception {
+        // Set up multiple data sources.
+        URL url1 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs1.xml");
+        assertNotNull("Could not load defs1 file.", url1);
+        URL url2 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs2.xml");
+        assertNotNull("Could not load defs2 file.", url2);
+        URL url3 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs3.xml");
+        assertNotNull("Could not load defs3 file.", url3);
+
+        TilesApplicationContext applicationContext = EasyMock
+                .createMock(TilesApplicationContext.class);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs1.xml"))
+                .andReturn(url1);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs2.xml"))
+                .andReturn(url2);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs3.xml"))
+                .andReturn(url3);
+        EasyMock.replay(applicationContext);
+        factory.setApplicationContext(applicationContext);
+
+        Map<String, String> params = new HashMap<String, String>();
+        params.put(DefinitionsFactory.DEFINITIONS_CONFIG,
+                "org/apache/tiles/config/defs1.xml,org/apache/tiles/config/defs2.xml,"
+                + "org/apache/tiles/config/defs3.xml");
+        factory.init(params);
+
+        // Parse files.
+        TilesRequestContext usContext = new MockOnlyLocaleTilesContext(Locale.US);
+        TilesRequestContext frenchContext = new MockOnlyLocaleTilesContext(Locale.FRENCH);
+        TilesRequestContext chinaContext = new MockOnlyLocaleTilesContext(Locale.CHINA);
+
+        assertNotNull("test.def1 definition not found.", factory.getDefinition(
+                "test.def1", null));
+        assertNotNull("test.def1 US definition not found.", factory
+                .getDefinition("test.def1", usContext));
+        assertNotNull("test.def1 France definition not found.", factory
+                .getDefinition("test.def1", frenchContext));
+        assertNotNull("test.def1 China should return default.", factory
+                .getDefinition("test.def1", chinaContext));
+
+        assertEquals("Incorrect default country value", "default", factory
+                .getDefinition("test.def1", null).getAttribute(
+                        "country").getValue());
+        assertEquals("Incorrect US country value", "US", factory.getDefinition(
+                "test.def1", usContext).getAttribute("country").getValue());
+        assertEquals("Incorrect France country value", "France", factory
+                .getDefinition("test.def1", frenchContext).getAttribute(
+                        "country").getValue());
+        assertEquals("Incorrect Chinese country value (should default)",
+                "default", factory.getDefinition("test.def1", chinaContext)
+                        .getAttribute("country").getValue());
+    }
+
+    /**
+     * Tests the reader init param.
+     *
+     * @throws Exception If something goes wrong.
+     */
+    public void testReaderParam() throws Exception {
+        Map<String, String> params = new HashMap<String, String>();
+        params.put(DefinitionsFactory.READER_IMPL_PROPERTY,
+                "org.apache.tiles.definition.MockDefinitionsReader");
+
+        int instanceCount = MockDefinitionsReader.getInstanceCount();
+
+        LocaleDefinitionsFactory factory = new LocaleDefinitionsFactory();
+
+        // Set up multiple data sources.
+        URL url1 = this.getClass().getClassLoader().getResource(
+                "org/apache/tiles/config/defs1.xml");
+        assertNotNull("Could not load defs1 file.", url1);
+
+        TilesApplicationContext applicationContext = EasyMock
+                .createMock(TilesApplicationContext.class);
+        EasyMock.expect(applicationContext
+                .getResource("org/apache/tiles/config/defs1.xml"))
+                .andReturn(url1);
+        EasyMock.replay(applicationContext);
+        factory.setApplicationContext(applicationContext);
+
+        params.put(DefinitionsFactory.DEFINITIONS_CONFIG,
+                "org/apache/tiles/config/defs1.xml");
+        factory.init(params);
+
+        assertEquals("MockDefinitionsReader not used.",
+                instanceCount + 1,
+                MockDefinitionsReader.getInstanceCount());
+    }
+}

Propchange: tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/LocaleDefinitionsFactoryTest.java
------------------------------------------------------------------------------
    svn:eol-style = native

Propchange: tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/LocaleDefinitionsFactoryTest.java
------------------------------------------------------------------------------
    svn:keywords = Date Author Id Revision HeadURL

Modified: tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/TestReloadableDefinitionsFactory.java
URL: http://svn.apache.org/viewvc/tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/TestReloadableDefinitionsFactory.java?rev=669653&r1=669652&r2=669653&view=diff
==============================================================================
--- tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/TestReloadableDefinitionsFactory.java (original)
+++ tiles/framework/trunk/tiles-core/src/test/java/org/apache/tiles/definition/TestReloadableDefinitionsFactory.java Thu Jun 19 12:03:10 2008
@@ -157,7 +157,7 @@
         assertEquals("Incorrect initial template value", "/test.jsp",
                 definition.getTemplate());
 
-        ReloadableDefinitionsFactory reloadable = (ReloadableDefinitionsFactory) factory;
+        Refreshable reloadable = (Refreshable) factory;
         assertEquals("Factory should be fresh.", false,
                 reloadable.refreshRequired());