Coverage Report - org.mule.util.SystemUtils
 
Classes in this File Line Coverage Branch Coverage Complexity
SystemUtils
51%
58/113
50%
33/66
4.3
 
 1  
 /*
 2  
  * $Id: SystemUtils.java 10404 2008-01-18 17:06:25Z dirk.olmes $
 3  
  * --------------------------------------------------------------------------------------
 4  
  * Copyright (c) MuleSource, Inc.  All rights reserved.  http://www.mulesource.com
 5  
  *
 6  
  * The software in this package is published under the terms of the CPAL v1.0
 7  
  * license, a copy of which has been included with this distribution in the
 8  
  * LICENSE.txt file.
 9  
  */
 10  
 
 11  
 package org.mule.util;
 12  
 
 13  
 import org.mule.MuleException;
 14  
 
 15  
 import java.io.BufferedReader;
 16  
 import java.io.InputStreamReader;
 17  
 import java.lang.reflect.Method;
 18  
 import java.util.Collections;
 19  
 import java.util.HashMap;
 20  
 import java.util.Map;
 21  
 
 22  
 import org.apache.commons.cli.BasicParser;
 23  
 import org.apache.commons.cli.CommandLine;
 24  
 import org.apache.commons.cli.Option;
 25  
 import org.apache.commons.cli.Options;
 26  
 import org.apache.commons.cli.ParseException;
 27  
 import org.apache.commons.logging.Log;
 28  
 import org.apache.commons.logging.LogFactory;
 29  
 
 30  
 // @ThreadSafe
 31  0
 public class SystemUtils extends org.apache.commons.lang.SystemUtils
 32  
 {
 33  
     // class logger
 34  6
     protected static final Log logger = LogFactory.getLog(SystemUtils.class);
 35  
 
 36  
     // bash prepends: declare -x
 37  
     // zsh prepends: typeset -x
 38  2
     private static final String[] UNIX_ENV_PREFIXES = new String[]{"declare -", "typeset -"};
 39  
 
 40  
     // the environment of the VM process
 41  2
     private static Map environment = null;
 42  
 
 43  
     /**
 44  
      * Get the operating system environment variables. This should work for Windows
 45  
      * and Linux.
 46  
      * 
 47  
      * @return Map<String, String> or an empty map if there was an error.
 48  
      */
 49  
     public static synchronized Map getenv()
 50  
     {
 51  6
         if (environment == null)
 52  
         {
 53  
             try
 54  
             {
 55  2
                 if (SystemUtils.IS_JAVA_1_4)
 56  
                 {
 57  
                     // fallback to external process
 58  0
                     environment = Collections.unmodifiableMap(getenvJDK14());
 59  
                 }
 60  
                 else
 61  
                 {
 62  
                     // the following runaround is necessary since we still want to
 63  
                     // compile on JDK 1.4
 64  2
                     Class target = System.class;
 65  2
                     Method envMethod = target.getMethod("getenv", ArrayUtils.EMPTY_CLASS_ARRAY);
 66  2
                     environment = Collections.unmodifiableMap((Map) envMethod.invoke(target, (Class[]) null));
 67  
                 }
 68  
             }
 69  0
             catch (Exception ex)
 70  
             {
 71  0
                 logger.error("Could not access OS environment: ", ex);
 72  0
                 environment = Collections.EMPTY_MAP;
 73  2
             }
 74  
         }
 75  
 
 76  6
         return environment;
 77  
     }
 78  
 
 79  
     private static Map getenvJDK14() throws Exception
 80  
     {
 81  0
         Map env = new HashMap();
 82  0
         Process process = null;
 83  
 
 84  
         try
 85  
         {
 86  0
             boolean isUnix = true;
 87  
             String command;
 88  
 
 89  0
             if (SystemUtils.IS_OS_WINDOWS)
 90  
             {
 91  0
                 command = "cmd /c set";
 92  0
                 isUnix = false;
 93  
             }
 94  
             else
 95  
             {
 96  0
                 command = "env";
 97  
             }
 98  
 
 99  0
             process = Runtime.getRuntime().exec(command);
 100  0
             BufferedReader br = new BufferedReader(new InputStreamReader(process.getInputStream()));
 101  
 
 102  
             String line;
 103  0
             while ((line = br.readLine()) != null)
 104  
             {
 105  0
                 for (int prefix = 0; prefix < UNIX_ENV_PREFIXES.length; prefix++)
 106  
                 {
 107  0
                     if (line.startsWith(UNIX_ENV_PREFIXES[prefix]))
 108  
                     {
 109  0
                         line = line.substring(UNIX_ENV_PREFIXES[prefix].length());
 110  
                     }
 111  
                 }
 112  
 
 113  0
                 int index = -1;
 114  0
                 if ((index = line.indexOf('=')) > -1)
 115  
                 {
 116  0
                     String key = line.substring(0, index).trim();
 117  0
                     String value = line.substring(index + 1).trim();
 118  
                     // remove quotes, if any
 119  0
                     if (isUnix && value.length() > 1 && (value.startsWith("\"") || value.startsWith("'")))
 120  
                     {
 121  0
                         value = value.substring(1, value.length() - 1);
 122  
                     }
 123  0
                     env.put(key, value);
 124  0
                 }
 125  
                 else
 126  
                 {
 127  0
                     env.put(line, StringUtils.EMPTY);
 128  
                 }
 129  0
             }
 130  
         }
 131  0
         catch (Exception e)
 132  
         {
 133  0
             throw e; // bubble up
 134  
         }
 135  
         finally
 136  
         {
 137  0
             if (process != null)
 138  
             {
 139  0
                 process.destroy();
 140  
             }
 141  
         }
 142  
 
 143  0
         return env;
 144  
     }
 145  
 
 146  
     public static String getenv(String name)
 147  
     {
 148  2
         return (String) SystemUtils.getenv().get(name);
 149  
     }
 150  
 
 151  
     public static boolean isSunJDK()
 152  
     {
 153  0
         return SystemUtils.JAVA_VM_VENDOR.toUpperCase().indexOf("SUN") != -1;
 154  
     }
 155  
 
 156  
     public static boolean isIbmJDK()
 157  
     {
 158  16
         return SystemUtils.JAVA_VM_VENDOR.toUpperCase().indexOf("IBM") != -1;
 159  
     }
 160  
 
 161  
     private static CommandLine parseCommandLine(String args[], String opts[][]) throws MuleException
 162  
     {
 163  0
         Options options = new Options();
 164  0
         for (int i = 0; i < opts.length; i++)
 165  
         {
 166  0
             options.addOption(opts[i][0], opts[i][1].equals("true") ? true : false, opts[i][2]);
 167  
         }
 168  
 
 169  0
         BasicParser parser = new BasicParser();
 170  
 
 171  
         try
 172  
         {
 173  0
             CommandLine line = parser.parse(options, args, true);
 174  0
             if (line == null)
 175  
             {
 176  0
                 throw new MuleException("Unknown error parsing the Mule command line");
 177  
             }
 178  
 
 179  0
             return line;
 180  
         }
 181  0
         catch (ParseException p)
 182  
         {
 183  0
             throw new MuleException("Unable to parse the Mule command line because of: " + p.toString(), p);
 184  
         }
 185  
     }
 186  
 
 187  
     /**
 188  
      * Returns the value corresponding to the given option from the command line, for
 189  
      * example if the options are "-config mule-config.xml"
 190  
      * getCommandLineOption("config") would return "mule-config.xml"
 191  
      */
 192  
     public static String getCommandLineOption(String option, String args[], String opts[][])
 193  
         throws MuleException
 194  
     {
 195  0
         CommandLine line = parseCommandLine(args, opts);
 196  0
         return line.getOptionValue(option);
 197  
     }
 198  
 
 199  
     /**
 200  
      * Checks whether a command line option is set. This is useful for command line
 201  
      * options that don't have an argument, like "-cluster", which means that this
 202  
      * Mule instance is part of a cluster.
 203  
      */
 204  
     public static boolean hasCommandLineOption(String option, String args[], String opts[][])
 205  
         throws MuleException
 206  
     {
 207  0
         CommandLine line = parseCommandLine(args, opts);
 208  0
         return line.hasOption(option);
 209  
     }
 210  
 
 211  
     /**
 212  
      * Returns a Map of all options in the command line. The Map is keyed off the
 213  
      * option name. The value will be whatever is present on the command line.
 214  
      * Options that don't have an argument will have the String "true".
 215  
      */
 216  
     public static Map getCommandLineOptions(String args[], String opts[][]) throws MuleException
 217  
     {
 218  0
         CommandLine line = parseCommandLine(args, opts);
 219  0
         Map ret = new HashMap();
 220  0
         Option[] options = line.getOptions();
 221  
 
 222  0
         for (int i = 0; i < options.length; i++)
 223  
         {
 224  0
             Option option = options[i];
 225  0
             ret.put(option.getOpt(), option.getValue("true"));
 226  
         }
 227  
 
 228  0
         return ret;
 229  
     }
 230  
 
 231  
     /**
 232  
      * Returns a Map of all valid property definitions in <code>-Dkey=value</code>
 233  
      * format. <code>-Dkey</code> is interpreted as <code>-Dkey=true</code>,
 234  
      * everything else is ignored. Whitespace in values is properly handled but needs
 235  
      * to be quoted properly: <code>-Dkey="some value"</code>.
 236  
      * 
 237  
      * @param input String with property definitionn
 238  
      * @return a {@link Map} of property String keys with their defined values
 239  
      *         (Strings). If no valid key-value pairs can be parsed, the map is
 240  
      *         empty.
 241  
      */
 242  
     public static Map parsePropertyDefinitions(String input)
 243  
     {
 244  46
         if (StringUtils.isEmpty(input))
 245  
         {
 246  4
             return Collections.EMPTY_MAP;
 247  
         }
 248  
 
 249  
         // the result map of property key/value pairs
 250  42
         final Map result = new HashMap();
 251  
 
 252  
         // where to begin looking for key/value tokens
 253  42
         int tokenStart = 0;
 254  
 
 255  
         // this is the main loop that scans for all tokens
 256  84
         findtoken : while (tokenStart < input.length())
 257  
         {
 258  
             // find first definition or bail
 259  70
             tokenStart = StringUtils.indexOf(input, "-D", tokenStart);
 260  70
             if (tokenStart == StringUtils.INDEX_NOT_FOUND)
 261  
             {
 262  20
                 break findtoken;
 263  
             }
 264  
             else
 265  
             {
 266  
                 // skip leading -D
 267  50
                 tokenStart += 2;
 268  
             }
 269  
 
 270  
             // find key
 271  50
             int keyStart = tokenStart;
 272  50
             int keyEnd = keyStart;
 273  
 
 274  50
             if (keyStart == input.length())
 275  
             {
 276  
                 // short input: '-D' only
 277  4
                 break;
 278  
             }
 279  
 
 280  
             // let's check out what we have next
 281  46
             char cursor = input.charAt(keyStart);
 282  
 
 283  
             // '-D xxx'
 284  46
             if (cursor == ' ')
 285  
             {
 286  2
                 continue findtoken;
 287  
             }
 288  
 
 289  
             // '-D='
 290  44
             if (cursor == '=')
 291  
             {
 292  
                 // skip over garbage to next potential definition
 293  10
                 tokenStart = StringUtils.indexOf(input, ' ', tokenStart);
 294  10
                 if (tokenStart != StringUtils.INDEX_NOT_FOUND)
 295  
                 {
 296  
                     // '-D= ..' - continue with next token
 297  6
                     continue findtoken;
 298  
                 }
 299  
                 else
 300  
                 {
 301  
                     // '-D=' - get out of here
 302  
                     break findtoken;
 303  
                 }
 304  
             }
 305  
 
 306  
             // apparently there's a key, so find the end
 307  166
             findkey : while (keyEnd < input.length())
 308  
             {
 309  158
                 cursor = input.charAt(keyEnd);
 310  
 
 311  
                 // '-Dkey ..'
 312  158
                 if (cursor == ' ')
 313  
                 {
 314  4
                     tokenStart = keyEnd;
 315  4
                     break findkey;
 316  
                 }
 317  
 
 318  
                 // '-Dkey=..'
 319  154
                 if (cursor == '=')
 320  
                 {
 321  22
                     break findkey;
 322  
                 }
 323  
 
 324  
                 // keep looking
 325  132
                 keyEnd++;
 326  
             }
 327  
 
 328  
             // yay, finally a key
 329  34
             String key = StringUtils.substring(input, keyStart, keyEnd);
 330  
 
 331  
             // assume that there is no value following
 332  34
             int valueStart = keyEnd;
 333  34
             int valueEnd = keyEnd;
 334  
 
 335  
             // default value
 336  34
             String value = "true";
 337  
 
 338  
             // now find the value, but only if the current cursor is not a space
 339  34
             if (keyEnd < input.length() && cursor != ' ')
 340  
             {
 341  
                 // bump value start/end
 342  22
                 valueStart = keyEnd + 1;
 343  22
                 valueEnd = valueStart;
 344  
 
 345  
                 // '-Dkey="..'
 346  22
                 cursor = input.charAt(valueStart);
 347  22
                 if (cursor == '"')
 348  
                 {
 349  
                     // opening "
 350  10
                     valueEnd = StringUtils.indexOf(input, '"', ++valueStart);
 351  
                 }
 352  
                 else
 353  
                 {
 354  
                     // unquoted value
 355  12
                     valueEnd = StringUtils.indexOf(input, ' ', valueStart);
 356  
                 }
 357  
 
 358  
                 // no '"' or ' ' delimiter found - use the rest of the string
 359  22
                 if (valueEnd == StringUtils.INDEX_NOT_FOUND)
 360  
                 {
 361  6
                     valueEnd = input.length();
 362  
                 }
 363  
 
 364  
                 // create value
 365  22
                 value = StringUtils.substring(input, valueStart, valueEnd);
 366  
             }
 367  
 
 368  
             // finally create key and value && loop again for next token
 369  34
             result.put(key, value);
 370  
 
 371  
             // start next search at end of value
 372  34
             tokenStart = valueEnd;
 373  34
         }
 374  
 
 375  42
         return result;
 376  
     }
 377  
 
 378  
 }