/**
* ***************************************************************
* JADE - Java Agent DEvelopment Framework is a framework to develop
* multi-agent systems in compliance with the FIPA specifications.
* Copyright (C) 2000 CSELT S.p.A.
*
* GNU Lesser General Public License
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation,
* version 2.1 of the License.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
* **************************************************************
*/
package jade;
//#MIDP_EXCLUDE_FILE
import jade.core.Runtime;
import jade.core.Profile;
import jade.core.ProfileImpl;
import jade.core.ProfileException;
import jade.util.leap.Properties;
import jade.util.ExtendedProperties;
import jade.util.Logger;
/**
* Boots the <B><em>JADE</em></b> system, parsing command line arguments.
*
* @author Giovanni Rimassa - Universita' di Parma
* @author Giovanni Caire - TILAB
* @author Nicolas Lhuillier - Motorola
* @author Jerome Picault - Motorola
* @version $Date: 2010-04-19 16:16:41 +0200 (lun, 19 apr 2010) $ $Revision: 6320 $
*
*/
public class Boot {
public static final String DEFAULT_FILENAME = "leap.properties";
private static Logger logger = Logger.getMyLogger("jade.Boot");
/**
* Fires up the <b><em>JADE</em></b> system.
* This method initializes the Profile Manager and then starts the
* bootstrap process for the <B><em>JADE</em></b>
* agent platform.
*/
public static void main(String args[]) {
try {
// Create the Profile
ProfileImpl p = null;
if (args.length > 0) {
if (args[0].startsWith("-")) {
// Settings specified as command line arguments
Properties pp = parseCmdLineArgs(args);
if (pp != null) {
p = new ProfileImpl(pp);
}
else {
// One of the "exit-immediately" options was specified!
return;
}
}
else {
// Settings specified in a property file
p = new ProfileImpl(args[0]);
}
}
else {
// Settings specified in the default property file
p = new ProfileImpl(DEFAULT_FILENAME);
}
// Start a new JADE runtime system
Runtime.instance().setCloseVM(true);
//#PJAVA_EXCLUDE_BEGIN
// Check whether this is the Main Container or a peripheral container
if (p.getBooleanProperty(Profile.MAIN, true)) {
Runtime.instance().createMainContainer(p);
} else {
Runtime.instance().createAgentContainer(p);
}
//#PJAVA_EXCLUDE_END
/*#PJAVA_INCLUDE_BEGIN
// Starts the container in SINGLE_MODE (Only one per JVM)
Runtime.instance().startUp(p);
#PJAVA_INCLUDE_END*/
}
catch (ProfileException pe) {
System.err.println("Error creating the Profile ["+pe.getMessage()+"]");
pe.printStackTrace();
printUsage();
//System.err.println("Usage: java jade.Boot <filename>");
System.exit(-1);
}
catch (IllegalArgumentException iae) {
System.err.println("Command line arguments format error. "+iae.getMessage());
iae.printStackTrace();
printUsage();
//System.err.println("Usage: java jade.Boot <filename>");
System.exit(-1);
}
}
/**
Default constructor.
*/
public Boot() {
}
public static Properties parseCmdLineArgs(String[] args) throws IllegalArgumentException {
Properties props = new ExtendedProperties();
int i = 0;
while (i < args.length) {
if (args[i].startsWith("-")) {
// Parse next option
// Switch options require special handling
if (args[i].equalsIgnoreCase("-version")) {
logger.log(Logger.INFO, "----------------------------------\n"+Runtime.getCopyrightNotice()+"----------------------------------------");
return null;
}
if (args[i].equalsIgnoreCase("-help")) {
printUsage();
return null;
}
if (args[i].equalsIgnoreCase("-container")) {
props.setProperty(Profile.MAIN, "false");
}
else if(args[i].equalsIgnoreCase("-"+Profile.LOCAL_SERVICE_MANAGER)) {
props.setProperty(Profile.LOCAL_SERVICE_MANAGER, "true");
}
else if (args[i].equalsIgnoreCase("-"+Profile.GUI)) {
props.setProperty(Profile.GUI, "true");
}
else if (args[i].equalsIgnoreCase("-"+Profile.NO_MTP)) {
props.setProperty(Profile.NO_MTP, "true");
}
// Options that can be specified in different ways require special handling
else if (args[i].equalsIgnoreCase("-name")) {
if (++i < args.length) {
props.setProperty(Profile.PLATFORM_ID, args[i]);
}
else {
throw new IllegalArgumentException("No platform name specified after \"-name\" option");
}
}
else if (args[i].equalsIgnoreCase("-mtp")) {
if (++i < args.length) {
props.setProperty(Profile.MTPS, args[i]);
}
else {
throw new IllegalArgumentException("No mtps specified after \"-mtp\" option");
}
}
// The -conf option requires special handling
else if (args[i].equalsIgnoreCase("-conf")) {
if (++i < args.length) {
// Some parameters are specified in a properties file
try {
props.load(args[i]);
}
catch (Exception e) {
if(logger.isLoggable(Logger.SEVERE))
logger.log(Logger.SEVERE, "WARNING: error loading properties from file "+args[i]+". "+e);
}
}
else {
throw new IllegalArgumentException("No configuration file name specified after \"-conf\" option");
}
}
// Default handling for all other properties
else {
String name = args[i].substring(1);
if (++i < args.length) {
props.setProperty(name, args[i]);
}
else {
throw new IllegalArgumentException("No value specified for property \""+name+"\"");
}
}
++i;
}
else {
// Get agents at the end of command line
if (props.getProperty(Profile.AGENTS) != null) {
if(logger.isLoggable(Logger.WARNING))
logger.log(Logger.WARNING,"WARNING: overriding agents specification set with the \"-agents\" option");
}
String agents = args[i];
props.setProperty(Profile.AGENTS, args[i]);
if (++i < args.length) {
if(logger.isLoggable(Logger.WARNING))
logger.log(Logger.WARNING,"WARNING: ignoring command line argument "+args[i]+" occurring after agents specification");
if (agents != null && agents.indexOf('(') != -1 && !agents.endsWith(")")) {
if(logger.isLoggable(Logger.WARNING))
logger.log(Logger.WARNING,"Note that agent arguments specifications must not contain spaces");
}
if (args[i].indexOf(':') != -1) {
if(logger.isLoggable(Logger.WARNING))
logger.log(Logger.WARNING,"Note that agent specifications must be separated by a semicolon character \";\" without spaces");
}
}
break;
}
}
// Consistency check
if ("true".equals(props.getProperty(Profile.NO_MTP)) && props.getProperty(Profile.MTPS) != null) {
if(logger.isLoggable(Logger.WARNING))
logger.log(Logger.WARNING,"WARNING: both \"-mtps\" and \"-nomtp\" options specified. The latter will be ignored");
props.remove(Profile.NO_MTP);
}
return props;
}
public static void printUsage() {
System.out.println("Usage:");
System.out.println("java -cp <classpath> jade.Boot [options] [agents]");
System.out.println("Main options:");
System.out.println(" -container");
System.out.println(" -gui");
System.out.println(" -name <platform name>");
System.out.println(" -host <main container host>");
System.out.println(" -port <main container port>");
System.out.println(" -local-host <host where to bind the local server socket on>");
System.out.println(" -local-port <port where to bind the local server socket on>");
System.out.println(" -conf <property file to load configuration properties from>");
System.out.println(" -services <semicolon separated list of service classes>");
System.out.println(" -mtps <semicolon separated list of mtp-specifiers>");
System.out.println(" where mtp-specifier = [in-address:]<mtp-class>[(comma-separated args)]");
System.out.println(" -<property-name> <property-value>");
System.out.println("Agents: [-agents] <semicolon separated list of agent-specifiers>");
System.out.println(" where agent-specifier = <agent-name>:<agent-class>[(comma separated args)]");
System.out.println();
System.out.println("Look at the JADE Administrator's Guide for more details");
}
}