Docjar: A Java Source and Docuemnt Enginecom.*    java.*    javax.*    org.*    all    new    plug-in

Quick Search    Search Deep

Source code: mucode/util/Launcher.java


1   /* mucode - A lightweight and flexible mobile code toolkit
2    * Copyright (C) 2000, Gian Pietro Picco
3    *  
4    * This library is free software; you can redistribute it and/or
5    * modify it under the terms of the GNU Lesser General Public
6    * License as published by the Free Software Foundation; either
7    * version 2.1 of the License, or (at your option) any later version.
8    *  
9    * This library is distributed in the hope that it will be useful,
10   * but WITHOUT ANY WARRANTY; without even the implied warranty of
11   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12   * Lesser General Public License for more details.
13   * 
14   * You should have received a copy of the GNU Lesser General Public
15   * License along with this library; if not, write to the Free Software
16   * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17   */
18  package mucode.util;
19  
20  import mucode.*;
21  import java.util.*;
22  import java.io.*;
23  
24  /**
25   * This class simplifies the task of passing command line parameteres from an
26   * application to a <i>&micro;</i>Server embedded in it. It also provides a
27   * facilities for starting a <i>&micro;</i>Server directly from the command
28   * line.
29   *
30   * The class is essentially a wrapper around a <i>&micro;</i>Server. The
31   * method {@link #parseArgs parseArgs} allows parsing of command line
32   * arguments. <br>
33   *
34   * Command line options start with a dash (<code>"-"</code>). The set of
35   * recognized options is the same as the set of <i>&micro;</i>Server
36   * properties, defined in {@link MuConstants} and explained in {@link
37   * mucode.MuServer#properties}. An additional option
38   * <code>-propertyfile</code> is recognized, that allows to load properties
39   * from a configuration file, formatted as explained in {@link
40   * MuServer#loadProperties loadProperties}. This option is mutually exclusive
41   * with standard options: e.g., it is <b>not</b> possible to specify: <br>
42   * <code>java mucode.util.Launcher -propertyfile prop.cfg -debug on</code><br>
43   * 
44   * Options setting a value are followed by the value. Flags (e.g.,
45   * <code>"-debug"</code>) accept one of the values <code>on</code> and
46   * <code>off</code>. <br>
47   *
48   * The method {@link #launch launch} parses the command line arguments, and
49   * then starts the run-time support for the <i>&micro;</i>Server, by calling
50   * its {@link MuServer#boot boot} method.
51   *
52   * This class contains a <code>main()</code>, thus a <i>&micro;</i>Server
53   * listening on the specified port can be started directly from command
54   * line. <P>
55   * 
56   * <B>Example.</B> <code>java mucode.util.Launcher -debug on -port 2000</code>
57   * creates a new Java VM containing a <i>&micro;</i>Server that will listen on
58   * port <code>2000</code>, and will output debug messages.
59   *
60   * @author <a href="mailto:picco@elet.polimi.it">Gian Pietro Picco</a>
61   * @version 1.0 
62   *
63   * @see MuServer
64   * @see MuConstants
65   *  */
66  public class Launcher implements MuConstants {
67    private MuServer server = null;
68  
69    /**
70     * Create a new <code>Launcher</code>, operating on a new
71     * <i>&micro;</i>Server.
72     */
73    public Launcher() { server = new MuServer(); }
74  
75    /**
76     * Create a new <code>Launcher</code> operating on the specified
77     * <i>&micro;</i>Server.
78     */
79    public Launcher(MuServer server) { this.server = server; }
80  
81    /**
82     * Retrieve the <i>&micro;</i>Server this object is operating on.
83     *
84     * @return a <code>MuServer</code> value
85     */
86    public MuServer getServer() { return server; }
87  
88  
89    /**
90     * Parse a set of arguments (typically coming from the command line),
91     * starting at the specified <code>index</code>, and then start the
92     * <i>&micro;</i>Server associated with this object, by calling its {@link
93     * MuServer#boot} method.
94     *
95     * @param args the arguments
96     * @param index the index of the first element of <code>args</code> to be
97     * considered for parsing.
98     * */
99    public void launch(String[] args, int index) {
100     try {  
101       parseArgs(args, index);
102       server.boot();
103       //      if (server.isDebugOn()) server.properties.list(System.out);
104 server.properties.list(System.out);
105     } catch(IllegalArgumentException e) {
106       System.out.println(e.toString());
107       if (server.isMessagesOn()) printHelp();
108       System.exit(0);
109     } 
110   }
111 
112   /** Parse an array of <code>String</code> arguments, usually coming directly
113    *  from the command line. Useful when the <i>&micro;</i>Server is embedded
114    *  in an application that needs to specify its own arguments and still
115    *  needs to provide access to the <i>&micro;</i>Server's options through
116    *  the command line. The arguments for the <i>&micro;</i>Server must always
117    *  be the last ones in the argument array. Thus, for instance, in
118    * 
119    * <pre>java MyApplication myArg1 myArg2 -debug on -compression on</pre>
120    *
121    * if a variable <code>String[] args</code> contains the arguments passed to
122    * <code>MyApplication</code> on the command line (e.g., as retrieved from
123    * <code>MyApplication.main()</code>, the <i>&micro;</i>Server object can be
124    * configured with the options by invoking
125    * 
126    * <pre>
127    * MuServer s = MuServer();
128    * new Launcher(s).parseArgs(args, 2);
129    * </pre>
130    * 
131    * @param args the arguments
132    * @param index the index of the first element of <code>args</code> to be
133    * considered for parsing. */ 
134   public void parseArgs(String[] args, int index) {
135     if (args.length != 0) {
136       if (index < 0 || index > args.length || args == null) 
137         throw new IllegalArgumentException();
138       if (args[0].equals("-propertyfile")) {
139         if (args.length != 2) {
140           printHelp();
141           System.exit(0);
142         } else {
143           try {
144             server.loadProperties(args[1]);
145           } catch(FileNotFoundException fe) {
146             System.out.println("Property file " + args[1] +
147                                " not found. Halting...");
148             System.exit(0);
149           } catch(IOException e) {
150             System.out.println("I/O problems. Halting...");
151             e.printStackTrace();
152             System.exit(0);
153           }
154         } // end of else
155       } else {
156         int i = index;
157         while (i < args.length) {
158           // Parse single arguments
159           if (args[i].equals("-" + PORTkey) || 
160               args[i].equals("-" + TIMEOUTkey))
161             server.setProperty(args[i].substring(1), args[++i]);
162           // Parse flag arguments
163           else if (args[i].equals("-" + COMPRESSIONkey) ||
164                    args[i].equals("-" + DEBUGkey) ||
165                    args[i].equals("-" + MESSAGESkey) ||
166                    args[i].equals("-" + ERRORSkey))
167             server.setProperty(args[i].substring(1), parseFlag(args[++i])); 
168           else if (args[i].equals("-" + UBICLASSESkey)) {
169             
170             String[] classnames = parseMultipleArgs(args, ++i);
171             i = i + classnames.length;
172             String propvalue = "";
173             for (int j = 0; j < classnames.length; j++) {
174               server.addUbiquitousClass(classnames[j]);
175               propvalue = propvalue + classnames[j] + " ";
176             }
177             server.setProperty(UBICLASSESkey, propvalue);
178           }
179           else if (args[i].equals("-" + UBIPACKAGESkey)) {
180             String[] packagenames = parseMultipleArgs(args, i++);
181             i = i + packagenames.length;
182             String propvalue = "";
183             for (int j = 0; j < packagenames.length; j++) {
184               server.addUbiquitousPackage(packagenames[j]);
185               propvalue = propvalue + packagenames[j] + " ";
186             }
187             server.setProperty(UBIPACKAGESkey, propvalue);
188           }
189           else throw new IllegalArgumentException(args[i]);
190           i++;
191         }
192       }
193     }
194   }
195 
196   private String[] parseMultipleArgs(String[] args, int start) {
197     int i = start; 
198     Vector vr = new Vector();
199 
200     while (i < args.length && !isFlag(args[i])) {
201       vr.addElement(args[i]);
202       i++;
203     } // end of while ()
204 
205     String[] res = new String[vr.size()];
206     vr.copyInto(res);
207     return res;
208   }
209 
210   private boolean isFlag(String arg) { return arg.startsWith("-"); }
211   
212   private String parseFlag(String flag) { 
213     if (flag.equals("on")) return "true";
214     else if (flag.equals("off")) return "false";
215     else throw new IllegalArgumentException(flag);
216   }
217 
218   private static void printHelp() {
219     System.out.println("Usage: java mucode.util.Launcher ");
220     System.out.println("                            "+
221                        "[-port <number>]");
222     System.out.println("                            "+
223                        "[-timeout <millisec>]");
224     System.out.println("                            "+
225                        "[-compression {on|off}]");
226     System.out.println("                            "+
227                        "[-debug {on|off}]");
228     System.out.println("                            "+
229                        "[-messages {on|off}]");
230     System.out.println("                            "+
231                        "[-errors {on|off}]");  
232     System.out.println("                            "+
233                        "[-ubiclasses <classname1 classname2 ...>]");  
234     System.out.println("                            "+
235                        "[-ubipackages <packagename1 packagename2 ...>]");  
236     System.out.println("                            "+
237                        "[-propertyfile <filename>]");  
238     System.out.println("The -propertyfile option is mutually exclusive with all the other options.");
239   }
240 
241   /** Create and start a <i>&micro;</i>Server directly from the command
242       line, by specifying command line options. */
243   public static void main(String[] args){
244     new Launcher().launch(args, 0);
245   }
246 }