1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.chemistry.opencmis.client.bindings.spi.http;
20
21 import java.math.BigInteger;
22 import java.util.Map;
23
24 import org.apache.chemistry.opencmis.client.bindings.spi.BindingSession;
25 import org.apache.chemistry.opencmis.commons.exceptions.CmisBaseException;
26 import org.apache.chemistry.opencmis.commons.exceptions.CmisRuntimeException;
27 import org.apache.chemistry.opencmis.commons.impl.ClassLoaderUtil;
28 import org.apache.chemistry.opencmis.commons.impl.UrlBuilder;
29 import org.slf4j.Logger;
30 import org.slf4j.LoggerFactory;
31
32
33
34
35
36
37
38
39
40
41 public class DelayingHttpInvoker implements HttpInvoker {
42
43 private static final Logger LOG = LoggerFactory.getLogger(DelayingHttpInvoker.class);
44
45
46
47
48
49 public static final String DELEGTAE_HTTP_INVOKER_CLASS = "org.apache.chemistry.opencmis.binding.httpinvoker.delay.delegate.classname";
50
51
52
53 public static final String DELAY_TIME = "org.apache.chemistry.opencmis.binding.httpinvoker.delay.delaytime";
54
55 protected static final String DELEGTAE_HTTP_INVOKER = "org.apache.chemistry.opencmis.client.bindings.spi.http.limiter.httpInvoker";
56 protected static final String LAST_EXECUTION = "org.apache.chemistry.opencmis.client.bindings.spi.http.limiter.lastExecution";
57
58 public DelayingHttpInvoker() {
59 }
60
61 @Override
62 public Response invokeGET(UrlBuilder url, BindingSession session) {
63 delay(session);
64 return getHttpInvoker(session).invokeGET(url, session);
65 }
66
67 @Override
68 public Response invokeGET(UrlBuilder url, BindingSession session, BigInteger offset, BigInteger length) {
69 delay(session);
70 return getHttpInvoker(session).invokeGET(url, session, offset, length);
71 }
72
73 @Override
74 public Response invokePOST(UrlBuilder url, String contentType, Output writer, BindingSession session) {
75 delay(session);
76 return getHttpInvoker(session).invokePOST(url, contentType, writer, session);
77 }
78
79 @Override
80 public Response invokePUT(UrlBuilder url, String contentType, Map<String, String> headers, Output writer,
81 BindingSession session) {
82 delay(session);
83 return getHttpInvoker(session).invokePUT(url, contentType, headers, writer, session);
84 }
85
86 @Override
87 public Response invokeDELETE(UrlBuilder url, BindingSession session) {
88 delay(session);
89 return getHttpInvoker(session).invokeDELETE(url, session);
90 }
91
92 protected void delay(BindingSession session) {
93 session.writeLock();
94 try {
95 int delayTime = session.get(DELAY_TIME, -1);
96 if (delayTime < 0) {
97 if (LOG.isInfoEnabled()) {
98 LOG.info("No delay time configured.");
99 }
100 return;
101 }
102
103 Object lastExcution = session.get(LAST_EXECUTION);
104 if (lastExcution instanceof Long) {
105 long lastExcutionLong = (Long) lastExcution;
106 long now = System.currentTimeMillis();
107 if (now - lastExcutionLong < delayTime) {
108 try {
109 Thread.sleep(delayTime - (now - lastExcutionLong));
110 } catch (InterruptedException e) {
111 if (LOG.isDebugEnabled()) {
112 LOG.debug("Interrupted sleep", e);
113 }
114 }
115 }
116 }
117
118 session.put(LAST_EXECUTION, System.currentTimeMillis());
119
120 } finally {
121 session.writeUnlock();
122 }
123 }
124
125 protected HttpInvoker getHttpInvoker(BindingSession session) {
126 HttpInvoker invoker = (HttpInvoker) session.get(DELEGTAE_HTTP_INVOKER);
127
128 if (invoker != null) {
129 return invoker;
130 }
131
132 session.writeLock();
133 try {
134
135 invoker = (HttpInvoker) session.get(DELEGTAE_HTTP_INVOKER);
136 if (invoker != null) {
137 return invoker;
138 }
139
140
141 try {
142 String invokerName = (String) session.get(DELEGTAE_HTTP_INVOKER_CLASS);
143 if (invokerName == null) {
144 invoker = new DefaultHttpInvoker();
145 } else {
146 invoker = (HttpInvoker) ClassLoaderUtil.loadClass(invokerName).newInstance();
147 }
148 } catch (CmisBaseException e) {
149 throw e;
150 } catch (Exception e) {
151 throw new CmisRuntimeException("Delegate HTTP invoker cannot be initialized: " + e.getMessage(), e);
152 }
153
154
155 session.put(DELEGTAE_HTTP_INVOKER, invoker, true);
156 } finally {
157 session.writeUnlock();
158 }
159
160 return invoker;
161 }
162 }