Author: oheger Date: Sun Sep 22 17:50:15 2013 New Revision: 1525400 URL: http://svn.apache.org/r1525400 Log: Added HomeDirectoryLocationStrategy.
This FileLocationStrategy implementation searches for files in a configurable home directory. Added: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/HomeDirectoryLocationStrategy.java commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/io/TestHomeDirectoryLocationStrategy.java Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/FileLocatorUtils.java Modified: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/FileLocatorUtils.java URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/FileLocatorUtils.java?rev=1525400&r1=1525399&r2=1525400&view=diff ============================================================================== --- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/FileLocatorUtils.java (original) +++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/FileLocatorUtils.java Sun Sep 22 17:50:15 2013 @@ -541,34 +541,46 @@ public final class FileLocatorUtils } else { - StringBuilder fName = new StringBuilder(); - fName.append(basePath); + file = new File(appendPath(basePath, fileName)); + } + + return file; + } - // My best friend. Paranoia. - if (!basePath.endsWith(File.separator)) - { - fName.append(File.separator); - } - - // - // We have a relative path, and we have - // two possible forms here. If we have the - // "./" form then just strip that off first - // before continuing. - // - if (fileName.startsWith("." + File.separator)) - { - fName.append(fileName.substring(2)); - } - else - { - fName.append(fileName); - } + /** + * Extends a path by another component. The given extension is added to the + * already existing path adding a separator if necessary. + * + * @param path the path to be extended + * @param ext the extension of the path + * @return the extended path + */ + static String appendPath(String path, String ext) + { + StringBuilder fName = new StringBuilder(); + fName.append(path); - file = new File(fName.toString()); + // My best friend. Paranoia. + if (!path.endsWith(File.separator)) + { + fName.append(File.separator); } - return file; + // + // We have a relative path, and we have + // two possible forms here. If we have the + // "./" form then just strip that off first + // before continuing. + // + if (ext.startsWith("." + File.separator)) + { + fName.append(ext.substring(2)); + } + else + { + fName.append(ext); + } + return fName.toString(); } /** Added: commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/HomeDirectoryLocationStrategy.java URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/HomeDirectoryLocationStrategy.java?rev=1525400&view=auto ============================================================================== --- commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/HomeDirectoryLocationStrategy.java (added) +++ commons/proper/configuration/trunk/src/main/java/org/apache/commons/configuration/io/HomeDirectoryLocationStrategy.java Sun Sep 22 17:50:15 2013 @@ -0,0 +1,172 @@ +/* + * 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.commons.configuration.io; + +import java.io.File; +import java.net.URL; + +import org.apache.commons.lang3.StringUtils; + +/** + * <p> + * A specialized implementation of {@code FileLocationStrategy} which searches + * for files in the user's home directory or another special configurable + * directory. + * </p> + * <p> + * This strategy implementation ignores the URL stored in the passed in + * {@link FileLocator}. It constructs a file path from the configured home + * directory (which is the user's home directory per default, but can be changed + * to another path), optionally the base path, and the file name. If the + * resulting path points to an existing file, its URL is returned. + * </p> + * <p> + * When constructing an instance it can be configured whether the base path + * should be taken into account. If this option is set, the base path is + * appended to the home directory if it is not <b>null</b>. This is useful for + * instance to select a specific sub directory of the user's home directory. If + * this option is set to <b>false</b>, the base path is always ignored, and only + * the file name is evaluated. + * </p> + * + * @version $Id: $ + */ +public class HomeDirectoryLocationStrategy implements FileLocationStrategy +{ + /** Constant for the system property with the user's home directory. */ + private static final String PROP_HOME = "user.home"; + + /** The home directory to be searched for the requested file. */ + private final String homeDirectory; + + /** The flag whether the base path is to be taken into account. */ + private final boolean evaluateBasePath; + + /** + * Creates a new instance of {@code HomeDirectoryLocationStrategy} and + * initializes it with the specified settings. + * + * @param homeDir the path to the home directory (can be <b>null</b>) + * @param withBasePath a flag whether the base path should be evaluated + */ + public HomeDirectoryLocationStrategy(String homeDir, boolean withBasePath) + { + homeDirectory = fetchHomeDirectory(homeDir); + evaluateBasePath = withBasePath; + } + + /** + * Creates a new instance of {@code HomeDirectoryLocationStrategy} and + * initializes the base path flag. The home directory is set to the user's + * home directory. + * + * @param withBasePath a flag whether the base path should be evaluated + */ + public HomeDirectoryLocationStrategy(boolean withBasePath) + { + this(null, withBasePath); + } + + /** + * Creates a new instance of {@code HomeDirectoryLocationStrategy} with + * default settings. The home directory is set to the user's home directory. + * The base path flag is set to <b>false</b> (which means that the base path + * is ignored). + */ + public HomeDirectoryLocationStrategy() + { + this(false); + } + + /** + * Returns the home directory. In this directory the strategy searches for + * files. + * + * @return the home directory used by this object + */ + public String getHomeDirectory() + { + return homeDirectory; + } + + /** + * Returns a flag whether the base path is to be taken into account when + * searching for a file. + * + * @return the flag whether the base path is evaluated + */ + public boolean isEvaluateBasePath() + { + return evaluateBasePath; + } + + /** + * {@inheritDoc} This implementation searches in the home directory for a + * file described by the passed in {@code FileLocator}. If the locator + * defines a base path and the {@code evaluateBasePath} property is + * <b>true</b>, a sub directory of the home directory is searched. + */ + public URL locate(FileSystem fileSystem, FileLocator locator) + { + if (StringUtils.isNotEmpty(locator.getFileName())) + { + String basePath = fetchBasePath(locator); + File file = + FileLocatorUtils.constructFile(basePath, + locator.getFileName()); + if (file.isFile()) + { + return FileLocatorUtils.convertFileToURL(file); + } + } + + return null; + } + + /** + * Determines the base path to be used for the current locate() operation. + * + * @param locator the {@code FileLocator} + * @return the base path to be used + */ + private String fetchBasePath(FileLocator locator) + { + if (isEvaluateBasePath() + && StringUtils.isNotEmpty(locator.getBasePath())) + { + return FileLocatorUtils.appendPath(getHomeDirectory(), + locator.getBasePath()); + } + else + { + return getHomeDirectory(); + } + } + + /** + * Obtains the home directory to be used by a new instance. If a directory + * name is provided, it is used. Otherwise, the user's home directory is + * looked up. + * + * @param homeDir the passed in home directory + * @return the directory to be used + */ + private static String fetchHomeDirectory(String homeDir) + { + return (homeDir != null) ? homeDir : System.getProperty(PROP_HOME); + } +} Added: commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/io/TestHomeDirectoryLocationStrategy.java URL: http://svn.apache.org/viewvc/commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/io/TestHomeDirectoryLocationStrategy.java?rev=1525400&view=auto ============================================================================== --- commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/io/TestHomeDirectoryLocationStrategy.java (added) +++ commons/proper/configuration/trunk/src/test/java/org/apache/commons/configuration/io/TestHomeDirectoryLocationStrategy.java Sun Sep 22 17:50:15 2013 @@ -0,0 +1,162 @@ +/* + * 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.commons.configuration.io; + +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertNull; +import static org.junit.Assert.assertTrue; + +import java.io.File; +import java.io.IOException; +import java.net.URL; + +import org.easymock.EasyMock; +import org.junit.Before; +import org.junit.Rule; +import org.junit.Test; +import org.junit.rules.TemporaryFolder; + +/** + * Test class for {@code HomeDirectoryLocationStrategy}. + * + * @version $Id: $ + */ +public class TestHomeDirectoryLocationStrategy +{ + /** Constant for a test file name. */ + private static final String FILE_NAME = "test.tst"; + + /** Constant for a base path to be used. */ + private static final String BASE_PATH = "sub"; + + /** An object for dealing with temporary files. */ + @Rule + public TemporaryFolder folder = new TemporaryFolder(); + + /** A mock for the file system. */ + private FileSystem fileSystem; + + @Before + public void setUp() throws Exception + { + fileSystem = EasyMock.createMock(FileSystem.class); + EasyMock.replay(fileSystem); + } + + /** + * Creates a strategy test object which uses the temporary root directory as + * its home directory. + * + * @param withBasePath the base path flag + * @return the test strategy + */ + private HomeDirectoryLocationStrategy setUpStrategy(boolean withBasePath) + { + return new HomeDirectoryLocationStrategy(folder.getRoot() + .getAbsolutePath(), withBasePath); + } + + /** + * Tests whether default values are correctly set by the constructor. + */ + @Test + public void testInitDefaults() + { + HomeDirectoryLocationStrategy strategy = + new HomeDirectoryLocationStrategy(); + assertEquals("Wrong home directory", System.getProperty("user.home"), + strategy.getHomeDirectory()); + assertFalse("Wrong base path flag", strategy.isEvaluateBasePath()); + } + + /** + * Tests whether a file can be located if the base path is ignored. + */ + @Test + public void testLocateSuccessIgnoreBasePath() throws IOException + { + File file = folder.newFile(FILE_NAME); + FileLocator locator = + FileLocatorUtils.fileLocator().basePath(BASE_PATH) + .fileName(FILE_NAME).create(); + HomeDirectoryLocationStrategy strategy = setUpStrategy(false); + URL url = strategy.locate(fileSystem, locator); + assertEquals("Wrong URL", file.getAbsoluteFile(), FileLocatorUtils + .fileFromURL(url).getAbsoluteFile()); + } + + /** + * Tests whether the base is actually evaluated if the flag is set. + */ + @Test + public void testLocateFailedWithBasePath() throws IOException + { + folder.newFile(FILE_NAME); + FileLocator locator = + FileLocatorUtils.fileLocator().basePath(BASE_PATH) + .fileName(FILE_NAME).create(); + HomeDirectoryLocationStrategy strategy = setUpStrategy(true); + assertNull("Got a URL", strategy.locate(fileSystem, locator)); + } + + /** + * Tests whether a file in a sub folder can be located. + */ + @Test + public void testLocateSuccessInSubFolder() throws IOException + { + File sub = folder.newFolder(BASE_PATH); + File file = new File(sub, FILE_NAME); + assertTrue("Could not create file", file.createNewFile()); + FileLocator locator = + FileLocatorUtils.fileLocator().basePath(BASE_PATH) + .fileName(FILE_NAME).create(); + HomeDirectoryLocationStrategy strategy = setUpStrategy(true); + URL url = strategy.locate(fileSystem, locator); + assertEquals("Wrong URL", file.getAbsoluteFile(), FileLocatorUtils + .fileFromURL(url).getAbsoluteFile()); + } + + /** + * Tests a locate() operation which evaluates the base path if no base path + * is set. + */ + @Test + public void testLocateSuccessNoBasePath() throws IOException + { + File file = folder.newFile(FILE_NAME); + FileLocator locator = + FileLocatorUtils.fileLocator().fileName(FILE_NAME).create(); + HomeDirectoryLocationStrategy strategy = setUpStrategy(true); + URL url = strategy.locate(fileSystem, locator); + assertEquals("Wrong URL", file.getAbsoluteFile(), FileLocatorUtils + .fileFromURL(url).getAbsoluteFile()); + } + + /** + * Tests a locate() operation if no file name is specified. + */ + @Test + public void testNoFileName() + { + FileLocator locator = + FileLocatorUtils.fileLocator().basePath(BASE_PATH).create(); + HomeDirectoryLocationStrategy strategy = setUpStrategy(true); + assertNull("Got a URL", strategy.locate(fileSystem, locator)); + } +}