001: /*
002: * <copyright>
003: *
004: * Copyright 1997-2004 BBNT Solutions, LLC
005: * under sponsorship of the Defense Advanced Research Projects
006: * Agency (DARPA).
007: *
008: * You can redistribute this software and/or modify it under the
009: * terms of the Cougaar Open Source License as published on the
010: * Cougaar Open Source Website (www.cougaar.org).
011: *
012: * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
013: * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
014: * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
015: * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
016: * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
017: * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
018: * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
019: * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
020: * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
021: * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
022: * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
023: *
024: * </copyright>
025: */
026:
027: package org.cougaar.mlm.plugin.ldm;
028:
029: import java.io.File;
030: import java.lang.reflect.Method;
031: import java.text.DateFormat;
032: import java.util.Collection;
033: import java.util.Date;
034: import java.util.Enumeration;
035: import java.util.Properties;
036: import java.util.Vector;
037:
038: import org.cougaar.core.blackboard.SubscriberException;
039: import org.cougaar.core.component.ServiceRevokedEvent;
040: import org.cougaar.core.component.ServiceRevokedListener;
041: import org.cougaar.core.domain.FactoryException;
042: import org.cougaar.core.plugin.ComponentPlugin;
043: import org.cougaar.core.service.DomainService;
044: import org.cougaar.planning.ldm.PlanningFactory;
045: import org.cougaar.planning.ldm.PropertyProvider;
046: import org.cougaar.planning.ldm.PrototypeProvider;
047: import org.cougaar.planning.ldm.asset.Asset;
048: import org.cougaar.planning.ldm.asset.NewPropertyGroup;
049: import org.cougaar.planning.ldm.asset.PropertyGroup;
050: import org.cougaar.planning.ldm.plan.NewRoleSchedule;
051: import org.cougaar.planning.ldm.plan.Schedule;
052: import org.cougaar.planning.service.PrototypeRegistryService;
053: import org.w3c.dom.Document;
054: import org.w3c.dom.Element;
055: import org.w3c.dom.Node;
056: import org.w3c.dom.NodeList;
057:
058: /**
059: * An instance of an LDMPlugin that reads a Cluster's startup data
060: * from an XML file (of the form *.ldm.xml).
061: *
062: * This Plugin is invoked with one parameter, the name of the
063: * .ldm.xml file to be parsed. This file is currently looked for
064: * in the local directory. Additional file search capabilities will
065: * be added. Example from a sample cluster.ini file:
066: * <PRE>
067: * plugin=org.cougaar.mlm.plugin.sql.LDMXMLPlugin( foo.ldm.xml )
068: * </PRE>
069: *
070: * @deprecated Try toolkit module's org.cougaar.lib.plugin.UTILLdmXMLPlugin, or XMLPrototypeProviderPlugin in this package
071: *
072: */
073: public class LDMXMLComponentPlugin extends ComponentPlugin implements
074: PropertyProvider, PrototypeProvider {
075:
076: private Properties globalParameters = new Properties();
077: private String xmlfilename;
078: private Enumeration assets;
079: //private XmlDocument doc;
080: private Document doc;
081: private PlanningFactory ldmf;
082: private DomainService domainService = null;
083: private PrototypeRegistryService protoRegistryService = null;
084:
085: //private AssetFactory theAssetFactory = new AssetFactory();
086:
087: public LDMXMLComponentPlugin() {
088: }
089:
090: protected void setupSubscriptions() {
091: if (getBlackboardService().didRehydrate())
092: return; // Assets already added after rehydration
093:
094: domainService = (DomainService) getServiceBroker().getService(
095: this , DomainService.class,
096: new ServiceRevokedListener() {
097: public void serviceRevoked(ServiceRevokedEvent re) {
098: if (DomainService.class.equals(re.getService()))
099: domainService = null;
100: }
101: });
102:
103: ldmf = ((PlanningFactory) domainService.getFactory("planning"));
104: try {
105: getParams();
106: parseXMLFile();
107: } catch (SubscriberException se) {
108: se.printStackTrace();
109: }
110: }
111:
112: /**
113: * Do nothing
114: */
115: public void execute() {
116: }
117:
118: /**
119: * Parse parameters passed to Plugin
120: */
121: private void getParams() {
122: Collection pc = getParameters();
123: Vector pv = new Vector(pc);
124: if (pv == null) {
125: throw new RuntimeException(
126: "LDMXMLPlugin requires a parameter");
127: } else {
128: try {
129: Enumeration ps = pv.elements();
130: String p = (String) ps.nextElement();
131: globalParameters.put("XMLFile", p);
132: xmlfilename = p;
133: } catch (Exception e) {
134: e.printStackTrace();
135: }
136: }
137: }
138:
139: private void parseXMLFile() {
140: try {
141: doc = getConfigFinder().parseXMLConfigFile(xmlfilename);
142: assets = getAssets(doc);
143: while (assets.hasMoreElements()) {
144: Asset asset = (Asset) assets.nextElement();
145: getBlackboardService().publishAdd(asset);
146: }
147: } catch (Exception e) {
148: e.printStackTrace();
149: }
150: }
151:
152: Enumeration getAssets(Document doc) {
153: Node root = doc.getDocumentElement();
154: if (root.getNodeName().equals("clusterassets")) {
155: //NodeList nlist = root.getChildNodes();
156: //int nlength = nlist.getLength();
157:
158: // The following call registers all protoypes
159: // found in our document, and returns to us
160: // all the instances found in the document.
161: //XMLAssetCreator xac = new XMLAssetCreator( this, getCluster() );
162: assets = getLDMAssets(doc);
163: } else {
164: throw new RuntimeException("unrecognized field: "
165: + root.getNodeName());
166: }
167: return assets;
168: }
169:
170: public Asset getPrototype(String atypename, Class hint) {
171: return null;
172: }
173:
174: public Asset getPrototype(String atypename) {
175: return null;
176: }
177:
178: public Asset getAssetPrototype(String typeid) {
179: protoRegistryService = (PrototypeRegistryService) getServiceBroker()
180: .getService(this , PrototypeRegistryService.class,
181: new ServiceRevokedListener() {
182: public void serviceRevoked(
183: ServiceRevokedEvent re) {
184: if (PrototypeRegistryService.class
185: .equals(re.getService()))
186: protoRegistryService = null;
187: }
188: });
189:
190: Asset proto = protoRegistryService.getPrototype(typeid);
191: if (proto == null) {
192: NodeList nlist = doc.getDocumentElement()
193: .getElementsByTagName("prototype");
194: Element node = findPrototype(typeid, nlist);
195: String assetClass = getAssetClass(node);
196: proto = ldmf.createPrototype(assetClass, typeid);
197:
198: protoRegistryService.fillProperties(proto);
199: //getOtherProperties( proto, node );
200: protoRegistryService.cachePrototype(typeid, proto);
201: }
202: return proto;
203: }
204:
205: private Element findPrototype(String typeid, NodeList nlist) {
206: int size = nlist.getLength();
207: for (int i = 0; i < size; i++) {
208: Element child = (Element) nlist.item(i);
209: if (child.getAttribute("name").equals(typeid))
210: return child;
211: }
212: return null;
213: }
214:
215: private String getAssetClass(Element node) {
216: NodeList nl = node.getElementsByTagName("object");
217: int size = nl.getLength();
218: for (int i = 0; i < size; i++) {
219: Element child = (Element) nl.item(i);
220: return child.getAttribute("class");
221: }
222: return null;
223: }
224:
225: private void getOtherProperties(Asset asset, Element node) {
226: NodeList nl = node.getElementsByTagName("property");
227: int size = nl.getLength();
228: for (int i = 0; i < size; i++) {
229: NewPropertyGroup prop = createPG(((Element) nl.item(i))
230: .getAttribute("class"));
231: populateProperty(prop, (Element) nl.item(i));
232: asset.setPropertyGroup(prop);
233: }
234: }
235:
236: private void populateProperty(PropertyGroup prop, Element node) {
237: try {
238: NodeList props = node.getElementsByTagName("field");
239: int props_size = props.getLength();
240: for (int i = 0; i < props_size; i++) {
241: Element child = (Element) props.item(i);
242: String methodName = new String("set"
243: + child.getAttribute("name"));
244: Class[] method_args = new Class[1];
245: String type = child.getAttribute("type");
246: method_args[0] = resolveClass(type);
247: Object[] setter_args = new Object[1];
248: setter_args[0] = resolveArgument(method_args[0], child
249: .getAttribute("value"));
250: Class propclass = prop.getClass();
251: Method propmethod = propclass.getMethod(methodName,
252: method_args);
253: propmethod.invoke(prop, setter_args);
254: }
255: } catch (Exception e) {
256: e.printStackTrace();
257: }
258: }
259:
260: /**
261: * Convert a string value to an object of the type specified.
262: */
263: private Object resolveArgument(Class type, String value)
264: throws ClassNotFoundException {
265: if (type == java.lang.Boolean.TYPE)
266: return new java.lang.Boolean(value);
267: else if (type == java.lang.Character.TYPE)
268: return new java.lang.Character(value.charAt(0));
269: else if (type == java.lang.Byte.TYPE)
270: return new java.lang.Byte(value);
271: else if (type == java.lang.Short.TYPE)
272: return new java.lang.Short(value);
273: else if (type == java.lang.Integer.TYPE)
274: return new java.lang.Integer(value);
275: else if (type == java.lang.Long.TYPE)
276: return new java.lang.Long(value);
277: else if (type == java.lang.Float.TYPE)
278: return new java.lang.Float(value);
279: else if (type == java.lang.Double.TYPE)
280: return new java.lang.Double(value);
281: else if (type == java.lang.Void.TYPE)
282: return null;
283: else
284: return value;
285: }
286:
287: /**
288: * Return a class object for the string classname provided.
289: * Will resolve primitives to their "Class" types.
290: */
291: private Class resolveClass(String type)
292: throws ClassNotFoundException {
293: if (type.equals("boolean"))
294: return java.lang.Boolean.TYPE;
295: else if (type.equals("char"))
296: return java.lang.Character.TYPE;
297: else if (type.equals("byte"))
298: return java.lang.Byte.TYPE;
299: else if (type.equals("short"))
300: return java.lang.Short.TYPE;
301: else if (type.equals("int"))
302: return java.lang.Integer.TYPE;
303: else if (type.equals("long"))
304: return java.lang.Long.TYPE;
305: else if (type.equals("float"))
306: return java.lang.Float.TYPE;
307: else if (type.equals("double"))
308: return java.lang.Double.TYPE;
309: else if (type.equals("void"))
310: return java.lang.Void.TYPE;
311: else
312: return Class.forName(type);
313: }
314:
315: public void fillProperties(Asset asset) {
316: }
317:
318: private Enumeration getLDMAssets(Document doc) {
319: PlanningFactory ldmf = ((PlanningFactory) domainService
320: .getFactory("planning"));
321: Vector assets = new Vector();
322:
323: NodeList prototypes = doc.getElementsByTagName("prototype");
324: int proto_size = prototypes.getLength();
325: for (int i = 0; i < proto_size; i++) {
326: Node child = prototypes.item(i);
327: Asset prototype = getAssetPrototype(child.getAttributes()
328: .getNamedItem("name").getNodeValue());
329: }
330:
331: NodeList instances = doc.getElementsByTagName("instance");
332: int inst_size = instances.getLength();
333: for (int j = 0; j < inst_size; j++) {
334: Node child = instances.item(j);
335: NodeList schedules = ((Element) child)
336: .getElementsByTagName("schedule");
337: // Really only expecting one Schedule here, but...
338: int sched_size = schedules.getLength();
339: Schedule sched = null;
340: for (int k = 0; k < sched_size; k++) {
341: try {
342: Node scheduleNode = schedules.item(k);
343: DateFormat df = DateFormat
344: .getDateInstance(DateFormat.SHORT);
345: Date start = df.parse(scheduleNode.getAttributes()
346: .getNamedItem("start").getNodeValue());
347: Date end = df.parse(scheduleNode.getAttributes()
348: .getNamedItem("end").getNodeValue());
349: sched = ldmf.newSimpleSchedule(start, end);
350: } catch (Exception e) {
351: e.printStackTrace();
352: }
353: }
354: String nomen = child.getAttributes().getNamedItem("id")
355: .getNodeValue();
356: String protoname = child.getAttributes().getNamedItem(
357: "prototype").getNodeValue();
358: Asset myAsset = ldmf.createInstance(protoname, nomen);
359: ((NewRoleSchedule) myAsset.getRoleSchedule())
360: .setAvailableSchedule(sched);
361: assets.addElement(myAsset);
362: }
363: return assets.elements();
364: }
365:
366: private NewPropertyGroup createPG(String propname) {
367: NewPropertyGroup tmp_prop = null;
368: try {
369: tmp_prop = (NewPropertyGroup) ldmf
370: .createPropertyGroup(propname);
371: } catch (FactoryException fe) {
372: try {
373: tmp_prop = (NewPropertyGroup) ldmf
374: .createPropertyGroup(Class.forName(propname));
375: } catch (ClassNotFoundException cnf) {
376: cnf.printStackTrace();
377: }
378: }
379: return tmp_prop;
380: }
381:
382: }
|