Java tutorial
/* * $Id: UrlDefinitionsFactory.java 734996 2009-01-16 13:27:28Z apetrelli $ * * 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 org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.apache.tiles.Definition; import org.apache.tiles.context.TilesRequestContext; import org.apache.tiles.definition.dao.DefinitionDAO; import org.apache.tiles.definition.dao.ResolvingLocaleUrlDefinitionDAO; import org.apache.tiles.definition.dao.URLReader; import org.apache.tiles.impl.BasicTilesContainer; import org.apache.tiles.util.LocaleUtil; import java.net.URL; import java.util.ArrayList; import java.util.List; import java.util.Locale; import java.util.Map; import java.util.StringTokenizer; /** * {@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> * * @version $Rev: 734996 $ $Date: 2009-01-16 14:27:28 +0100 (Fri, 16 Jan 2009) $ */ public class UrlDefinitionsFactory extends LocaleDefinitionsFactory implements Refreshable { /** * Compatibility constant. * * @deprecated use {@link DEFINITIONS_CONFIG} to avoid namespace collisions. */ private static final String LEGACY_DEFINITIONS_CONFIG = "definitions-config"; /** * LOG instance for all UrlDefinitionsFactory instances. */ private final Log log = LogFactory.getLog(UrlDefinitionsFactory.class); /** * Contains the URL objects identifying where configuration data is found. * * @deprecated Use {@link #sourceURLs}. */ protected List<Object> sources; /** * Reader used to get definitions from the sources. * * @deprecated No more used. */ protected DefinitionsReader reader; /** * Contains the dates that the URL sources were last modified. * * @deprecated No more used. */ protected Map<String, Long> lastModifiedDates; /** * Returns a Definition object that matches the given name and * Tiles context. * * @param name The name of the Definition to return. * @param tilesContext The Tiles context to use to resolve the definition. * @return the Definition matching the given name or null if none * is found. * @throws DefinitionsFactoryException if an error occurs reading definitions. */ @Override public Definition getDefinition(String name, TilesRequestContext tilesContext) { Locale locale = localeResolver.resolveLocale(tilesContext); return definitionDao.getDefinition(name, locale); } /** {@inheritDoc} */ public synchronized void refresh() { log.debug("Updating Tiles definitions. . ."); if (definitionDao instanceof Refreshable) { ((Refreshable) definitionDao).refresh(); } } /** * 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(); } /** * Indicates whether a given context has been processed or not. * <p/> * This method can be used to avoid unnecessary synchronization of the * DefinitionsFactory in multi-threaded situations. Check the return of * isContextProcessed before synchronizing the object and reading * locale-specific definitions. * * @param tilesContext The Tiles context to check. * @return true if the given context has been processed and false otherwise. * @deprecated It always return <code>true</code>. */ @Deprecated protected boolean isContextProcessed(TilesRequestContext tilesContext) { return true; } /** * 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 ResolvingLocaleUrlDefinitionDAO(); } /** * 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() { return new CompatibilityDefinitionsImpl(definitionDao); } /** * Returns the definitions holder object. * * @return The definitions holder. * @deprecated Do not use! Deprecated with no replacement. */ @Deprecated protected Definitions getDefinitions() { return new CompatibilityDefinitionsImpl(definitionDao); } /** * 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 Let the definitions be loaded by a {@link DefinitionDAO}. */ @Deprecated protected void addDefinitions(Definitions definitions, TilesRequestContext tilesContext) { Locale locale = localeResolver.resolveLocale(tilesContext); Map<String, Definition> defsMap = definitionDao.getDefinitions(locale); if (defsMap == null) { throw new NullPointerException("There are no definitions mapped to locale '" + locale.toString() + "'"); } } /** * 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 CompatibilityDefinitionsImpl(definitionDao); } /** * 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; } /** * {@link Definitions} implementation that uses a {@link DefinitionDAO}. * * @since 2.1.0 * @deprecated Here only for compatibility reasons. */ @Deprecated private static final class CompatibilityDefinitionsImpl implements Definitions { /** * The definition DAO to use. * * @since 2.1.0 */ private DefinitionDAO<Locale> definitionDao; /** * Constructor. * * @param definitionDao The definition DAO to use. * @since 2.1.0 */ public CompatibilityDefinitionsImpl(DefinitionDAO<Locale> definitionDao) { this.definitionDao = definitionDao; } /** {@inheritDoc} */ public void addDefinitions(Map<String, Definition> defsMap) { Map<String, Definition> definitions = definitionDao.getDefinitions(null); if (definitions == null) { throw new NullPointerException("No definitions loaded for default locale"); } definitions.putAll(defsMap); } /** {@inheritDoc} */ public void addDefinitions(Map<String, Definition> defsMap, Locale locale) { Map<String, Definition> definitions = definitionDao.getDefinitions(locale); if (definitions == null) { throw new NullPointerException("No definitions loaded for locale '" + locale.toString() + "'"); } definitions.putAll(defsMap); } /** {@inheritDoc} */ public Map<String, Definition> getBaseDefinitions() { return definitionDao.getDefinitions(null); } /** {@inheritDoc} */ public Definition getDefinition(String name) { return definitionDao.getDefinition(name, null); } /** {@inheritDoc} */ public Definition getDefinition(String name, Locale locale) { return definitionDao.getDefinition(name, locale); } /** {@inheritDoc} */ public void reset() { if (definitionDao instanceof Refreshable) { ((Refreshable) definitionDao).refresh(); } } /** {@inheritDoc} */ public void resolveInheritances() { // Does nothing. } /** {@inheritDoc} */ public void resolveInheritances(Locale locale) { // Does nothing. } } }