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 org.apache.hc.client5.http.impl.routing;
29
30 import java.net.InetAddress;
31
32 import org.apache.hc.client5.http.HttpRoute;
33 import org.apache.hc.client5.http.RouteInfo.LayerType;
34 import org.apache.hc.client5.http.RouteInfo.TunnelType;
35 import org.apache.hc.client5.http.routing.HttpRouteDirector;
36 import org.apache.hc.core5.http.HttpHost;
37 import org.junit.jupiter.api.Assertions;
38 import org.junit.jupiter.api.Test;
39
40
41
42
43 class TestRouteDirector {
44
45
46 public final static HttpHost TARGET1 = new HttpHost("target1.test.invalid", 80);
47 public final static HttpHost TARGET2 = new HttpHost("target2.test.invalid", 8080);
48
49
50
51
52 public final static HttpHost PROXY1 = new HttpHost("proxy1.test.invalid", 80);
53 public final static HttpHost PROXY2 = new HttpHost("proxy2.test.invalid", 1080);
54 public final static HttpHost PROXY3 = new HttpHost("proxy3.test.invalid", 88);
55
56 public final static InetAddress LOCAL41;
57 public final static InetAddress LOCAL42;
58 public final static InetAddress LOCAL61;
59 public final static InetAddress LOCAL62;
60
61
62 static {
63 try {
64 LOCAL41 = InetAddress.getByAddress(new byte[]{127, 0, 0, 1});
65 LOCAL42 = InetAddress.getByAddress(new byte[]{127, 0, 0, 2});
66
67 LOCAL61 = InetAddress.getByAddress(new byte[]{
68 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1
69 });
70 LOCAL62 = InetAddress.getByAddress(new byte[]{
71 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2
72 });
73
74 } catch (final Exception x) {
75 throw new ExceptionInInitializerError(x);
76 }
77 }
78
79 @Test
80 void testIllegal() {
81 final HttpRouteDirector rowdy = BasicRouteDirector.INSTANCE;
82 final HttpRoute route = new HttpRoute(TARGET1);
83 Assertions.assertThrows(NullPointerException.class, () ->
84 rowdy.nextStep(null, route));
85 }
86
87 @Test
88 void testDirect() {
89
90 final HttpRouteDirector rowdy = BasicRouteDirector.INSTANCE;
91 final HttpRoute route1 = new HttpRoute(TARGET1);
92 final HttpRoute route2 = new HttpRoute(TARGET2);
93 final HttpRoute route1p1 = new HttpRoute(TARGET1, null, PROXY1, false);
94
95 int step = rowdy.nextStep(route1, null);
96 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route1");
97
98 step = rowdy.nextStep(route2, null);
99 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route2");
100
101 step = rowdy.nextStep(route1, route1);
102 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1 not detected");
103
104 step = rowdy.nextStep(route2, route2);
105 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route2 not detected");
106
107 step = rowdy.nextStep(route1, route2);
108 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable target not detected");
109
110 step = rowdy.nextStep(route1, route1p1);
111 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "invalid proxy not detected");
112 }
113
114 @Test
115 void testProxy() {
116
117 final HttpRouteDirector rowdy = BasicRouteDirector.INSTANCE;
118 final HttpRoute route1p1 = new HttpRoute(TARGET1, null, PROXY1, false);
119 final HttpRoute route1p2 = new HttpRoute(TARGET1, null, PROXY2, false);
120 final HttpRoute route2p1 = new HttpRoute(TARGET2, null, PROXY1, false);
121 final HttpRoute route0 = new HttpRoute(PROXY1);
122 final HttpRoute route1 = new HttpRoute(TARGET1);
123
124 int step = rowdy.nextStep(route1p1, null);
125 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1p1");
126
127 step = rowdy.nextStep(route1p2, null);
128 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1p2");
129
130 step = rowdy.nextStep(route1p1, route1p1);
131 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1p1 not detected");
132
133 step = rowdy.nextStep(route1p2, route1p2);
134 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1p2 not detected");
135
136 step = rowdy.nextStep(route2p1, route2p1);
137 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route2p1 not detected");
138
139 step = rowdy.nextStep(route1p1, route1p2);
140 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1p1 via route1p2 not detected");
141
142 step = rowdy.nextStep(route1p1, route2p1);
143 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1p1 via route2p1 not detected");
144
145 step = rowdy.nextStep(route1p1, route0);
146 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1p1 via route0 not detected");
147
148 step = rowdy.nextStep(route1p1, route1);
149 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1p1 via route1 not detected");
150 }
151
152 @Test
153 void testProxyChain() {
154 final HttpHost[] chainA = {PROXY1};
155 final HttpHost[] chainB = {PROXY1, PROXY2};
156 final HttpHost[] chainC = {PROXY2, PROXY1};
157
158 final HttpRouteDirector rowdy = BasicRouteDirector.INSTANCE;
159 final HttpRoute route1cA = new HttpRoute(TARGET1, null, chainA, false,
160 TunnelType.PLAIN, LayerType.PLAIN);
161 final HttpRoute route1cB = new HttpRoute(TARGET1, null, chainB, false,
162 TunnelType.PLAIN, LayerType.PLAIN);
163 final HttpRoute route1cC = new HttpRoute(TARGET1, null, chainC, false,
164 TunnelType.PLAIN, LayerType.PLAIN);
165 final HttpRoute route1cD = new HttpRoute(TARGET1, null, chainC, false,
166 TunnelType.PLAIN, LayerType.PLAIN);
167
168 int step = rowdy.nextStep(route1cA, null);
169 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1cA");
170
171 step = rowdy.nextStep(route1cB, null);
172 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1cB");
173
174 step = rowdy.nextStep(route1cC, null);
175 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1cC");
176
177 step = rowdy.nextStep(route1cD, null);
178 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1cD");
179
180
181 step = rowdy.nextStep(route1cB, route1cA);
182 Assertions.assertEquals(HttpRouteDirector.TUNNEL_PROXY, step, "wrong step to route 1cB from 1cA");
183
184 step = rowdy.nextStep(route1cB, route1cB);
185 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route 1cB not detected");
186
187 step = rowdy.nextStep(route1cB, route1cC);
188 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route 1cB from 1cC not detected");
189
190 step = rowdy.nextStep(route1cB, route1cD);
191 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route 1cB from 1cD not detected");
192
193
194 step = rowdy.nextStep(route1cA, route1cB);
195 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route 1cA from 1cB not detected");
196 }
197
198 @Test
199 void testLocalDirect() {
200
201 final HttpRouteDirector rowdy = BasicRouteDirector.INSTANCE;
202 final HttpRoute route1l41 = new HttpRoute(TARGET1, LOCAL41, false);
203 final HttpRoute route1l42 = new HttpRoute(TARGET1, LOCAL42, false);
204 final HttpRoute route1l61 = new HttpRoute(TARGET1, LOCAL61, false);
205 final HttpRoute route1l00 = new HttpRoute(TARGET1, null, false);
206
207 int step = rowdy.nextStep(route1l41, null);
208 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route1l41");
209
210 step = rowdy.nextStep(route1l42, null);
211 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route1l42");
212
213 step = rowdy.nextStep(route1l61, null);
214 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route1l61");
215
216 step = rowdy.nextStep(route1l00, null);
217 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route1l00");
218
219 step = rowdy.nextStep(route1l41, route1l41);
220 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1l41 not detected");
221
222 step = rowdy.nextStep(route1l42, route1l42);
223 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1l42 not detected");
224
225 step = rowdy.nextStep(route1l61, route1l61);
226 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1l61 not detected");
227
228 step = rowdy.nextStep(route1l00, route1l00);
229 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1l00 not detected");
230
231
232 step = rowdy.nextStep(route1l41, route1l42);
233 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1l41 via route1l42 not detected");
234
235 step = rowdy.nextStep(route1l41, route1l61);
236 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1l41 via route1l61 not detected");
237
238 step = rowdy.nextStep(route1l41, route1l00);
239 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1l41 via route1l00 not detected");
240
241
242 step = rowdy.nextStep(route1l00, route1l41);
243 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1l00 as route1l41 not detected");
244
245 step = rowdy.nextStep(route1l00, route1l42);
246 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1l00 as route1l42 not detected");
247
248 step = rowdy.nextStep(route1l00, route1l61);
249 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1l00 as route1l61 not detected");
250 }
251
252 @Test
253 void testDirectSecure() {
254
255 final HttpRouteDirector rowdy = BasicRouteDirector.INSTANCE;
256 final HttpRoute route1u = new HttpRoute(TARGET1, null, false);
257 final HttpRoute route1s = new HttpRoute(TARGET1, null, true);
258 final HttpRoute route1p1u = new HttpRoute(TARGET1, null, PROXY1, false);
259 final HttpRoute route1p1s = new HttpRoute(TARGET1, null, PROXY1, true);
260
261 int step = rowdy.nextStep(route1u, null);
262 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route1u");
263
264 step = rowdy.nextStep(route1s, null);
265 Assertions.assertEquals(HttpRouteDirector.CONNECT_TARGET, step, "wrong step to route1s");
266
267
268 step = rowdy.nextStep(route1u, route1s);
269 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route 1u from 1s not detected");
270
271
272 step = rowdy.nextStep(route1s, route1u);
273 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route 1s from 1u not detected");
274
275
276 step = rowdy.nextStep(route1s, route1p1u);
277 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route 1s from 1p1u not detected");
278
279 step = rowdy.nextStep(route1s, route1p1s);
280 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route 1s from 1p1s not detected");
281 }
282
283 @Test
284 void testProxyTLS() {
285
286 final HttpRouteDirector rowdy = BasicRouteDirector.INSTANCE;
287 final HttpRoute route1 = new HttpRoute
288 (TARGET1, null, PROXY1, false,
289 TunnelType.PLAIN, LayerType.PLAIN);
290 final HttpRoute route1t = new HttpRoute
291 (TARGET1, null, PROXY1, false,
292 TunnelType.TUNNELLED, LayerType.PLAIN);
293 final HttpRoute route1tl = new HttpRoute
294 (TARGET1, null, PROXY1, false,
295 TunnelType.TUNNELLED, LayerType.LAYERED);
296 final HttpRoute route1s = new HttpRoute
297 (TARGET1, null, PROXY1, true,
298 TunnelType.PLAIN, LayerType.PLAIN);
299 final HttpRoute route1ts = new HttpRoute
300 (TARGET1, null, PROXY1, true,
301 TunnelType.TUNNELLED, LayerType.PLAIN);
302 final HttpRoute route1tls = new HttpRoute
303 (TARGET1, null, PROXY1, true,
304 TunnelType.TUNNELLED, LayerType.LAYERED);
305
306
307
308 int step = rowdy.nextStep(route1, null);
309 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1");
310
311 step = rowdy.nextStep(route1t, null);
312 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1t");
313
314 step = rowdy.nextStep(route1tl, null);
315 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1tl");
316
317 step = rowdy.nextStep(route1s, null);
318 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1s");
319
320 step = rowdy.nextStep(route1ts, null);
321 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1ts");
322
323 step = rowdy.nextStep(route1tls, null);
324 Assertions.assertEquals(HttpRouteDirector.CONNECT_PROXY, step, "wrong step to route1tls");
325
326
327 step = rowdy.nextStep(route1, route1);
328 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1 not detected");
329
330 step = rowdy.nextStep(route1t, route1t);
331 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1t not detected");
332
333 step = rowdy.nextStep(route1tl, route1tl);
334 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1tl not detected");
335
336 step = rowdy.nextStep(route1s, route1s);
337 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1s not detected");
338
339 step = rowdy.nextStep(route1ts, route1ts);
340 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1ts not detected");
341
342 step = rowdy.nextStep(route1tls, route1tls);
343 Assertions.assertEquals(HttpRouteDirector.COMPLETE, step, "complete route1tls not detected");
344
345
346 step = rowdy.nextStep(route1, route1t);
347 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1 from 1t not detected");
348
349 step = rowdy.nextStep(route1, route1tl);
350 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1 from 1tl not detected");
351
352
353 step = rowdy.nextStep(route1, route1s);
354 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1 from 1s not detected");
355
356 step = rowdy.nextStep(route1, route1ts);
357 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1 from 1ts not detected");
358
359 step = rowdy.nextStep(route1, route1tls);
360 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1 from 1tls not detected");
361
362
363
364 step = rowdy.nextStep(route1s, route1);
365 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1s from 1 not detected");
366
367
368 step = rowdy.nextStep(route1tls, route1tl);
369 Assertions.assertEquals(HttpRouteDirector.UNREACHABLE, step, "unreachable route1tls from 1tl not detected");
370
371
372
373 step = rowdy.nextStep(route1t, route1);
374 Assertions.assertEquals(HttpRouteDirector.TUNNEL_TARGET, step, "wrong step to route1t from 1");
375
376 step = rowdy.nextStep(route1tl, route1);
377 Assertions.assertEquals(HttpRouteDirector.TUNNEL_TARGET, step, "wrong step to route1tl from 1");
378
379 step = rowdy.nextStep(route1tls, route1);
380 Assertions.assertEquals(HttpRouteDirector.TUNNEL_TARGET, step, "wrong step to route1tls from 1");
381
382
383
384 step = rowdy.nextStep(route1tl, route1t);
385 Assertions.assertEquals(HttpRouteDirector.LAYER_PROTOCOL, step, "wrong step to route1tl from 1t");
386
387 step = rowdy.nextStep(route1tl, route1ts);
388 Assertions.assertEquals(HttpRouteDirector.LAYER_PROTOCOL, step, "wrong step to route1tl from 1ts");
389
390 step = rowdy.nextStep(route1tls, route1t);
391 Assertions.assertEquals(HttpRouteDirector.LAYER_PROTOCOL, step, "wrong step to route1tls from 1t");
392
393 step = rowdy.nextStep(route1tls, route1ts);
394 Assertions.assertEquals(HttpRouteDirector.LAYER_PROTOCOL, step, "wrong step to route1tls from 1ts");
395
396
397
398
399 }
400
401 }