View Javadoc

    1   /*
    2    * Licensed to the Apache Software Foundation (ASF) under one or more
    3    * contributor license agreements.  See the NOTICE file distributed with
    4    * this work for additional information regarding copyright ownership.
    5    * The ASF licenses this file to You under the Apache License, Version 2.0
    6    * (the "License"); you may not use this file except in compliance with
    7    * the License.  You may obtain a copy of the License at
    8    *
    9    *     http://www.apache.org/licenses/LICENSE-2.0
    10   *
    11   * Unless required by applicable law or agreed to in writing, software
    12   * distributed under the License is distributed on an "AS IS" BASIS,
    13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    14   * See the License for the specific language governing permissions and
    15   * limitations under the License.
    16   */
    17  package org.apache.commons.configuration;
    18
    19  import java.lang.reflect.Method;
    20  import java.util.Collection;
    21  import java.util.HashMap;
    22  import java.util.Iterator;
    23  import java.util.Map;
    24
    25  import org.apache.commons.lang.SystemUtils;
    26  import org.apache.tools.ant.taskdefs.Execute;
    27
    28  /***
    29   * <p>
    30   * A Configuration implementation that reads the platform specific environment
    31   * variables. On pre java5 JRE it uses Ant Execute task to read the environment.
    32   * (in this case ant must be present in classpath). On java >= 5 JRE it uses
    33   * {@link java.lang.System#getenv()} and ant is not required.
    34   * </p>
    35   * <p>
    36   * This configuration implementation is read-only. It allows read access to the
    37   * defined OS environment variables, but their values cannot be changed.
    38   * </p>
    39   * <p>
    40   * Usage of this class is easy: After an instance has been created the get
    41   * methods provided by the <code>Configuration</code> interface can be used
    42   * for querying environment variables, e.g.:
    43   *
    44   * <pre>
    45   * Configuration envConfig = new EnvironmentConfiguration();
    46   * System.out.println("JAVA_HOME=" + envConfig.getString("JAVA_HOME");
    47   * </pre>
    48   *
    49   * </p>
    50   *
    51   * @author <a href="mailto:nicolas.deloof@gmail.com">Nicolas De Loof</a>
    52   * @see org.apache.tools.ant.taskdefs.Execute#getProcEnvironment()
    53   * @since 1.5
    54   */
    55  public class EnvironmentConfiguration extends AbstractConfiguration
    56  {
    57      /*** Constant for the name of the getenv() method. */
    58      private static final String METHOD_NAME = "getenv";
    59
    60      /*** Constant for the Java version 1.5. */
    61      private static final int VERSION_1_5 = 150;
    62
    63      /*** Stores the environment properties. */
    64      private Map environment;
    65
    66      /***
    67       * Constructor.
    68       */
    69      public EnvironmentConfiguration()
    70      {
    71          if (SystemUtils.isJavaVersionAtLeast(VERSION_1_5))
    72          {
    73              extractProperties15();
    74          }
    75          else
    76          {
    77              extractProperties14();
    78          }
    79      }
    80
    81      /***
    82       * Adds a property to this configuration. Because this configuration is
    83       * read-only, this operation is not allowed and will cause an exception.
    84       *
    85       * @param key the key of the property to be added
    86       * @param value the property value
    87       */
    88      protected void addPropertyDirect(String key, Object value)
    89      {
    90          throw new UnsupportedOperationException("Configuration is read-only!");
    91      }
    92
    93      /***
    94       * {@inheritDoc}
    95       *
    96       * @see org.apache.commons.configuration.AbstractConfiguration#containsKey(java.lang.String)
    97       */
    98      public boolean containsKey(String key)
    99      {
    100         return environment.containsKey(key);
    101     }
    102
    103     /***
    104      * {@inheritDoc}
    105      *
    106      * @see org.apache.commons.configuration.AbstractConfiguration#getKeys()
    107      */
    108     public Iterator getKeys()
    109     {
    110         return environment.keySet().iterator();
    111     }
    112
    113     /***
    114      * {@inheritDoc}
    115      *
    116      * @see org.apache.commons.configuration.AbstractConfiguration#getProperty(java.lang.String)
    117      */
    118     public Object getProperty(String key)
    119     {
    120         return environment.get(key);
    121     }
    122
    123     /***
    124      * {@inheritDoc}
    125      *
    126      * @see org.apache.commons.configuration.AbstractConfiguration#isEmpty()
    127      */
    128     public boolean isEmpty()
    129     {
    130         return environment.isEmpty();
    131     }
    132
    133     /***
    134      * Removes a property from this configuration. Because this configuration is
    135      * read-only, this operation is not allowed and will cause an exception.
    136      *
    137      * @param key the key of the property to be removed
    138      */
    139     public void clearProperty(String key)
    140     {
    141         throw new UnsupportedOperationException("Configuration is read-only!");
    142     }
    143
    144     /***
    145      * Removes all properties from this configuration. Because this
    146      * configuration is read-only, this operation is not allowed and will cause
    147      * an exception.
    148      */
    149     public void clear()
    150     {
    151         throw new UnsupportedOperationException("Configuration is read-only!");
    152     }
    153
    154     /***
    155      * Extracts environment properties on a JRE &lt; 1.5. This implementation
    156      * uses ant for this purpose.
    157      */
    158     void extractProperties14()
    159     {
    160         extractPropertiesFromCollection(Execute.getProcEnvironment());
    161     }
    162
    163     /***
    164      * An internally used method for processing a collection with environment
    165      * entries. The collection must contain strings like
    166      * <code>property=value</code>. Such a collection is returned by ant.
    167      *
    168      * @param env the collection with the properties
    169      */
    170     void extractPropertiesFromCollection(Collection env)
    171     {
    172         environment = new HashMap();
    173         for (Iterator it = env.iterator(); it.hasNext();)
    174         {
    175             String entry = (String) it.next();
    176             int pos = entry.indexOf('=');
    177             if (pos == -1)
    178             {
    179                 getLogger().warn("Ignoring: " + entry);
    180             }
    181             else
    182             {
    183                 environment.put(entry.substring(0, pos), entry
    184                         .substring(pos + 1));
    185             }
    186         }
    187     }
    188
    189     /***
    190      * Extracts environment properties on a JR &gt;= 1.5. From this Java version
    191      * on, there is an official way of doing this. However because the code
    192      * should compile on lower Java versions, too, we have to invoke the method
    193      * using reflection.
    194      */
    195     void extractProperties15()
    196     {
    197         try
    198         {
    199             Method method = System.class.getMethod(METHOD_NAME, null);
    200             environment = (Map) method.invoke(null, null);
    201         }
    202         catch (Exception ex)
    203         {
    204             // this should normally not happen on a JRE >= 1.5
    205             throw new ConfigurationRuntimeException(
    206                     "Error when accessing environment properties", ex);
    207         }
    208     }
    209 }