1 package ca.uhn.hl7v2.hoh.relay.sender;
2
3 import java.io.IOException;
4 import java.net.ConnectException;
5 import java.util.Map;
6
7 import org.springframework.beans.factory.BeanNameAware;
8 import org.springframework.beans.factory.InitializingBean;
9
10 import ca.uhn.hl7v2.HL7Exception;
11 import ca.uhn.hl7v2.hoh.api.DecodeException;
12 import ca.uhn.hl7v2.hoh.api.EncodeException;
13 import ca.uhn.hl7v2.hoh.api.IReceivable;
14 import ca.uhn.hl7v2.hoh.hapi.api.MessageSendable;
15 import ca.uhn.hl7v2.hoh.hapi.client.HohClientMultithreaded;
16 import ca.uhn.hl7v2.hoh.relay.Binder;
17 import ca.uhn.hl7v2.hoh.util.Validate;
18 import ca.uhn.hl7v2.model.Message;
19 import ca.uhn.hl7v2.protocol.ApplicationRouter;
20 import ca.uhn.hl7v2.protocol.MetadataKeys;
21 import ca.uhn.hl7v2.protocol.ReceivingApplicationException;
22 import ca.uhn.hl7v2.util.Terser;
23
24 public class RelayHttpSender extends HohClientMultithreaded implements IRelaySender<Message>, BeanNameAware, InitializingBean {
25
26 private static final org.slf4j.Logger ourLog = org.slf4j.LoggerFactory.getLogger(RelayHttpSender.class);
27 private String myBeanName;
28 private int myIoRetries = 0;
29
30
31
32
33 public void afterPropertiesSet() throws Exception {
34 Validate.propertySet(getUrl(), "Url");
35 ourLog.info("Sender [{}] will transmit by HL7 over HTTP to {}", myBeanName, getUrl().toExternalForm());
36 }
37
38
39
40
41
42
43 public boolean canProcess(Message theMessage) {
44 return true;
45 }
46
47
48
49
50 public String getBeanName() {
51 return myBeanName;
52 }
53
54
55
56
57 public int getIoRetries() {
58 return myIoRetries;
59 }
60
61
62
63
64 public Message processMessage(Message theMessage, Map<String, Object> theMetadata) throws ReceivingApplicationException, HL7Exception {
65 String sendingIp = (String) theMetadata.get(ApplicationRouter.METADATA_KEY_SENDING_IP);
66 Object sendingPort = theMetadata.get(ApplicationRouter.METADATA_KEY_SENDING_PORT);
67 String controlId = (String) theMetadata.get(ApplicationRouter.METADATA_KEY_MESSAGE_CONTROL_ID);
68 String rawMessage = (String) theMetadata.get(MetadataKeys.IN_RAW_MESSAGE);
69
70 ourLog.info("Relaying message ({} bytes) with ID {} from {}:{} to URL {}", new Object[] {rawMessage.length(), controlId, sendingIp, sendingPort, getUrl()});
71
72 IReceivable<Message> response;
73 long delay = System.currentTimeMillis();
74 int attempt = -1;
75 while(true) {
76 attempt++;
77
78 if (attempt > 0) {
79 ourLog.info("This is attempt {}", attempt);
80 }
81
82 try {
83 response = sendAndReceiveMessage(new MessageSendable(theMessage));
84 delay = System.currentTimeMillis() - delay;
85 } catch (DecodeException e) {
86 ourLog.error("Failed to process HL7 over HTTP response from URL \"" + getUrl().toExternalForm() + "\"", e);
87 throw new HL7Exception(Binder.getProductname() + " - Failed to process HL7 over HTTP response from URL \"" + getUrl().toExternalForm() + "\" - Error was: " + e.getMessage());
88 } catch (ConnectException e) {
89 ourLog.info("Failed to connect to URL \"" + getUrl().toExternalForm() + "\" - Error was: " + e.getMessage());
90 throw new HL7Exception(Binder.getProductname() + " - Failed to connect to URL \"" + getUrl().toExternalForm() + "\" - Error was: " + e.getMessage());
91 } catch (IOException e) {
92 if (attempt < myIoRetries) {
93 ourLog.warn("Got an IOException, going to retry transmission: " + e.toString());
94 continue;
95 }
96 ourLog.error("IO Exception communicating with URL \"" + getUrl().toExternalForm() + "\"", e);
97 throw new HL7Exception(Binder.getProductname() + " - IO Exception communicating with URL URL \"" + getUrl().toExternalForm() + "\" - Error was: " + e.getMessage());
98 } catch (EncodeException e) {
99 ourLog.error("Failed to create HTTP request", e);
100 throw new HL7Exception(Binder.getProductname() + " - Failed to create HTTP request - Error was: " + e.getMessage());
101 }
102
103 break;
104 }
105
106 String responseControlId = new Terser(response.getMessage()).get("/MSH-10");
107 ourLog.info("Received response to ID {} with ID {} in {} ms", new Object[] {controlId, responseControlId, delay});
108
109 return response.getMessage();
110 }
111
112
113
114
115 public void setBeanName(String theBeanName) {
116 myBeanName = theBeanName;
117 }
118
119
120
121
122
123 public void setIoRetries(int theIoRetries) {
124 myIoRetries = theIoRetries;
125 }
126
127
128 }