View Javadoc
1   package org.miloss.fgsms.agents;
2   
3   import java.util.HashMap;
4   import java.util.UUID;
5   import org.miloss.fgsms.agentcore.MessageProcessor;
6   import org.miloss.fgsms.common.Utility;
7   import org.apache.log4j.Level;
8   import org.miloss.fgsms.common.Logger;;
9   import org.jboss.soa.esb.ConfigurationException;
10  import org.jboss.soa.esb.actions.ActionLifecycleException;
11  import org.jboss.soa.esb.actions.ActionProcessingException;
12  import org.jboss.soa.esb.helpers.ConfigTree;
13  import org.jboss.soa.esb.http.HttpHeader;
14  import org.jboss.soa.esb.http.HttpRequest;
15  import org.jboss.soa.esb.http.HttpResponse;
16  import org.jboss.soa.esb.message.Message;
17  import org.jboss.soa.esb.message.body.content.TextBody;
18  
19  /**
20   * For Jboss ESB deployments. trigger this BEFORE doing any kind of work
21   *
22   * @author AO
23   */
24  public class JbossESBProxyAction implements org.jboss.soa.esb.actions.ActionPipelineProcessor {
25  
26      private Logger log;
27  
28      public JbossESBProxyAction(ConfigTree config) throws ConfigurationException {
29          log = Logger.getLogger(org.miloss.fgsms.common.Constants.LoggerName);
30  
31          httpport = config.getAttribute("http_port", "80");
32          httpsport = config.getAttribute("https_port", "443");
33  
34      }
35      private String httpport = "80";
36      private String httpsport = "443";
37  
38      public Message process(Message msg) throws ActionProcessingException {
39          
40          //JbossESB had a MessageID property: used to uniquely identify this message. OPTIONAL
41          //Since they consider it optional, I'm relying on my own
42          String id = UUID.randomUUID().toString();
43  
44  
45          msg.getProperties().setProperty("fgsms.TransactionID", id);
46  
47          /*
48           * for (int i = 0; i < msg.getProperties().getNames().length; i++) {
49           * log.log(Level.DEBUG, "key = " + msg.getProperties().getNames()[i] + "
50           * value = " +
51           * msg.getProperties().getProperty(msg.getProperties().getNames()[i]));
52          }
53           */
54  
55          String relatedTransaction = "";
56          String transactionthreadid = "";
57  
58          HttpRequest request = HttpRequest.getRequest(msg);
59  
60          HashMap headers = new HashMap();
61          int relatedIndex=-1;
62          if (request != null && !request.getHeaders().isEmpty()) {
63              for (int i = 0; i < request.getHeaders().size(); i++) {
64                  headers.put(request.getHeaders().get(i).getName(), request.getHeaders().get(i).getValue());
65                  if (request.getHeaders().get(i).getName().equalsIgnoreCase(org.miloss.fgsms.common.Constants.relatedtransactionKey)) {
66                      //represents that this transaction was recorded somewhere else before I got it, so we should track this
67                      relatedTransaction = request.getHeaders().get(i).getValue();
68                     relatedIndex = i;
69                  }
70                  if (request.getHeaders().get(i).getName().equalsIgnoreCase(org.miloss.fgsms.common.Constants.transactionthreadKey)) {
71                      transactionthreadid = request.getHeaders().get(i).getValue();
72                  }
73  
74              }
75              if (relatedIndex >=0 && MessageProcessor.getSingletonObject().isDependencyInjectionEnabled())
76              {
77                  //replace the related message id with the id associated with *this
78                  request.getHeaders().remove(relatedIndex);
79                  request.getHeaders().add(new HttpHeader(org.miloss.fgsms.common.Constants.relatedtransactionKey, id));
80              }
81          }
82  
83  
84  
85          //msg.getProperties().setProperty(org.miloss.fgsms.common.Constants.relatedtransactionKey, relatedTransaction);
86  
87          if (Utility.stringIsNullOrEmpty(transactionthreadid)) {
88              transactionthreadid = UUID.randomUUID().toString();
89              if (MessageProcessor.getSingletonObject().isDependencyInjectionEnabled() && request !=null)
90              {
91                  //insert http header
92                  request.getHeaders().add(new HttpHeader(org.miloss.fgsms.common.Constants.transactionthreadKey, transactionthreadid));
93                  //insert soap header if the message is soap
94              }
95          }
96          try {
97              MessageProcessor.getSingletonObject().setTransactionThreadId(Thread.currentThread().getId(), transactionthreadid);
98          } catch (Exception ex) {
99          }
100         
101         
102 
103 
104 
105         //request.getHeaders()
106         //    String httpport = org.jboss.soa.esb.common.Configuration.getHttpPort();
107         //    String httpsport = org.jboss.soa.esb.common.Configuration.getHttpSecurePort();
108 
109 
110         //grab the original url from the gateway, useful but not fullproof
111         String url = (String) msg.getProperties().getProperty("org.jboss.soa.esb.gateway.original.url");
112         if (Utility.stringIsNullOrEmpty(url)) {
113             if (request != null) {
114 
115                 if (request.getScheme().equalsIgnoreCase("http")) {
116                     url = request.getScheme() + "://" + request.getServerName() + ":" + httpport + request.getRequestURI();
117                 } else if (request.getScheme().equalsIgnoreCase("https")) {
118                     url = request.getScheme() + "://" + request.getServerName() + ":" + httpsport + request.getRequestURI();
119                 }
120             }
121             //   url = request.getProtocol() + request.getServerName() + request.getRequestURI() + request.getLocalAddr() + request.getLocalName()
122             //            + request.getMethod() + request.getPathInfo() + request.getScheme() ;
123         }
124 
125         if (Utility.stringIsNullOrEmpty(url)) {
126             try {
127                 //alternate method, but should always work
128                 url = msg.getHeader().getCall().getTo().getURI().toString();
129                 if (url.startsWith("invm://")) {
130                     log.log(Level.INFO, "fgsms Agent for JbossESBProxyAgent, inbound message is internal esb traffic " + url);
131                     return msg;
132                 }
133                 log.log(Level.DEBUG, "fgsms Agent for JbossESBProxyAgent, inbound message for " + url + " via SOAP To field.");
134             } catch (Exception ex) {
135 //                log.log(Level.WARN, "fgsms Agent for JbossESBProxyAgent, unable to determine the URL or TO field from the message, this message will be ignored");
136                 //               return msg;
137             }
138         }
139         //else {
140         //  log.log(Level.DEBUG, "fgsms Agent for JbossESBProxyAgent, inbound message for " + url + " via transport.");
141         // }
142 
143 
144         if (Utility.stringIsNullOrEmpty(url)) {
145             log.log(Level.WARN, "untable to determine request url, message will be ignored.");
146             return msg;
147         }
148 
149         Integer msgsize = null;
150         try {
151             msgsize = (Integer) msg.getProperties().getProperty("org.jboss.soa.esb.message.byte.size");
152             log.log(Level.DEBUG, "fgsms Agent for JbossESBProxyAgent, inbound message size " + msgsize + " via long.");
153         } catch (Exception ex) {
154         }
155         try {
156             msgsize = Integer.parseInt((String) msg.getProperties().getProperty("org.jboss.soa.esb.message.byte.size"));
157             log.log(Level.DEBUG, "fgsms Agent for JbossESBProxyAgent, inbound message size " + msgsize + " via string.");
158         } catch (Exception ex) {
159         }
160 
161         if (msg.getAttachment().getNamedCount() > 0 || msg.getAttachment().getUnnamedCount() > 0) {
162             log.log(Level.INFO, "fgsms Agent for JbossESBProxyAgent, inbound message has attachments, named: " + msg.getAttachment().getNamedCount() + " unnamed:" + msg.getAttachment().getUnnamedCount());
163             int count = (msg.getAttachment().getNamedCount() + msg.getAttachment().getUnnamedCount());
164             for (int i = 0; i < count; i++) {
165                 log.log(Level.INFO, "fgsms Agent for JbossESBProxyAgent, inbound message has attachments " + i + " type: " + msg.getAttachment().itemAt(i).getClass().getCanonicalName());
166             }
167         }
168 
169 
170 
171         String action = "";;
172         if (request != null) {
173             // request.getHeaders().add(new HttpHeader("TESTHeader","TESTvalue"));
174             action = request.getHeaderValue("soapaction");
175             if (!Utility.stringIsNullOrEmpty(action)) {
176                 action = action.replaceAll("\"", "");
177                 action = action.replaceAll("\'", "");
178             }
179 
180             if (Utility.stringIsNullOrEmpty(action)) {
181                 action = request.getHeaderValue("SOAPAction");
182                 if (!Utility.stringIsNullOrEmpty(action)) {
183                     action = action.replaceAll("\"", "");
184                     action = action.replaceAll("\'", "");
185                 }
186             }
187         }
188         if (Utility.stringIsNullOrEmpty(action)) {
189             action = (String) msg.getProperties().getProperty("SOAPAction");
190             if (!Utility.stringIsNullOrEmpty(action)) {
191                 action = action.replaceAll("\"", "");
192                 action = action.replaceAll("\'", "");
193             }
194         }
195         if (Utility.stringIsNullOrEmpty(action)) {
196 
197             //Action: used by the sender to indicate the semantics of the message. Must be unique. MANDATORY
198             if (msg != null && msg.getHeader() != null && msg.getHeader().getCall() != null
199                     && msg.getHeader().getCall().getAction() != null) {
200                 action = msg.getHeader().getCall().getAction().toString();
201                 if (!Utility.stringIsNullOrEmpty(action)) {
202                     action = action.replaceAll("\"", "");
203                     action = action.replaceAll("\'", "");
204                 }
205             }
206         }
207 
208 
209 
210 
211 
212 
213 
214 
215         String sender = "";
216 
217         //sender is optional
218         if (msg != null && msg.getHeader() != null && msg.getHeader().getCall() != null
219                 && msg.getHeader().getCall().getFrom() != null) {
220             sender = msg.getHeader().getCall().getFrom().toString();
221 
222         }
223         if (Utility.stringIsNullOrEmpty(sender) && request != null) {
224             request.getRemoteUser();
225         }
226         String body = "";
227         if (MessageProcessor.getSingletonObject().shouldAgentRecordRequestContent(url)) {
228             try {
229                 //msg.getBody could be one of several interfaces, for right now, just stick to text bodies
230                 ///org.jboss.internal.soa.esb.message.format.serialized.BodyImpl
231                 //org.jboss.internal.soa.esb.message.format.xml.BodyImpl
232                 if (msg.getBody() instanceof TextBody) {
233                     TextBody t = (TextBody) msg.getBody();
234                     if (t != null) {
235                         //  log.log(Level.WARN, "*******getText()**********");
236                         //   log.log(Level.WARN, t.getText());
237                         //   log.log(Level.WARN, "*******get().toString()***********");
238                         //   log.log(Level.WARN, t.get().toString());
239                         // body = t.getText();
240                         body += t.get().toString();
241                     }
242                 }
243                 if (msg.getBody() instanceof org.jboss.internal.soa.esb.message.format.xml.BodyImpl) {
244                     org.jboss.internal.soa.esb.message.format.xml.BodyImpl t = (org.jboss.internal.soa.esb.message.format.xml.BodyImpl) msg.getBody();
245                     //body = new String(t.getContents());
246                     //  body = t.toString();// new String(t.getContents());
247                     log.log(Level.DEBUG, "body get is of type " + t.get().getClass().getCanonicalName());
248                     body += t.get().toString();
249                 }
250                 if (msg.getBody() instanceof org.jboss.internal.soa.esb.message.format.serialized.BodyImpl) {
251                     org.jboss.internal.soa.esb.message.format.serialized.BodyImpl t = (org.jboss.internal.soa.esb.message.format.serialized.BodyImpl) msg.getBody();
252                     // body = t.toString();//new String(t.getContents());
253                     //body = new String(t.getContents());
254                     log.log(Level.DEBUG, "body get is of type " + t.get().getClass().getCanonicalName());
255                     body += t.get().toString();
256                 }
257                 // log.log(Level.WARN, "fgsms Agent for JbossESBProxyAgent, inbound message for " + url + " has body that I don't know how to identify of type " + msg.getBody().getClass().getName());
258             } catch (Exception ex) {
259                 log.log(Level.WARN, "fgsms Agent for JbossESBProxyAgent, inbound message for " + url + " has body that I don't know how to identify of type " + msg.getBody().getClass().getName());
260             }
261         }
262         if (Utility.stringIsNullOrEmpty(action)) {
263             action = Utility.getActionNameFromXML(body);
264             if (!Utility.stringIsNullOrEmpty(action)) {
265                 action = action.replaceAll("\"", "");
266                 action = action.replaceAll("\'", "");
267             }
268         }
269         if (Utility.stringIsNullOrEmpty(action)) {
270             if (request != null) {
271                 action = request.getMethod();
272             }
273             if (!Utility.stringIsNullOrEmpty(action)) {
274                 action = action.replaceAll("\"", "");
275                 action = action.replaceAll("\'", "");
276             }
277             //action = org.miloss.fgsms.common.Constants.Undetermineable;
278         }
279 
280         if (Utility.stringIsNullOrEmpty(action)) {
281             action = org.miloss.fgsms.common.Constants.Undetermineable;
282         }
283 
284         if (action.toLowerCase().trim().equals(org.miloss.fgsms.common.Constants.DCSaction3.toLowerCase().trim())) {
285             log.log(Level.DEBUG, "fgsms, skipping the request for DCS AddData to prevent recursive looping. This is normal and no action is required.");
286             return msg;     //prevent recursive loops
287         }
288         if (action.toLowerCase().trim().equals(org.miloss.fgsms.common.Constants.DCSaction4.toLowerCase().trim())) {
289             log.log(Level.DEBUG, "fgsms, skipping the request for DCS AddData to prevent recursive looping. This is normal and no action is required.");
290             return msg;     //prevent recursive loops
291         }
292 
293         if (action.toLowerCase().trim().equals(org.miloss.fgsms.common.Constants.DCSaction.toLowerCase().trim())) {
294             log.log(Level.DEBUG, "fgsms, skipping the request for DCS AddData to prevent recursive looping. This is normal and no action is required.");
295             return msg;     //prevent recursive loops
296         }
297         //if (action.equalsIgnoreCase("urn:org:miloss:fgsms:services:interfaces:policyConfiguration/policyConfigurationService/GetServicePolicy")) {
298         if (action.toLowerCase().trim().equals(org.miloss.fgsms.common.Constants.PCSaction.toLowerCase().trim())) {
299             log.log(Level.DEBUG, "fgsms, skipping the request for PCS GetServicePolicy to prevent recursive looping. This is normal and no action is required.");
300             return msg;     //prevent recursive loops
301         }
302 
303         if (action.toLowerCase().trim().equals(org.miloss.fgsms.common.Constants.DCSaction2.toLowerCase().trim())) {
304             log.log(Level.DEBUG, "fgsms, skipping the request for DCS AddData to prevent recursive looping. This is normal and no action is required.");
305             return msg;     //prevent recursive loops
306         }
307         //if (action.equalsIgnoreCase("urn:org:miloss:fgsms:services:interfaces:policyConfiguration/policyConfigurationService/GetServicePolicy")) {
308         if (action.toLowerCase().trim().equals(org.miloss.fgsms.common.Constants.PCSaction2.toLowerCase().trim())) {
309             log.log(Level.DEBUG, "fgsms, skipping the request for PCS GetServicePolicy to prevent recursive looping. This is normal and no action is required.");
310             return msg;     //prevent recursive loops
311         }
312 
313         log.log(Level.INFO, "fgsms Agent for JbossESBProxyAgent, inbound message for " + url + " action " + action);
314 
315 //        Long dob = (Long) msg.getProperties().getProperty("org.jboss.soa.esb.message.time.dob");
316         //if (dob == null) {
317         //    long dob = System.currentTimeMillis();
318         //}//public static void processMessageInput(String XMLrequest, String url, String soapAction, String HttpUsername, String HashCode,
319         //HashMap headers, String ipaddress, String agentclassname) {
320         String ip = "";
321         if (request != null) {
322             ip = request.getRemoteAddr();
323         }
324         if (msgsize == null) {
325             MessageProcessor.getSingletonObject().processMessageInput(body, body.length(), url, action, sender, id, headers, ip, JbossESBProxyAction.class.getCanonicalName(), relatedTransaction, transactionthreadid);
326         } else {
327             //related
328             //threadid
329             MessageProcessor.getSingletonObject().processMessageInput(body, msgsize, url, action, sender, id, headers, ip, JbossESBProxyAction.class.getCanonicalName(), relatedTransaction, transactionthreadid);
330         }
331         return msg;
332     }
333 
334     /**
335      * this is unlikely to ever be called
336      * @param msg
337      * @param thrwbl 
338      */
339     public void processException(Message msg, Throwable thrwbl) {
340 
341         log.log(Level.INFO, "Current VM Memory : total = " + Runtime.getRuntime().totalMemory() + " free = " + Runtime.getRuntime().freeMemory());
342 
343 
344         for (int i = 0; i < msg.getProperties().getNames().length; i++) {
345             log.log(Level.DEBUG, "key = " + msg.getProperties().getNames()[i] + " value = " + msg.getProperties().getProperty(msg.getProperties().getNames()[i]));
346         }
347 
348 
349         //Serializable obj = (Serializable) msg.getBody().get();
350         String id = "";
351         try {
352             id = (String) msg.getProperties().getProperty("fgsms.TransactionID");
353         } catch (Exception ex) {
354             log.log(Level.ERROR, "fgsms Agent for JbossESBPostProxyAgent, could not obtain the transaction id, this was unexpected." + ex.getLocalizedMessage());
355             return;// msg;
356         }
357         if (Utility.stringIsNullOrEmpty(id)) {
358             log.log(Level.ERROR, "fgsms Agent for JbossESBPostProxyAgent, outbound message does not have transaction id, this was unexpected.");
359             return;// msg;
360         }
361 
362         HttpRequest request = HttpRequest.getRequest(msg);
363         HttpResponse response = HttpResponse.getResponse(msg);
364 
365 
366         //grab the original url from the gateway, useful but not fullproof
367         String url = (String) msg.getProperties().getProperty("org.jboss.soa.esb.gateway.original.url");
368         if (Utility.stringIsNullOrEmpty(url)) {
369             if (request != null) {
370 
371                 if (request.getScheme().equalsIgnoreCase("http")) {
372                     url = request.getScheme() + "://" + request.getServerName() + ":" + httpport + request.getRequestURI();
373                 } else if (request.getScheme().equalsIgnoreCase("https")) {
374                     url = request.getScheme() + "://" + request.getServerName() + ":" + httpsport + request.getRequestURI();
375                 }
376             }
377             //   url = request.getProtocol() + request.getServerName() + request.getRequestURI() + request.getLocalAddr() + request.getLocalName()
378             //            + request.getMethod() + request.getPathInfo() + request.getScheme() ;
379         }
380 
381         if (Utility.stringIsNullOrEmpty(url)) {
382             try {
383                 //alternate method, but should always work
384                 url = msg.getHeader().getCall().getTo().getURI().toString();
385                 if (url.startsWith("invm://")) {
386                     log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, inbound message is internal esb traffic " + url);
387                     return;
388                 }
389                 log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, inbound message for " + url + " via SOAP To field.");
390             } catch (Exception ex) {
391 //                log.log(Level.WARN, "fgsms Agent for JbossESBPostProxyAgent, unable to determine the URL or TO field from the message, this message will be ignored");
392                 //               return msg;
393             }
394         }
395         //else {
396         //  log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, inbound message for " + url + " via transport.");
397         // }
398 
399 
400         if (Utility.stringIsNullOrEmpty(url)) {
401             log.log(Level.WARN, "untable to determine request url, message will be ignored.");
402             return;
403         }
404 
405 
406         Long msgsize = null;
407         try {
408             Integer i = (Integer) msg.getProperties().getProperty("org.jboss.soa.esb.message.byte.size");
409             if (i != null) {
410                 msgsize = i.longValue();
411             }
412             if (msgsize != null) {
413                 log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, outbound message size " + msgsize + " via long.");
414             }
415         } catch (Exception ex) {
416         }
417         if (msgsize == null) {
418             try {
419                 msgsize = Long.parseLong((String) msg.getProperties().getProperty("org.jboss.soa.esb.message.byte.size"));
420                 if (msgsize != null) {
421                     log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, outbound message size " + msgsize + " via string.");
422                 }
423             } catch (Exception ex) {
424             }
425         }
426         if (msgsize == null) {
427             try {
428                 msgsize = response.getLength();
429                 if (msgsize != null) {
430                     log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, outbound message size " + msgsize + " via response object.");
431                 }
432             } catch (Exception ex) {
433             }
434         }
435 
436 
437 
438         boolean fault = true;
439 
440         log.log(Level.WARN, "fgsms, this message to " + url + " transaction id:" + id.toString() + " has faulted.");
441 
442 //        Long dod = (Long) params.get("org.jboss.soa.esb.message.time.dod");
443         //      if (dod == null) {
444         Long dod = System.currentTimeMillis();
445         //    }
446 
447         if (msg.getAttachment().getNamedCount() > 0 || msg.getAttachment().getUnnamedCount() > 0) {
448             log.log(Level.INFO, "fgsms Agent for JbossESBPostProxyAgent, outbound message has attachments, named: " + msg.getAttachment().getNamedCount() + " unnamed:" + msg.getAttachment().getUnnamedCount());
449             int count = (msg.getAttachment().getNamedCount() + msg.getAttachment().getUnnamedCount());
450             for (int i = 0; i < count; i++) {
451                 log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, outbound message has attachments " + i + " type: " + msg.getAttachment().itemAt(i).getClass().getCanonicalName());
452             }
453         }
454 
455 
456         String body = "";
457         try {
458             body = thrwbl.getMessage();
459             body += thrwbl.toString();
460         } catch (Exception ex) {
461             log.log(Level.DEBUG, "fgsms Agent for JbossESBPostProxyAgent, outbound message for " + url + " has a non-text body", ex);
462 
463         }
464 
465        
466         if (msgsize == null) {
467             MessageProcessor.getSingletonObject().processMessageOutput(id, body, body.length(), true, Long.valueOf(dod), new HashMap());
468         } else {
469             MessageProcessor.getSingletonObject().processMessageOutput(id, body, msgsize.intValue(), true, Long.valueOf(dod),new HashMap());
470         }
471     }
472 
473     public void processSuccess(Message msg) {
474         //log.log(Level.DEBUG, "#D1000 fgsms JbossESBProxyAgentProxyAction, exception recieved:" + msg.toString());
475     }
476 
477     public void initialise() throws ActionLifecycleException {
478         log.log(Level.INFO, "fgsms Agent for JbossESB Action Pipeline Processor started.");
479     }
480 
481     public void destroy() throws ActionLifecycleException {
482     }
483 }