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 package org.apache.hc.core5.http2.impl.nio.bootstrap;
28
29 import java.util.ArrayList;
30 import java.util.List;
31
32 import org.apache.hc.core5.function.Callback;
33 import org.apache.hc.core5.function.Decorator;
34 import org.apache.hc.core5.function.Supplier;
35 import org.apache.hc.core5.http.config.CharCodingConfig;
36 import org.apache.hc.core5.http.impl.DefaultAddressResolver;
37 import org.apache.hc.core5.http.nio.AsyncPushConsumer;
38 import org.apache.hc.core5.http.nio.ssl.TlsStrategy;
39 import org.apache.hc.core5.http.protocol.HttpProcessor;
40 import org.apache.hc.core5.http.protocol.RequestHandlerRegistry;
41 import org.apache.hc.core5.http.protocol.UriPatternType;
42 import org.apache.hc.core5.http2.config.H2Config;
43 import org.apache.hc.core5.http2.impl.H2Processors;
44 import org.apache.hc.core5.http2.impl.nio.ClientH2StreamMultiplexerFactory;
45 import org.apache.hc.core5.http2.impl.nio.ClientH2PrefaceHandler;
46 import org.apache.hc.core5.http2.impl.nio.H2StreamListener;
47 import org.apache.hc.core5.http2.nio.support.DefaultAsyncPushConsumerFactory;
48 import org.apache.hc.core5.http2.ssl.H2ClientTlsStrategy;
49 import org.apache.hc.core5.reactor.IOReactorConfig;
50 import org.apache.hc.core5.reactor.IOSession;
51 import org.apache.hc.core5.reactor.IOSessionListener;
52 import org.apache.hc.core5.util.Args;
53
54
55
56
57
58
59 public class H2MultiplexingRequesterBootstrap {
60
61 private final List<HandlerEntry<Supplier<AsyncPushConsumer>>> pushConsumerList;
62 private UriPatternType uriPatternType;
63 private IOReactorConfig ioReactorConfig;
64 private HttpProcessor httpProcessor;
65 private CharCodingConfig charCodingConfig;
66 private H2Config h2Config;
67 private TlsStrategy tlsStrategy;
68 private boolean strictALPNHandshake;
69 private Decorator<IOSession> ioSessionDecorator;
70 private Callback<Exception> exceptionCallback;
71 private IOSessionListener sessionListener;
72 private H2StreamListener streamListener;
73
74 private H2MultiplexingRequesterBootstrap() {
75 this.pushConsumerList = new ArrayList<>();
76 }
77
78 public static H2MultiplexingRequesterBootstrap bootstrap() {
79 return new H2MultiplexingRequesterBootstrap();
80 }
81
82
83
84
85 public final H2MultiplexingRequesterBootstrap setIOReactorConfig(final IOReactorConfig ioReactorConfig) {
86 this.ioReactorConfig = ioReactorConfig;
87 return this;
88 }
89
90
91
92
93 public final H2MultiplexingRequesterBootstrap setHttpProcessor(final HttpProcessor httpProcessor) {
94 this.httpProcessor = httpProcessor;
95 return this;
96 }
97
98
99
100
101 public final H2MultiplexingRequesterBootstrap setH2Config(final H2Config h2Config) {
102 this.h2Config = h2Config;
103 return this;
104 }
105
106
107
108
109 public final H2MultiplexingRequesterBootstrap setCharCodingConfig(final CharCodingConfig charCodingConfig) {
110 this.charCodingConfig = charCodingConfig;
111 return this;
112 }
113
114
115
116
117 public final H2MultiplexingRequesterBootstrap setTlsStrategy(final TlsStrategy tlsStrategy) {
118 this.tlsStrategy = tlsStrategy;
119 return this;
120 }
121
122 public final H2MultiplexingRequesterBootstrap setStrictALPNHandshake(final boolean strictALPNHandshake) {
123 this.strictALPNHandshake = strictALPNHandshake;
124 return this;
125 }
126
127
128
129
130 public final H2MultiplexingRequesterBootstrap setIOSessionDecorator(final Decorator<IOSession> ioSessionDecorator) {
131 this.ioSessionDecorator = ioSessionDecorator;
132 return this;
133 }
134
135
136
137
138 public final H2MultiplexingRequesterBootstrap setExceptionCallback(final Callback<Exception> exceptionCallback) {
139 this.exceptionCallback = exceptionCallback;
140 return this;
141 }
142
143
144
145
146 public final H2MultiplexingRequesterBootstrap setIOSessionListener(final IOSessionListener sessionListener) {
147 this.sessionListener = sessionListener;
148 return this;
149 }
150
151
152
153
154 public final H2MultiplexingRequesterBootstrap setStreamListener(final H2StreamListener streamListener) {
155 this.streamListener = streamListener;
156 return this;
157 }
158
159
160
161
162 public final H2MultiplexingRequesterBootstrap setUriPatternType(final UriPatternType uriPatternType) {
163 this.uriPatternType = uriPatternType;
164 return this;
165 }
166
167
168
169
170
171
172
173
174 public final H2MultiplexingRequesterBootstrap register(final String uriPattern, final Supplier<AsyncPushConsumer> supplier) {
175 Args.notBlank(uriPattern, "URI pattern");
176 Args.notNull(supplier, "Supplier");
177 pushConsumerList.add(new HandlerEntry<>(null, uriPattern, supplier));
178 return this;
179 }
180
181
182
183
184
185
186
187
188
189 public final H2MultiplexingRequesterBootstrap registerVirtual(final String hostname, final String uriPattern, final Supplier<AsyncPushConsumer> supplier) {
190 Args.notBlank(hostname, "Hostname");
191 Args.notBlank(uriPattern, "URI pattern");
192 Args.notNull(supplier, "Supplier");
193 pushConsumerList.add(new HandlerEntry<>(hostname, uriPattern, supplier));
194 return this;
195 }
196
197 public H2MultiplexingRequester create() {
198 final RequestHandlerRegistry<Supplier<AsyncPushConsumer>> registry = new RequestHandlerRegistry<>(uriPatternType);
199 for (final HandlerEntry<Supplier<AsyncPushConsumer>> entry: pushConsumerList) {
200 registry.register(entry.hostname, entry.uriPattern, entry.handler);
201 }
202 final ClientH2StreamMultiplexerFactory http2StreamHandlerFactory = new ClientH2StreamMultiplexerFactory(
203 httpProcessor != null ? httpProcessor : H2Processors.client(),
204 new DefaultAsyncPushConsumerFactory(registry),
205 h2Config != null ? h2Config : H2Config.DEFAULT,
206 charCodingConfig != null ? charCodingConfig : CharCodingConfig.DEFAULT,
207 streamListener);
208 return new H2MultiplexingRequester(
209 ioReactorConfig,
210 (ioSession, attachment) -> new ClientH2PrefaceHandler(ioSession, http2StreamHandlerFactory, strictALPNHandshake),
211 ioSessionDecorator,
212 exceptionCallback,
213 sessionListener,
214 DefaultAddressResolver.INSTANCE,
215 tlsStrategy != null ? tlsStrategy : new H2ClientTlsStrategy());
216 }
217
218 }