001: /*
002: * <copyright>
003: *
004: * Copyright 2001-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: package org.cougaar.glm.execution.eg;
027:
028: import java.awt.GridBagConstraints;
029: import java.awt.GridBagLayout;
030: import java.awt.event.ActionEvent;
031: import java.awt.event.ActionListener;
032: import java.util.Arrays;
033: import java.util.HashMap;
034: import java.util.Iterator;
035: import java.util.Map;
036: import java.util.Properties;
037: import java.util.SortedMap;
038: import java.util.StringTokenizer;
039: import java.util.TreeMap;
040: import javax.swing.JButton;
041: import javax.swing.JComboBox;
042: import javax.swing.JComponent;
043: import javax.swing.JLabel;
044: import javax.swing.JPanel;
045: import javax.swing.JTextField;
046: import javax.swing.JOptionPane;
047: import javax.swing.SwingUtilities;
048: import javax.swing.text.AttributeSet;
049: import javax.swing.text.PlainDocument;
050: import javax.swing.text.BadLocationException;
051: import org.cougaar.glm.execution.common.FailureConsumptionRate;
052: import org.cougaar.util.OptionPane;
053: import org.cougaar.util.Random;
054:
055: /**
056: * Example F/C plugin illustrating how one might write a plugin that
057: * applies to a certain class of supply and how to use the GUI
058: * configuration features. Consult the default plugin for more mundane
059: * matters.
060: **/
061: public abstract class TripletFCPlugin implements
062: FailureConsumptionPlugin, TimeConstants {
063: protected long MAX_INTERVAL = ONE_DAY;
064: protected long MIN_INTERVAL = 6 * ONE_HOUR;
065: protected final String ALL_CLUSTERS = "All Clusters";
066: protected final String ALL_CONSUMERS = "All Consumers";
067: protected final String ALL_CONSUMABLES = "All Consumables";
068:
069: protected static final Random random = new Random();
070: protected EventGenerator theEventGenerator = null;
071: protected String currentConsumer = null;
072: protected String currentConsumable = null;
073: protected String currentCluster = null;
074: private TripletKey currentTripletKey = null;
075:
076: protected static Map consumerNameToId = new TreeMap();
077: protected static Map consumerIdToName = new HashMap();
078: protected static Map consumableNameToId = new TreeMap();
079: protected static Map consumableIdToName = new HashMap();
080: protected static SortedMap triplets = new TreeMap();
081:
082: protected static final int BUTTON_ROW = 100;
083: protected static final int COMMENT_ROW = 90;
084:
085: private JComboBox cb1 = new JComboBox();
086: private JComboBox cb2 = new JComboBox();
087: private JComboBox cb3 = new JComboBox();
088:
089: private JTextField[] valueTextField;
090: private JLabel[] valueLabel;
091: private JButton nextButton = new JButton(">>");
092: private JButton prevButton = new JButton("<<");
093: private JButton deleteButton = new JButton("Delete");
094: private JButton saveButton = new JButton("Save");
095: private JPanel buttons = new JPanel();
096: protected JPanel message;
097:
098: private boolean enableListener = false;
099: private ActionListener cbListener = new ActionListener() {
100: public void actionPerformed(ActionEvent e) {
101: if (!enableListener)
102: return;
103: Object src = e == null ? null : e.getSource();
104: if (e == null || src == cb1)
105: currentConsumable = (String) cb1.getSelectedItem();
106: if (e == null || src == cb2)
107: currentConsumer = (String) cb2.getSelectedItem();
108: if (e == null || src == cb3)
109: currentCluster = (String) cb3.getSelectedItem();
110: if ((currentConsumable != null)
111: && (currentConsumer != null)
112: && (currentCluster != null)) {
113: TripletKey tk_temp = new TripletKey(
114: (String) consumableNameToId
115: .get(currentConsumable),
116: (String) consumerNameToId.get(currentConsumer),
117: (String) currentCluster);
118: setTripletKey(tk_temp);
119: }
120: }
121: };
122:
123: private void setTripletKey(TripletKey key) {
124: TripletValue tv;
125: if (key == null) {
126: tv = null;
127: } else {
128: tv = (TripletValue) triplets.get(key);
129: cb1.setSelectedItem(consumableIdToName.get(key
130: .getConsumable()));
131: cb2
132: .setSelectedItem(consumerIdToName.get(key
133: .getConsumer()));
134: cb3.setSelectedItem(key.getCluster());
135: }
136: if (tv != null || key == null) {
137: currentTripletKey = key;
138: setTripletValue(tv);
139: } else {
140: currentTripletKey = null; // Keep the values, but no key
141: }
142: updateButtons();
143: }
144:
145: private void updateButtons() {
146: if (currentTripletKey == null) {
147: if (triplets.isEmpty()) {
148: prevButton.setEnabled(false);
149: nextButton.setEnabled(false);
150: } else {
151: prevButton.setEnabled(true);
152: nextButton.setEnabled(true);
153: }
154: deleteButton.setEnabled(false);
155: } else {
156: nextButton
157: .setEnabled(getNextTripletKey(currentTripletKey) != null);
158: prevButton
159: .setEnabled(getPreviousTripletKey(currentTripletKey) != null);
160: deleteButton.setEnabled(true);
161: }
162: if (computeTripletKey() != null
163: && computeTripletValue() != null) {
164: saveButton.setEnabled(true);
165: } else {
166: if (saveButton.isSelected())
167: saveButton.setSelected(false);
168: saveButton.setEnabled(false);
169: }
170: }
171:
172: private ActionListener nextListener = new ActionListener() {
173: public void actionPerformed(ActionEvent e) {
174: TripletKey newKey = getNextTripletKey(currentTripletKey);
175: setTripletKey(newKey);
176: }
177: };
178:
179: private ActionListener prevListener = new ActionListener() {
180: public void actionPerformed(ActionEvent e) {
181: TripletKey newKey = getPreviousTripletKey(currentTripletKey);
182: setTripletKey(newKey);
183: }
184: };
185:
186: private ActionListener deleteListener = new ActionListener() {
187: public void actionPerformed(ActionEvent e) {
188: if (currentTripletKey != null) {
189: TripletKey nextKey = getNextTripletKey(currentTripletKey);
190: triplets.remove(currentTripletKey);
191: setTripletKey(nextKey);
192: }
193: }
194: };
195:
196: private ActionListener saveListener = new ActionListener() {
197: public void actionPerformed(ActionEvent e) {
198: if (!saveTriplet()) {
199: // SwingUtilities.invokeLater(new Runnable() {
200: // public void run() {
201: // JOptionPane.showMessageDialog(message,
202: // "Invalid parameters entered",
203: // "Invalid Parameters",
204: // JOptionPane.ERROR_MESSAGE);
205: // }
206: // });
207: }
208: }
209: };
210:
211: private TripletKey getNextTripletKey(TripletKey key) {
212: TripletKey result = null;
213: if (key != null) {
214: Iterator tail = triplets.tailMap(key).keySet().iterator();
215: tail.next(); // Skip past the current key
216: if (tail.hasNext()) {
217: result = (TripletKey) tail.next();
218: }
219: } else if (!triplets.isEmpty()) {
220: result = (TripletKey) triplets.firstKey();
221: }
222: return result;
223: }
224:
225: private TripletKey getPreviousTripletKey(TripletKey key) {
226: TripletKey result = null;
227: if (key != null) {
228: SortedMap head = triplets.headMap(key);
229: if (!head.isEmpty()) {
230: result = (TripletKey) head.lastKey();
231: }
232: } else if (!triplets.isEmpty()) {
233: result = (TripletKey) triplets.lastKey();
234: }
235: return result;
236: }
237:
238: private class TripletKey implements Comparable {
239: private String consumable;
240: private String consumer;
241: private String cluster;
242: private int hashCode;
243:
244: public TripletKey(String ft, String co, String cl) {
245: if (ft == null)
246: throw new IllegalArgumentException("ft is null");
247: if (co == null)
248: throw new IllegalArgumentException("co is null");
249: if (cl == null)
250: throw new IllegalArgumentException("cl is null");
251: consumable = ft;
252: consumer = co;
253: cluster = cl;
254: setHashCode();
255: }
256:
257: private void setHashCode() {
258: hashCode = consumable.hashCode() + consumer.hashCode()
259: + cluster.hashCode();
260: }
261:
262: public String getConsumable() {
263: return consumable;
264: }
265:
266: public String getConsumer() {
267: return consumer;
268: }
269:
270: public String getCluster() {
271: return cluster;
272: }
273:
274: public boolean equals(Object o) {
275: TripletKey tk = (TripletKey) o;
276: if (tk.getConsumable().equals(consumable)
277: && tk.getConsumer().equals(consumer)
278: && tk.getCluster().equals(cluster)) {
279: return true;
280: } else {
281: return false;
282: }
283: }
284:
285: public int compareTo(Object o) {
286: TripletKey tk = (TripletKey) o;
287: int diff;
288: if ((diff = getConsumable().compareTo(tk.getConsumable())) != 0)
289: return diff;
290: if ((diff = getConsumer().compareTo(tk.getConsumer())) != 0)
291: return diff;
292: if ((diff = getCluster().compareTo(tk.getCluster())) != 0)
293: return diff;
294: return 0;
295: }
296:
297: public int hashCode() {
298: return hashCode;
299: }
300:
301: public TripletKey(String key) {
302: StringTokenizer tokens = new StringTokenizer(key, ",");
303: consumable = tokens.nextToken();
304: consumer = tokens.nextToken();
305: cluster = tokens.nextToken();
306: if (tokens.hasMoreTokens())
307: throw new IllegalArgumentException("Too many tokens");
308: setHashCode();
309: }
310:
311: public String toString() {
312: return getConsumable() + "," + getConsumer() + ","
313: + getCluster();
314: }
315: }
316:
317: protected interface TripletValue {
318: long getStartDate(); // For basic computation
319:
320: long getEndDate(); // For basic computation
321:
322: AnnotatedDouble getMultiplier(); // For basic computation
323:
324: int getFieldCount();
325:
326: Object getFieldValue(int ix); // For GUI
327: }
328:
329: protected class Item extends FailureConsumptionPluginItem {
330: long previousTime = 0L;
331: TripletKey[] tks;
332:
333: public Item(FailureConsumptionRate aRate,
334: long theExecutionTime,
335: FailureConsumptionSegment aSegment) {
336: super (aRate);
337: tks = new TripletKey[] {
338: new TripletKey(aRate.theItemIdentification,
339: aRate.theConsumerId, aSegment.theSource),
340: new TripletKey(aRate.theItemIdentification,
341: aRate.theConsumerId, ALL_CLUSTERS),
342: new TripletKey(aRate.theItemIdentification,
343: ALL_CONSUMERS, aSegment.theSource),
344: new TripletKey(ALL_CONSUMABLES,
345: aRate.theConsumerId, aSegment.theSource),
346: new TripletKey(aRate.theItemIdentification,
347: ALL_CONSUMERS, ALL_CLUSTERS),
348: new TripletKey(ALL_CONSUMABLES,
349: aRate.theConsumerId, ALL_CLUSTERS),
350: new TripletKey(ALL_CONSUMABLES, ALL_CONSUMERS,
351: aSegment.theSource),
352: new TripletKey(ALL_CONSUMABLES, ALL_CONSUMERS,
353: ALL_CLUSTERS) };
354: long quantum = getRawTimeQuantum(theExecutionTime);
355: previousTime = Math.max(theExecutionTime - quantum,
356: aRate.theStartTime);
357: }
358:
359: private AnnotatedDouble getQPerMilli(long executionTime) {
360: AnnotatedDouble multiplier = null;
361: TripletValue tv = null;
362: for (int i = 0; tv == null && i < tks.length; i++) {
363: tv = (TripletValue) triplets.get(tks[i]);
364: }
365: if (tv != null) {
366: long startDate = tv.getStartDate();
367: long endDate = tv.getEndDate();
368: if (startDate <= executionTime
369: && endDate > executionTime) {
370: multiplier = tv.getMultiplier();
371: }
372: }
373: if (multiplier == null)
374: multiplier = new AnnotatedDouble(1.0);
375: multiplier.value = ((theFailureConsumptionRate.theRateValue
376: * multiplier.value / theFailureConsumptionRate.theRateMultiplier) / ONE_DAY);
377: return multiplier;
378: }
379:
380: public AnnotatedDouble getQuantity(long executionTime) {
381: checkExecutionTime(executionTime);
382: AnnotatedDouble v = getQPerMilli(executionTime);
383: if (v.value <= 0.0) {
384: v.value = 0.0;
385: return v;
386: }
387: long elapsed = executionTime - previousTime;
388: previousTime = executionTime;
389: v.value = random.nextPoisson(elapsed * v.value);
390: return v;
391: }
392:
393: /**
394: * Use a time quantum such that a quantity of at least one is expected.
395: **/
396: public long getTimeQuantum(long executionTime) {
397: long interval = getRawTimeQuantum(executionTime);
398: return previousTime + interval - executionTime;
399: }
400:
401: public long getRawTimeQuantum(long executionTime) {
402: AnnotatedDouble v = getQPerMilli(executionTime);
403: if (v.value <= 0.0)
404: return MAX_INTERVAL;
405: long interval = (long) (1.0 / v.value);
406: if (interval < MIN_INTERVAL)
407: interval = MIN_INTERVAL;
408: if (interval > MAX_INTERVAL)
409: interval = MAX_INTERVAL;
410: return interval;
411: }
412: }
413:
414: private class WatchDocument extends PlainDocument {
415: public void insertString(int offset, String str, AttributeSet a)
416: throws BadLocationException {
417: super .insertString(offset, str, a);
418: updateButtons();
419: }
420:
421: public void remove(int offs, int len)
422: throws BadLocationException {
423: super .remove(offs, len);
424: updateButtons();
425: }
426: }
427:
428: protected void checkExecutionTime(long executionTime) {
429: // Base class does nothing.
430: }
431:
432: protected TripletFCPlugin() {
433: consumerNameToId.put(ALL_CONSUMERS, ALL_CONSUMERS);
434: consumerIdToName.put(ALL_CONSUMERS, ALL_CONSUMERS);
435: consumableNameToId.put(ALL_CONSUMABLES, ALL_CONSUMABLES);
436: consumableIdToName.put(ALL_CONSUMABLES, ALL_CONSUMABLES);
437: }
438:
439: private void guiInit() {
440: String[] labels = getTripletValueNames();
441: Class[] classes = getTripletValueClasses();
442: Object[] values = getTripletDefaultValues();
443: valueTextField = new JTextField[labels.length];
444: valueLabel = new JLabel[labels.length];
445: for (int i = 0; i < labels.length; i++) {
446: Class cls = classes[i];
447: String s = values[i].toString();
448: if (cls == Double.class) {
449: valueTextField[i] = new JTextField(new WatchDocument(),
450: s, 10);
451: } else if (cls == EGDate.class) {
452: valueTextField[i] = new JTextField(new WatchDocument(),
453: s, 20);
454: } else {
455: valueTextField[i] = new JTextField(new WatchDocument(),
456: s, 20);
457: }
458: valueLabel[i] = new JLabel(labels[i]);
459: }
460: prevButton.addActionListener(prevListener);
461: nextButton.addActionListener(nextListener);
462: saveButton.addActionListener(saveListener);
463: deleteButton.addActionListener(deleteListener);
464: buttons.add(prevButton);
465: buttons.add(nextButton);
466: buttons.add(saveButton);
467: buttons.add(deleteButton);
468: cb1.addActionListener(cbListener);
469: cb2.addActionListener(cbListener);
470: cb3.addActionListener(cbListener);
471: }
472:
473: /**
474: * @return the name of this plugin
475: **/
476: public abstract String getPluginName();
477:
478: public abstract String getDescription();
479:
480: protected abstract String[] getTripletValueNames();
481:
482: protected abstract Class[] getTripletValueClasses();
483:
484: protected abstract Object[] getTripletDefaultValues();
485:
486: protected abstract TripletValue createTripletValue(String[] args);
487:
488: public boolean isConfigurable() {
489: return true;
490: }
491:
492: public abstract void setParameter(String parameter);
493:
494: protected static void addItem(JPanel message, int x, int y,
495: JComponent c) {
496: GridBagConstraints gbc = new GridBagConstraints();
497: gbc.gridx = x;
498: gbc.gridy = y;
499: gbc.anchor = gbc.WEST;
500: message.add(c, gbc);
501: }
502:
503: protected static void addItem(JPanel message, int y, JComponent c) {
504: GridBagConstraints gbc = new GridBagConstraints();
505: gbc.gridx = 0;
506: gbc.gridwidth = 2;
507: gbc.gridy = y;
508: gbc.anchor = gbc.CENTER;
509: message.add(c, gbc);
510: }
511:
512: private void setEnableListener(boolean newEnable) {
513: enableListener = newEnable;
514: }
515:
516: public void configure(java.awt.Component c) {
517: message = createMessage();
518: while (true) {
519: int result = OptionPane.showOptionDialog(c, message,
520: "Configure " + getPluginName(),
521: OptionPane.OK_CANCEL_OPTION,
522: OptionPane.QUESTION_MESSAGE, null, null, null);
523:
524: if (result != OptionPane.OK_OPTION)
525: break;
526: if (saveTriplet())
527: break;
528: result = JOptionPane.showConfirmDialog(message,
529: "Invalid parameters entered", "Invalid Parameters",
530: JOptionPane.OK_CANCEL_OPTION,
531: JOptionPane.ERROR_MESSAGE);
532: if (result != OptionPane.OK_OPTION)
533: break;
534: }
535: }
536:
537: protected JPanel createMessage() {
538: if (valueTextField == null)
539: guiInit();
540: JPanel message = new JPanel(new GridBagLayout());
541: setEnableListener(false);
542: cb1.removeAllItems();
543: cb1.addItem(ALL_CONSUMABLES);
544: Iterator consumablesIter = consumableNameToId.keySet()
545: .iterator();
546: while (consumablesIter.hasNext()) {
547: String s = (String) consumablesIter.next();
548: if (!s.equals(ALL_CONSUMABLES)) {
549: cb1.addItem(s);
550: }
551: }
552: if (currentConsumable == null) {
553: currentConsumable = ALL_CONSUMABLES;
554: }
555: cb1.setSelectedItem(currentConsumable);
556:
557: cb2.removeAllItems();
558: cb2.addItem(ALL_CONSUMERS);
559: Iterator consumersIter = consumerNameToId.keySet().iterator();
560: while (consumersIter.hasNext()) {
561: String s = (String) consumersIter.next();
562: if (!s.equals(ALL_CONSUMERS)) {
563: cb2.addItem(s);
564: }
565: }
566: if (currentConsumer == null) {
567: currentConsumer = ALL_CONSUMERS;
568: }
569: cb2.setSelectedItem(currentConsumer);
570:
571: cb3.removeAllItems();
572: cb3.addItem(ALL_CLUSTERS);
573: if (theEventGenerator != null) {
574: // First, add an "All" option for clusters and consumers
575:
576: // Get the cluster names from the EventGenerator and add to the list
577: String[] clusterNames = theEventGenerator.getClusterNames();
578: Arrays.sort(clusterNames);
579: for (int i = 0; i < clusterNames.length; i++) {
580: cb3.addItem(clusterNames[i]);
581: }
582: }
583: if (currentCluster == null) {
584: currentCluster = ALL_CLUSTERS;
585: }
586: cb3.setSelectedItem(currentCluster);
587:
588: setEnableListener(true);
589: cbListener.actionPerformed(null);
590:
591: int row = 0;
592: addItem(message, 0, row, new JLabel("Item"));
593: addItem(message, 1, row, cb1);
594: row++;
595:
596: addItem(message, 0, row, new JLabel("Consumer"));
597: addItem(message, 1, row, cb2);
598: row++;
599:
600: addItem(message, 0, row, new JLabel("Cluster"));
601: addItem(message, 1, row, cb3);
602: row++;
603:
604: for (int i = 0; i < valueTextField.length; i++, row++) {
605: addItem(message, 0, row, valueLabel[i]);
606: addItem(message, 1, row, valueTextField[i]);
607: }
608:
609: addItem(message, 100, buttons);
610: return message;
611: }
612:
613: protected boolean saveTriplet() {
614: TripletKey key = computeTripletKey();
615: TripletValue val = computeTripletValue();
616: if (key == null || val == null) {
617: return false;
618: } else {
619: currentTripletKey = key;
620: triplets.put(key, val);
621: updateButtons();
622: return true;
623: }
624: }
625:
626: private TripletKey computeTripletKey() {
627: try {
628: String consumable = (String) cb1.getSelectedItem();
629: String consumer = (String) cb2.getSelectedItem();
630: String cluster = (String) cb3.getSelectedItem();
631: return new TripletKey((String) consumableNameToId
632: .get(consumable), (String) consumerNameToId
633: .get(consumer), cluster);
634: } catch (RuntimeException re) {
635: return null;
636: }
637: }
638:
639: private TripletValue computeTripletValue() {
640: try {
641: String[] values = new String[valueTextField.length];
642: for (int i = 0; i < values.length; i++) {
643: values[i] = valueTextField[i].getText();
644: }
645: return createTripletValue(values);
646: } catch (RuntimeException re) {
647: return null;
648: }
649: }
650:
651: private void setTripletValue(TripletValue tv) {
652: for (int i = 0; i < valueTextField.length; i++) {
653: String s;
654: if (tv != null) {
655: s = tv.getFieldValue(i).toString();
656: } else {
657: s = getTripletDefaultValues()[i].toString();
658: }
659: try {
660: valueTextField[i].setText(s);
661: } catch (IllegalArgumentException iae) {
662: valueTextField[i].setText(getTripletDefaultValues()[i]
663: .toString());
664: }
665: }
666: }
667:
668: private interface ValueCoder {
669: int getFieldCount();
670:
671: String getValue(Object o, int i);
672:
673: Object createKey(String keyString);
674:
675: Object createValue(String[] args);
676: }
677:
678: private ValueCoder singleValueCoder = new ValueCoder() {
679: public int getFieldCount() {
680: return 1;
681: }
682:
683: public String getValue(Object o, int i) {
684: return (String) o;
685: }
686:
687: public Object createKey(String keyString) {
688: return keyString;
689: }
690:
691: public Object createValue(String[] args) {
692: return args[0];
693: }
694: };
695:
696: private ValueCoder tripleValueCoder = new ValueCoder() {
697: public int getFieldCount() {
698: return getTripletValueNames().length;
699: }
700:
701: public String getValue(Object o, int i) {
702: TripletValue tv = (TripletValue) o;
703: return tv.getFieldValue(i).toString();
704: }
705:
706: public Object createKey(String keyString) {
707: return new TripletKey(keyString);
708: }
709:
710: public Object createValue(String[] args) {
711: return createTripletValue(args);
712: }
713: };
714:
715: private void saveMap(Properties props, Map map, String prefix,
716: ValueCoder vc) {
717: int count = 0;
718: int nfields = vc.getFieldCount();
719: for (Iterator keys = map.keySet().iterator(); keys.hasNext(); count++) {
720: Object key = keys.next();
721: String keyString = key.toString();
722: Object val = map.get(key);
723: props.setProperty(prefix + count + ".key", keyString);
724: for (int j = 0; j < nfields; j++) {
725: props.setProperty(prefix + count + ".val." + j, vc
726: .getValue(val, j));
727: }
728: }
729: props.setProperty(prefix + "count", String.valueOf(count));
730: }
731:
732: public void save(Properties props, String prefix) {
733: saveMap(props, consumableNameToId, prefix + "consumables.",
734: singleValueCoder);
735: saveMap(props, consumerNameToId, prefix + "consumers.",
736: singleValueCoder);
737: saveMap(props, triplets, prefix + "triplets.", tripleValueCoder);
738: props.setProperty(prefix + "currentConsumer", currentConsumer);
739: props.setProperty(prefix + "currentConsumable",
740: currentConsumable);
741: props.setProperty(prefix + "currentCluster", currentCluster);
742: }
743:
744: private void restoreMap(Properties props, Map map, Map reverseMap,
745: String prefix, ValueCoder vc) {
746: int count = Integer.parseInt(props
747: .getProperty(prefix + "count"));
748: int nfields = vc.getFieldCount();
749: String[] args = new String[nfields];
750: for (int i = 0; i < count; i++) {
751: try {
752: Object key = vc.createKey(props.getProperty(prefix + i
753: + ".key"));
754: for (int j = 0; j < nfields; j++) {
755: args[j] = props.getProperty(prefix + i + ".val."
756: + j);
757: }
758: Object val = vc.createValue(args);
759: map.put(key, val);
760: if (reverseMap != null)
761: reverseMap.put(val, key);
762: } catch (RuntimeException re) {
763: re.printStackTrace();
764: }
765: }
766: }
767:
768: public void restore(Properties props, String prefix) {
769: try {
770: restoreMap(props, consumableNameToId, consumableIdToName,
771: prefix + "consumables.", singleValueCoder);
772: restoreMap(props, consumerNameToId, consumerIdToName,
773: prefix + "consumers.", singleValueCoder);
774: restoreMap(props, triplets, null, prefix + "triplets.",
775: tripleValueCoder);
776: currentConsumer = props.getProperty(prefix
777: + "currentConsumer");
778: currentConsumable = props.getProperty(prefix
779: + "currentConsumable");
780: currentCluster = props.getProperty(prefix
781: + "currentCluster");
782: } catch (Exception e) {
783: e.printStackTrace();// State not present in props
784: }
785: }
786:
787: public void setEventGenerator(EventGenerator eg) {
788: theEventGenerator = eg;
789: }
790:
791: /**
792: * Create a FailureConsumptionItem for this plugin to handle a
793: * particular FailureConsumptionRate. Override this to filter the
794: * items being handled.
795: **/
796: public FailureConsumptionPluginItem createFailureConsumptionItem(
797: FailureConsumptionRate aRate,
798: FailureConsumptionSegment aSegment, long theExecutionTime,
799: FailureConsumptionPluginItem aFailureConsumptionPluginItem) {
800: consumableNameToId.put(aRate.theItemName,
801: aRate.theItemIdentification);
802: consumableIdToName.put(aRate.theItemIdentification,
803: aRate.theItemName);
804: consumerNameToId.put(aRate.theConsumer, aRate.theConsumerId);
805: consumerIdToName.put(aRate.theConsumerId, aRate.theConsumer);
806: if (aFailureConsumptionPluginItem instanceof Item
807: && aFailureConsumptionPluginItem.theFailureConsumptionRate == aRate) {
808: return aFailureConsumptionPluginItem;
809: }
810: return new Item(aRate, theExecutionTime, aSegment);
811: }
812: }
|