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.examples;
028:
029: import java.awt.FlowLayout;
030: import java.awt.Label;
031: import java.awt.event.ActionEvent;
032: import java.awt.event.ActionListener;
033: import java.util.Calendar;
034: import java.util.Enumeration;
035:
036: import javax.swing.JButton;
037: import javax.swing.JFrame;
038: import javax.swing.JPanel;
039:
040: import org.cougaar.core.blackboard.IncrementalSubscription;
041: import org.cougaar.glm.ldm.Constants;
042: import org.cougaar.glm.ldm.asset.Organization;
043: import org.cougaar.planning.ldm.PlanningFactory;
044: import org.cougaar.planning.ldm.asset.Asset;
045: import org.cougaar.planning.ldm.plan.Allocation;
046: import org.cougaar.planning.ldm.plan.AllocationResult;
047: import org.cougaar.planning.ldm.plan.AspectType;
048: import org.cougaar.planning.ldm.plan.AspectValue;
049: import org.cougaar.planning.ldm.plan.NewTask;
050: import org.cougaar.planning.ldm.plan.PlanElement;
051: import org.cougaar.planning.ldm.plan.Task;
052: import org.cougaar.planning.ldm.plan.TimeAspectValue;
053: import org.cougaar.planning.ldm.plan.Verb;
054: import org.cougaar.planning.ldm.trigger.Trigger;
055: import org.cougaar.planning.ldm.trigger.TriggerAction;
056: import org.cougaar.planning.ldm.trigger.TriggerMakeStaleAction;
057: import org.cougaar.planning.ldm.trigger.TriggerMonitor;
058: import org.cougaar.planning.ldm.trigger.TriggerPredicateBasedMonitor;
059: import org.cougaar.planning.ldm.trigger.TriggerRescindAction;
060: import org.cougaar.planning.ldm.trigger.TriggerStaleTester;
061: import org.cougaar.planning.ldm.trigger.TriggerTester;
062: import org.cougaar.planning.ldm.trigger.TriggerTimeBasedMonitor;
063: import org.cougaar.planning.plugin.legacy.SimplePlugin;
064: import org.cougaar.util.UnaryPredicate;
065:
066: /**
067: * The Trigger tester plugin. A GUI based plugin which creates test planelements
068: * that triggers are placed on. Both timebasedmonitors and predicatebasedmonitors
069: * can be created. Currently configured with 2 triggers with timebasedmonitors that
070: * watch for stale allocations, and rescind them and 1 predicatebasedmonitor that looks
071: * for certain planelements and marks them as stale.
072: *
073: *
074: */
075:
076: public class TriggerTesterPlugin extends SimplePlugin {
077: private IncrementalSubscription selfAssets;
078: private IncrementalSubscription myplanelements;
079: private IncrementalSubscription mype2;
080: private Trigger mytrigger2, mytrigger;
081:
082: /** frame for 1-button UI **/
083: static JFrame frame;
084:
085: Label TRLabel;
086:
087: protected JButton trButton;
088:
089: // Have to provide these on this plugin class, else the inner class
090: // below will not be able to find them
091: public void openTheTransaction() {
092: openTransaction();
093: }
094:
095: public void closeTheTransaction(boolean b) {
096: closeTransaction(b);
097: }
098:
099: /** An ActionListener that listens to the Trigger buttons. */
100: class TRButtonListener implements ActionListener {
101: public void actionPerformed(ActionEvent e) {
102: String lnfName = e.getActionCommand();
103: try {
104: openTheTransaction();
105: System.out.println("Creating Triggers...");
106: createTriggers();
107: closeTheTransaction(false);
108: TRLabel.setText("sent triggers");
109: } catch (Exception exc) {
110: JButton button = (JButton) e.getSource();
111: button.setEnabled(false);
112: System.err.println("Could not execute TR button: "
113: + lnfName);
114: }
115: }
116: }
117:
118: private void createGUI() {
119: frame = new JFrame("TriggerPlugin");
120: frame.setLocation(0, 80);
121: frame.getContentPane().setLayout(new FlowLayout());
122: JPanel panel = new JPanel();
123: // Create the button
124: trButton = new JButton("Create Trigger Objects");
125: trButton.setEnabled(true);
126: // Create a label for feedback on if the root task was sent
127: TRLabel = new Label(
128: " ");
129: // Register a listener for the check box
130: TRButtonListener myTRListener = new TRButtonListener();
131: trButton.addActionListener(myTRListener);
132: panel.add(trButton);
133: panel.add(TRLabel);
134: frame.getContentPane().add("Center", panel);
135: frame.pack();
136: frame.setVisible(true);
137: }
138:
139: protected void setupSubscriptions() {
140: selfAssets = (IncrementalSubscription) subscribe(selfPred());
141: myplanelements = (IncrementalSubscription) subscribe(pepred());
142: mype2 = (IncrementalSubscription) subscribe(pepred2());
143: createGUI();
144: }
145:
146: public synchronized void execute() {
147:
148: // used if we want to make the allocation stale to kick a trigger into action
149: //if (myplanelements.hasChanged()) {
150: //Enumeration added = myplanelements.getAddedList();
151: //while (added.hasMoreElements()) {
152: //Allocation alloc = (Allocation) added.nextElement();
153: // make it stale for testing purposes
154: //alloc.setStale(true);
155: //publishChange(alloc);
156: //}
157: //}
158:
159: // rescind the trigger if it did its job and we don't expect anything else to use it.
160: // Used mostly to test the TriggerManagerPlugin's management of triggers.
161: if (myplanelements.hasChanged()) {
162: Enumeration oneremoved = myplanelements.getRemovedList();
163: if (oneremoved.hasMoreElements()) {
164: publishRemove(mytrigger);
165: System.err.println("Just rescinded mytrigger (1)");
166: }
167: }
168:
169: // rescind the trigger if it did its job and we don't expect anything else to use it
170: // Used mostly to test the TriggerManagerPlugin's management of triggers.
171: if (mype2.hasChanged()) {
172: Enumeration removed = mype2.getRemovedList();
173: if (removed.hasMoreElements()) {
174: // we only expect one, so if we are here, rescind its trigger.
175: publishRemove(mytrigger2);
176: System.err.println("Just rescinded mytrigger2!");
177: }
178: }
179:
180: }
181:
182: private void createTriggers() {
183: // create a planelement first
184: PlanElement boguspe = createAPlanElement(Constants.Verb.TRANSPORT);
185: // now create a trigger.
186: // first make a montior
187: //TriggerMonitor mymonitor = new TriggerPredicateBasedMonitor(pepred());
188: Object[] monobjects = { boguspe };
189: TriggerMonitor mytimemon = new TriggerTimeBasedMonitor(30000,
190: monobjects, getDelegate());
191: // create a stale tester.
192: TriggerTester mytester = new TriggerStaleTester();
193: // create a rescind action
194: TriggerAction myaction = new TriggerRescindAction(boguspe);
195: mytrigger = new Trigger(mytimemon, mytester, myaction);
196: //mytrigger = new Trigger(mymonitor, mytester, myaction);
197: publishAdd(mytrigger);
198:
199: // create a second one
200: PlanElement secondpe = createAPlanElement(Constants.Verb.TRANSPORTATIONMISSION);
201: Object[] monobjects2 = { secondpe };
202: TriggerMonitor mytimemon2 = new TriggerTimeBasedMonitor(10000,
203: monobjects2, getDelegate());
204: // create a stale tester.
205: TriggerTester mytester2 = new TriggerStaleTester();
206: // create a rescind action
207: TriggerAction myaction2 = new TriggerRescindAction(secondpe);
208: mytrigger2 = new Trigger(mytimemon2, mytester2, myaction2);
209: publishAdd(mytrigger2);
210:
211: // create another trigger on one of the planelements.
212: TriggerMonitor mymonitor3 = new TriggerPredicateBasedMonitor(
213: pepred3());
214: // create a stale tester.
215: TriggerTester mytester3 = null;
216: // create a make stale action
217: TriggerAction myaction3 = new TriggerMakeStaleAction(
218: ((Allocation) boguspe));
219: Trigger mytrigger3 = new Trigger(mymonitor3, mytester3,
220: myaction3);
221: publishAdd(mytrigger3);
222:
223: }
224:
225: public PlanElement createAPlanElement(String theverb) {
226: PlanningFactory factory = getFactory();
227: NewTask ntask = factory.newTask();
228: // only fill in a few things on the task since it is only for testing.
229: // if this was a real task we would need to fill in more.
230: ntask.setVerb(Verb.get(theverb));
231: ntask.setPlan(factory.getRealityPlan());
232:
233: Asset theasset = null;
234: Enumeration assete = selfAssets.elements();
235: if (assete.hasMoreElements()) {
236: theasset = (Asset) assete.nextElement();
237: }
238:
239: if (theasset != null) {
240: // create an allocationresult
241: Calendar now = Calendar.getInstance();
242: now.add(Calendar.DATE, 5);
243: AspectValue time1 = TimeAspectValue.create(
244: AspectType.START_TIME, now.getTime());
245: now.add(Calendar.DATE, 5);
246: AspectValue time2 = TimeAspectValue.create(
247: AspectType.END_TIME, now.getTime());
248: AspectValue[] avresults = { time1, time2 };
249: AllocationResult theresult = factory.newAVAllocationResult(
250: 1.0, true, avresults);
251: // create an allocation of the new task to this cluster
252: Allocation newalloc = factory.createAllocation(ntask
253: .getPlan(), ntask, theasset, theresult,
254: Constants.Role.TRANSPORTER);
255: // make it stale for testing purposes
256: //newalloc.setStale(true);
257: publishAdd(newalloc);
258: return newalloc;
259: } else {
260: System.err.println("Don't have an asset to allocate to!!!");
261: }
262: //if we make it to here, there was a problem
263: return null;
264: }
265:
266: // predicate for getting all PlanElement objects
267: private static UnaryPredicate pepred() {
268: return new UnaryPredicate() {
269: public boolean execute(Object o) {
270: if (o instanceof PlanElement) {
271: Task t = ((PlanElement) o).getTask();
272: if (t.getVerb().equals(Constants.Verb.TRANSPORT)) {
273: return true;
274: }
275: }
276: return false;
277: }
278: };
279: }
280:
281: // predicate for getting all PlanElement objects
282: private static UnaryPredicate pepred3() {
283: return new UnaryPredicate() {
284: public boolean execute(Object o) {
285: if (o instanceof PlanElement) {
286: Task t = ((PlanElement) o).getTask();
287: if ((t.getVerb().equals(Constants.Verb.TRANSPORT))
288: && (!((Allocation) o).isStale())) {
289: return true;
290: }
291: }
292: return false;
293: }
294: };
295: }
296:
297: // predicate for getting second PlanElement objects
298: private static UnaryPredicate pepred2() {
299: return new UnaryPredicate() {
300: public boolean execute(Object o) {
301: if (o instanceof PlanElement) {
302: Task t = ((PlanElement) o).getTask();
303: if (t.getVerb().equals(
304: Constants.Verb.TRANSPORTATIONMISSION)) {
305: return true;
306: }
307: }
308: return false;
309: }
310: };
311: }
312:
313: // predicate for getting self asset
314: private static UnaryPredicate selfPred() {
315: return new UnaryPredicate() {
316: public boolean execute(Object o) {
317: if (o instanceof Organization) {
318: return ((Organization) o).isSelf();
319: }
320: return false;
321: }
322: };
323: }
324:
325: }
|