1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28 package zeus.concepts;
29
30 import java.io.*;
31 import java.util.*;
32 import zeus.util.*;
33 import zeus.actors.*;
34 import zeus.actors.factories.*;
35 import zeus.actors.outtrays.*;
36
37 /***
38 * The Performative class provides a standard data structure for inter-agent
39 * messaging. The message format and available message types have been derived
40 * from the FIPA Agent Communication Language description. <p>
41 *
42 * This class contains methods that allow the attributes of performative objects
43 * to be set and modified, although typically developers will only need to
44 * invoke one of the constructors. More information on performatives and the
45 * communication mechanism is provided in the Zeus Technical Manual.
46 */
47
48
49 public class Performative
50 {
51 public static final String[] MESSAGE_TYPES = {
52 "accept-proposal",
53 "agree",
54 "cancel",
55 "cfp",
56 "confirm",
57 "disconfirm",
58 "failure",
59 "inform",
60 "inform-if",
61 "inform-ref",
62 "not-understood",
63 "propose",
64 "query-if",
65 "query-ref",
66 "refuse",
67 "reject-proposal",
68 "request",
69 "request-when",
70 "request-whenever",
71 "subscribe",
72 "request-forward"
73 };
74
75 public static final String[] MESSAGE_TYPES_UPPER = {
76 "ACCEPT-PROPOSAL",
77 "AGREE",
78 "CANCEL",
79 "CFP",
80 "CONFIRM",
81 "DISCONFIRM",
82 "FAILURE",
83 "INFORM",
84 "INFORM-IF",
85 "INFORM-REF",
86 "NOT-UNDERSTOOD",
87 "PROPOSE",
88 "QUERY-IF",
89 "QUERY-REF",
90 "REFUSE",
91 "REJECT-PROPOSAL",
92 "REQUEST",
93 "REQUEST-WHEN",
94 "REQUEST-WHENEVER",
95 "SUBSCRIBE",
96 "REQUEST-FORWARD"
97 };
98
99 public static final String[] ATTRIBUTE_TYPES = {
100 "type",
101 "sender",
102 "receiver",
103 "content",
104 "reply-with",
105 "in-reply-to",
106 "reply-by",
107 "ontology",
108 "language",
109 "protocol",
110 "conversation-id",
111 "reply-to"
112 };
113
114
115 private static final int TYPE = 0;
116 private static final int SENDER = 1;
117 private static final int RECEIVER = 2;
118 private static final int CONTENT = 3;
119 private static final int REPLY_WITH = 4;
120 private static final int IN_REPLY_TO = 5;
121 private static final int REPLY_BY = 6;
122 private static final int ONTOLOGY = 7;
123 private static final int LANGUAGE = 8;
124 private static final int PROTOCOL = 9;
125 private static final int CONVERSATION_ID = 10;
126 private static final int REPLY_TO = 11;
127
128 protected String type;
129 protected String sender;
130 protected HSet receivers = new HSet();
131 protected String content;
132 protected String replyWith;
133 protected String inReplyTo;
134 protected String replyBy;
135 protected String ontology;
136 protected String language;
137 protected String protocol;
138 protected String conversationId;
139 protected Hashtable envelope = new Hashtable();
140 protected String replyTo;
141
142 public Performative () {
143 }
144
145 public Performative(String type) {
146 setType(type);
147 }
148
149 public Performative(Performative perf) {
150 String token;
151 Hashtable table;
152 Enumeration data;
153
154 if ( (token = perf.getType()) != null ) setType(token);
155 if ( (token = perf.getSender()) != null ) setSender(token);
156 if ( (data = perf.getReceivers()) != null ) setReceivers(data);
157 if ( (token = perf.getReplyWith()) != null ) setReplyWith(token);
158 if ( (token = perf.getInReplyTo()) != null ) setInReplyTo(token);
159 if ( (token = perf.getReplyBy()) != null ) setReplyBy(token);
160 if ( (token = perf.getOntology()) != null ) setOntology(token);
161 if ( (token = perf.getLanguage()) != null ) setLanguage(token);
162 if ( (token = perf.getContent()) != null ) setContent(token);
163 if ( (token = perf.getProtocol()) != null ) setProtocol(token);
164 if ( (token = perf.getConversationId()) != null ) setConversationId(token);
165 if ( (table = perf.getEnvelope()) != null ) setEnvelope(table);
166 if ( (token = perf.getReplyTo()) != null ) setReplyTo(token);
167 }
168
169
170 public void setType(String type) {
171 type = type.trim();
172 if ( Misc.member(type,MESSAGE_TYPES) ) {
173 this.type = type;
174 }
175 else if ( Misc.member(type,MESSAGE_TYPES_UPPER) ) {
176 this.type = type;
177 }
178 else {
179 Core.ERROR(null,1,"Invalid Performative type: " + type);
180 }
181 }
182
183 public void setSender(String value){
184 sender = value; }
185
186
187 public void setReceiver(String value){
188 receivers.add(value); }
189
190
191 public void setReplyWith(String value){
192 replyWith = value; }
193
194
195 public void setInReplyTo(String value){
196 inReplyTo = value; }
197
198
199 public void setReplyBy(String value) {
200 replyBy = value; }
201
202
203 public void setReplyTo (String value) {
204 replyTo = value;
205 }
206
207
208 public void setOntology(String value) {
209 ontology = value; }
210
211
212 public void setLanguage(String value) {
213 language = value; }
214
215
216 public void setContent(String value) {
217 content = value; }
218
219
220 public void setProtocol(String value) {
221 protocol = value; }
222
223
224 public void setConversationId(String value) {
225 conversationId = value; }
226
227
228
229 public void setReceivers(Vector input) {
230 receivers.clear();
231 Enumeration enum = input.elements();
232 while( enum.hasMoreElements() )
233 receivers.add(enum.nextElement());
234 }
235
236
237 public void setReceivers(HSet input) {
238 receivers.clear();
239 Enumeration enum = input.elements();
240 while( enum.hasMoreElements() )
241 receivers.add(enum.nextElement());
242 }
243
244
245 public void setReceivers(Enumeration enum) {
246 receivers.clear();
247 while( enum.hasMoreElements() )
248 receivers.add(enum.nextElement());
249 }
250
251 public void setAddress(Address value ) {
252 envelope.put("address",value);
253 }
254
255
256 public void setSendTime(Time value) {
257 envelope.put("sendTime",value);
258 }
259
260
261 public void setReceiveTime(Time value) {
262 envelope.put("receiveTime",value);
263 }
264
265 public void setEnvelopeItem(String name, Object item) {
266 envelope.put(name,item);
267 }
268
269
270 public Object getEnvelopeItem(String name) {
271 return envelope.get(name);
272 }
273
274
275 public void setEnvelope(Hashtable input) {
276 envelope.clear();
277 Enumeration enum = input.keys();
278 Object key;
279 Object value;
280 while( enum.hasMoreElements() ) {
281 key = enum.nextElement();
282 value = input.get(key);
283 envelope.put(key,value);
284 }
285 }
286
287 public Hashtable getEnvelope() {
288 return envelope; }
289
290
291 public String getType() {
292 return type; }
293
294
295 public String getSender() {
296 return sender; }
297
298
299 public String getReplyWith(){
300 return replyWith; }
301
302
303 public String getInReplyTo() {
304 return inReplyTo; }
305
306
307 public String getReplyBy(){
308 return replyBy; }
309
310
311 public String getReplyTo () {
312 return replyTo;
313 }
314
315
316 public String getOntology() {
317 return ontology; }
318
319
320 public String getLanguage() {
321 return language; }
322
323
324 public String getContent() {
325 return content; }
326
327
328 public String getProtocol(){
329 return protocol; }
330
331
332 public String getConversationId() {
333 return conversationId; }
334
335
336 public String getReceiver() {
337 Enumeration enum = receivers.elements();
338 try {
339 return (String) enum.nextElement();}
340 catch (Exception e ) {
341 return enum.nextElement().toString(); }
342 }
343
344
345 public Enumeration getReceivers(){
346 return receivers.elements();
347 }
348
349
350 public Address getAddress() {
351 Object item = envelope.get("address");
352 if ( item instanceof String ) {
353 Address a = ZeusParser.address((String)item);
354 envelope.put("address",a);
355 return a;
356 }
357 else
358 return (Address)item;
359 }
360
361
362 public Time getSendTime() {
363 Object item = envelope.get("sendTime");
364 if ( item instanceof String ) {
365 Time t = new Time((String)item);
366 envelope.put("sendTime", t);
367 return t;
368 }
369 else
370 return (Time)item;
371 }
372
373
374 public Time getReceiveTime() {
375 Object item = envelope.get("receiveTime");
376 if ( item instanceof String ) {
377 Time t = new Time((String)item);
378 envelope.put("receiveTime", t);
379 return t;
380 }
381 else
382 return (Time)item;
383 }
384
385
386 public boolean isValid() {
387 return type != null && sender != null && !receivers.isEmpty();
388 }
389
390
391
392
393 StringBuffer sb ;
394
395 public final String toString() {
396 sb = new StringBuffer(300);
397 sb.append ("(");
398 sb.append (type);
399 sb.append ("\n");
400
401
402 if ( sender != null ) {
403 sb.append (" :sender ");
404 sb.append (sender);
405 sb.append ("\n");
406 }
407
408 if ( receivers != null && !receivers.isEmpty() ) {
409 sb.append (" :receiver " );
410 if ( receivers.size() > 1 ){
411 sb.append ("(");
412 sb.append (Misc.concat(receivers));
413 sb.append (")");
414 }
415 else {
416 sb.append ( Misc.concat(receivers));
417 }
418 sb.append ("\n");
419
420 }
421 if ( replyWith != null ) {
422 sb.append (" :reply-with ");
423 sb.append (replyWith);
424 sb.append ("\n");
425
426 }
427 if ( inReplyTo != null ) {
428 sb.append (" :in-reply-to ");
429 sb.append (inReplyTo);
430 sb.append ("\n");
431 }
432
433 if ( replyBy != null ) {
434 sb.append (" :reply-by ");
435 sb.append (replyBy);
436 sb.append ("\n");
437 }
438
439 if ( ontology != null ) {
440 sb.append (" :ontology ");
441 sb.append (ontology);
442 sb.append ("\n");
443 }
444
445 if ( language != null ) {
446 sb.append (" :language ");
447 sb.append (language);
448 sb.append ("\n");
449 }
450
451 if ( content != null ) {
452 sb.append (" :content ");
453 sb.append ("\"");
454 String temp = Misc.escape (content);
455 sb.append (temp);
456 temp = null;
457 sb.append ("\"");
458 sb.append ("\n");
459 }
460
461 if ( protocol != null ) {
462 sb.append (" :protocol ");
463 sb.append (protocol);
464 sb.append ("\n");
465 }
466
467 if ( conversationId != null ) {
468 sb.append (" :conversation-id ");
469 sb.append (conversationId);
470 sb.append ("\n");
471 }
472
473 if ( replyTo != null ) {
474 sb.append (" :reply-to ");
475 sb.append (replyTo);
476 sb.append ("\n");
477 }
478
479
480 if ( envelope != null && !envelope.isEmpty() ) {
481 sb.append(" :envelope (");
482 Enumeration enum = envelope.keys();
483 String key;
484 Object value;
485 while( enum.hasMoreElements() ) {
486 key = (String)enum.nextElement();
487 value = envelope.get(key);
488 sb.append("(");
489 sb.append(key);
490 sb.append(" \"");
491 sb.append ( Misc.escape(value.toString()));
492 sb.append ("\")");
493 }
494 sb.append(")");
495 }
496
497 sb.append(")\n");
498 return sb.toString();
499 }
500
501
502 public Object getAttribute(String attribute) {
503 switch( Misc.whichPosition(attribute,ATTRIBUTE_TYPES) ) {
504 case TYPE:
505 return type;
506 case SENDER:
507 return sender;
508 case RECEIVER:
509 return getReceiver();
510 case CONTENT:
511 return content;
512 case REPLY_WITH:
513 return replyWith;
514 case IN_REPLY_TO:
515 return inReplyTo;
516 case REPLY_BY:
517 return replyBy;
518 case ONTOLOGY:
519 return ontology;
520 case LANGUAGE:
521 return language;
522 case PROTOCOL:
523 return protocol;
524 case CONVERSATION_ID:
525 return conversationId;
526 case REPLY_TO:
527 return replyTo;
528 default:
529 return envelope.get(attribute);
530 }
531 }
532 public void setAttribute(String attribute, Object value) {
533 switch( Misc.whichPosition(attribute,ATTRIBUTE_TYPES) ) {
534 case TYPE:
535 setType((String)value);
536 break;
537 case SENDER:
538 setSender((String)value);
539 break;
540 case RECEIVER:
541 setReceiver((String)value);
542 break;
543 case CONTENT:
544 setContent((String)value);
545 break;
546 case REPLY_WITH:
547 setReplyWith((String)value);
548 break;
549 case IN_REPLY_TO:
550 setInReplyTo((String)value);
551 break;
552 case REPLY_BY:
553 setReplyBy((String)value);
554 break;
555 case ONTOLOGY:
556 setOntology((String)value);
557 break;
558 case LANGUAGE:
559 setLanguage((String)value);
560 break;
561 case PROTOCOL:
562 setProtocol((String)value);
563 break;
564 case CONVERSATION_ID:
565 setConversationId((String)value);
566 break;
567 case REPLY_TO:
568 setReplyTo ((String) value);
569 break;
570
571 default:
572 envelope.put(attribute,value);
573 break;
574 }
575 }
576
577 public void send (AgentContext context) {
578 TransportFactory factory = context.getTransportFactory();
579 try {
580 OutTray out = factory.getTransport (this.getReceiver());
581
582
583 context.MailBox().sendMsg(this);
584
585
586 }
587 catch (Exception e) {
588 e.printStackTrace();
589 }
590
591
592
593
594
595
596
597
598
599
600 }
601
602
603 }