working on http router creation from settings
This commit is contained in:
parent
91fd31a85c
commit
d4a8beaf65
64 changed files with 401 additions and 132 deletions
|
@ -1,3 +1,3 @@
|
||||||
group = org.xbib
|
group = org.xbib
|
||||||
name = net-http
|
name = net-http
|
||||||
version = 4.9.0
|
version = 5.0.0
|
||||||
|
|
|
@ -21,7 +21,7 @@ tasks.withType(JavaCompile) {
|
||||||
options.fork = true
|
options.fork = true
|
||||||
options.forkOptions.jvmArgs += ['-Duser.language=en','-Duser.country=US']
|
options.forkOptions.jvmArgs += ['-Duser.language=en','-Duser.country=US']
|
||||||
options.encoding = 'UTF-8'
|
options.encoding = 'UTF-8'
|
||||||
options.compilerArgs.add('-Xlint:all')
|
options.compilerArgs.add('-Xlint:all,-exports')
|
||||||
options.compilerArgs.add("--module-path")
|
options.compilerArgs.add("--module-path")
|
||||||
options.compilerArgs.add(classpath.asPath)
|
options.compilerArgs.add(classpath.asPath)
|
||||||
classpath = files()
|
classpath = files()
|
||||||
|
|
|
@ -17,6 +17,9 @@ public class EventStreamTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(EventStreamTest.class.getName());
|
private static final Logger logger = Logger.getLogger(EventStreamTest.class.getName());
|
||||||
|
|
||||||
|
public EventStreamTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testSimpleJournalGateway() throws URISyntaxException, IOException, InterruptedException {
|
void testSimpleJournalGateway() throws URISyntaxException, IOException, InterruptedException {
|
||||||
var uri = new URI("http://localhost:19531/entries?follow");
|
var uri = new URI("http://localhost:19531/entries?follow");
|
||||||
|
|
|
@ -229,12 +229,16 @@ public class Https1ChannelInitializer implements HttpChannelInitializer {
|
||||||
throw new IllegalStateException();
|
throw new IllegalStateException();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
// TODO replace deprecation
|
||||||
Http2MultiplexCodecBuilder multiplexCodecBuilder = Http2MultiplexCodecBuilder.forClient(initializer)
|
Http2MultiplexCodecBuilder multiplexCodecBuilder = Http2MultiplexCodecBuilder.forClient(initializer)
|
||||||
.initialSettings(nettyHttpClientConfig.getHttp2Settings());
|
.initialSettings(nettyHttpClientConfig.getHttp2Settings());
|
||||||
if (nettyHttpClientConfig.isDebug()) {
|
if (nettyHttpClientConfig.isDebug()) {
|
||||||
multiplexCodecBuilder.frameLogger(new Http2FrameLogger(LogLevel.DEBUG, "client-frame"));
|
multiplexCodecBuilder.frameLogger(new Http2FrameLogger(LogLevel.DEBUG, "client-frame"));
|
||||||
}
|
}
|
||||||
Http2MultiplexCodec multiplexCodec = multiplexCodecBuilder.autoAckSettingsFrame(true).build();
|
// TODO replace deprecation
|
||||||
|
Http2MultiplexCodec multiplexCodec = multiplexCodecBuilder
|
||||||
|
.autoAckSettingsFrame(true)
|
||||||
|
.build();
|
||||||
pipeline.addLast("client-multiplex", multiplexCodec);
|
pipeline.addLast("client-multiplex", multiplexCodec);
|
||||||
pipeline.addLast("client-messages", new Http2Messages(interaction));
|
pipeline.addLast("client-messages", new Http2Messages(interaction));
|
||||||
// simulate we are ready for HTTP/2
|
// simulate we are ready for HTTP/2
|
||||||
|
|
|
@ -170,11 +170,13 @@ public class Https2ChannelInitializer implements HttpChannelInitializer {
|
||||||
throw new IllegalStateException();
|
throw new IllegalStateException();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
// TODO replace deprecation
|
||||||
Http2MultiplexCodecBuilder multiplexCodecBuilder = Http2MultiplexCodecBuilder.forClient(initializer)
|
Http2MultiplexCodecBuilder multiplexCodecBuilder = Http2MultiplexCodecBuilder.forClient(initializer)
|
||||||
.initialSettings(nettyHttpClientConfig.getHttp2Settings());
|
.initialSettings(nettyHttpClientConfig.getHttp2Settings());
|
||||||
if (nettyHttpClientConfig.isDebug()) {
|
if (nettyHttpClientConfig.isDebug()) {
|
||||||
multiplexCodecBuilder.frameLogger(new Http2FrameLogger(LogLevel.DEBUG, "client-frame"));
|
multiplexCodecBuilder.frameLogger(new Http2FrameLogger(LogLevel.DEBUG, "client-frame"));
|
||||||
}
|
}
|
||||||
|
// TODO replace deprecation
|
||||||
Http2MultiplexCodec multiplexCodec = multiplexCodecBuilder
|
Http2MultiplexCodec multiplexCodec = multiplexCodecBuilder
|
||||||
.autoAckSettingsFrame(true)
|
.autoAckSettingsFrame(true)
|
||||||
.autoAckPingFrame(true)
|
.autoAckPingFrame(true)
|
||||||
|
|
|
@ -15,6 +15,9 @@ public class AkamaiTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(AkamaiTest.class.getName());
|
private static final Logger logger = Logger.getLogger(AkamaiTest.class.getName());
|
||||||
|
|
||||||
|
public AkamaiTest() {
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Problems with akamai:
|
* Problems with akamai:
|
||||||
* failing: Cannot invoke "io.netty.handler.codec.http2.AbstractHttp2StreamChannel.fireChildRead(io.netty.handler.codec.http2.Http2Frame)" because "channel" is null * demo/h2_demo_frame.html sends no content, only a push promise, and does not continue
|
* failing: Cannot invoke "io.netty.handler.codec.http2.AbstractHttp2StreamChannel.fireChildRead(io.netty.handler.codec.http2.Http2Frame)" because "channel" is null * demo/h2_demo_frame.html sends no content, only a push promise, and does not continue
|
||||||
|
|
|
@ -17,12 +17,17 @@ class ThreadLeakTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(ThreadLeakTest.class.getName());
|
private static final Logger logger = Logger.getLogger(ThreadLeakTest.class.getName());
|
||||||
|
|
||||||
|
public ThreadLeakTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testForLeaks() throws IOException {
|
void testForLeaks() throws IOException {
|
||||||
NettyHttpClientConfig config = new NettyHttpsClientConfig();
|
NettyHttpClientConfig config = new NettyHttpsClientConfig();
|
||||||
try (NettyHttpClient client = NettyHttpClient.builder()
|
try (NettyHttpClient client = NettyHttpClient.builder()
|
||||||
.setConfig(config)
|
.setConfig(config)
|
||||||
.build()) {
|
.build()) {
|
||||||
|
// do something with the client
|
||||||
|
client.getClientConfig();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -66,11 +66,13 @@ public class Http2ChannelInitializer implements HttpChannelInitializer {
|
||||||
throw new IllegalStateException();
|
throw new IllegalStateException();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
// TODO replace deprecation
|
||||||
Http2MultiplexCodecBuilder multiplexCodecBuilder = Http2MultiplexCodecBuilder.forClient(initializer)
|
Http2MultiplexCodecBuilder multiplexCodecBuilder = Http2MultiplexCodecBuilder.forClient(initializer)
|
||||||
.initialSettings(nettyHttpClientConfig.getHttp2Settings());
|
.initialSettings(nettyHttpClientConfig.getHttp2Settings());
|
||||||
if (nettyHttpClientConfig.isDebug()) {
|
if (nettyHttpClientConfig.isDebug()) {
|
||||||
multiplexCodecBuilder.frameLogger(new Http2FrameLogger(LogLevel.DEBUG, "client-frame"));
|
multiplexCodecBuilder.frameLogger(new Http2FrameLogger(LogLevel.DEBUG, "client-frame"));
|
||||||
}
|
}
|
||||||
|
// TODO replace deprecation
|
||||||
Http2MultiplexCodec multiplexCodec = multiplexCodecBuilder
|
Http2MultiplexCodec multiplexCodec = multiplexCodecBuilder
|
||||||
.autoAckPingFrame(true)
|
.autoAckPingFrame(true)
|
||||||
.autoAckSettingsFrame(true)
|
.autoAckSettingsFrame(true)
|
||||||
|
|
|
@ -278,7 +278,7 @@ public class ExponentialBackOff implements BackOff {
|
||||||
if (currentIntervalMillis >= maxIntervalMillis / multiplier) {
|
if (currentIntervalMillis >= maxIntervalMillis / multiplier) {
|
||||||
currentIntervalMillis = maxIntervalMillis;
|
currentIntervalMillis = maxIntervalMillis;
|
||||||
} else {
|
} else {
|
||||||
currentIntervalMillis *= multiplier;
|
currentIntervalMillis = (int)(currentIntervalMillis * multiplier);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -14,6 +14,9 @@ import static org.xbib.j2html.TagCreator.html;
|
||||||
|
|
||||||
public class BadRequestHandler extends J2HtmlResourceHandler {
|
public class BadRequestHandler extends J2HtmlResourceHandler {
|
||||||
|
|
||||||
|
public BadRequestHandler() {
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Resource createResource(HttpRouterContext httpRouterContext)
|
protected Resource createResource(HttpRouterContext httpRouterContext)
|
||||||
throws IOException, ParameterException {
|
throws IOException, ParameterException {
|
||||||
|
|
|
@ -19,6 +19,9 @@ import static org.xbib.j2html.TagCreator.pre;
|
||||||
|
|
||||||
public class InternalServerErrorHandler extends J2HtmlResourceHandler {
|
public class InternalServerErrorHandler extends J2HtmlResourceHandler {
|
||||||
|
|
||||||
|
public InternalServerErrorHandler() {
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Resource createResource(HttpRouterContext httpRouterContext)
|
protected Resource createResource(HttpRouterContext httpRouterContext)
|
||||||
throws IOException, ParameterException {
|
throws IOException, ParameterException {
|
||||||
|
|
|
@ -14,6 +14,9 @@ import static org.xbib.j2html.TagCreator.html;
|
||||||
|
|
||||||
public class NotFoundHandler extends J2HtmlResourceHandler {
|
public class NotFoundHandler extends J2HtmlResourceHandler {
|
||||||
|
|
||||||
|
public NotFoundHandler() {
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Resource createResource(HttpRouterContext httpRouterContext)
|
protected Resource createResource(HttpRouterContext httpRouterContext)
|
||||||
throws IOException, ParameterException {
|
throws IOException, ParameterException {
|
||||||
|
|
|
@ -14,6 +14,9 @@ import static org.xbib.j2html.TagCreator.html;
|
||||||
|
|
||||||
public class UnauthorizedHandler extends J2HtmlResourceHandler {
|
public class UnauthorizedHandler extends J2HtmlResourceHandler {
|
||||||
|
|
||||||
|
public UnauthorizedHandler() {
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Resource createResource(HttpRouterContext httpRouterContext)
|
protected Resource createResource(HttpRouterContext httpRouterContext)
|
||||||
throws IOException, ParameterException {
|
throws IOException, ParameterException {
|
||||||
|
|
|
@ -13,6 +13,9 @@ public class Http1Test {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(Http1Test.class.getName());
|
private static final Logger logger = Logger.getLogger(Http1Test.class.getName());
|
||||||
|
|
||||||
|
public Http1Test() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testGoogleConscrypt() throws Exception {
|
void testGoogleConscrypt() throws Exception {
|
||||||
|
|
||||||
|
|
|
@ -27,7 +27,7 @@ public class WebApplication extends BaseApplication {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected Codec<Session> newSessionCodec(HttpRouterContext httpRouterContext) {
|
protected Codec<Session> newSessionCodec(HttpRouterContext httpRouterContext) {
|
||||||
return new FileJsonSessionCodec(sessionName, this, 1024, Duration.ofDays(1),
|
return new FileJsonSessionCodec(getSessionName(), this, 1024, Duration.ofDays(1),
|
||||||
Paths.get("/var/tmp/session"));
|
Paths.get("/var/tmp/session"));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -8,10 +8,10 @@ import org.xbib.settings.Settings;
|
||||||
|
|
||||||
public class WebApplicationBuilder extends BaseApplicationBuilder {
|
public class WebApplicationBuilder extends BaseApplicationBuilder {
|
||||||
|
|
||||||
protected String profile;
|
|
||||||
|
|
||||||
protected String name;
|
protected String name;
|
||||||
|
|
||||||
|
protected String profile;
|
||||||
|
|
||||||
protected WebApplicationBuilder() {
|
protected WebApplicationBuilder() {
|
||||||
super();
|
super();
|
||||||
this.name = System.getProperty("application.name");
|
this.name = System.getProperty("application.name");
|
||||||
|
@ -28,11 +28,11 @@ public class WebApplicationBuilder extends BaseApplicationBuilder {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
/*@Override
|
||||||
public WebApplicationBuilder setSettings(Settings settings) {
|
public WebApplicationBuilder setSettings(Settings settings) {
|
||||||
this.settings = settings;
|
this.settings = settings;
|
||||||
return this;
|
return this;
|
||||||
}
|
}*/
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public WebApplicationBuilder setSecret(String secret) {
|
public WebApplicationBuilder setSecret(String secret) {
|
||||||
|
|
|
@ -174,7 +174,7 @@ public final class Bootstrap {
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
WebApplication application = WebApplication.builder()
|
WebApplication application = WebApplication.builder()
|
||||||
.setSettings(settings)
|
//.setSettings(settings)
|
||||||
.setSecret("1088e6b7ad58d64d09961e1357bf95544447051c6ad1332cd626e3a33bb5786b")
|
.setSecret("1088e6b7ad58d64d09961e1357bf95544447051c6ad1332cd626e3a33bb5786b")
|
||||||
.setExecutor(executor)
|
.setExecutor(executor)
|
||||||
.setRouter(httpRouter)
|
.setRouter(httpRouter)
|
||||||
|
|
|
@ -46,8 +46,6 @@ import java.nio.charset.StandardCharsets;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.Optional;
|
|
||||||
import java.util.ServiceLoader;
|
|
||||||
|
|
||||||
import static org.xbib.j2html.TagCreator.body;
|
import static org.xbib.j2html.TagCreator.body;
|
||||||
import static org.xbib.j2html.TagCreator.h1;
|
import static org.xbib.j2html.TagCreator.h1;
|
||||||
|
@ -57,7 +55,7 @@ public final class Bootstrap {
|
||||||
private Bootstrap() {
|
private Bootstrap() {
|
||||||
}
|
}
|
||||||
|
|
||||||
public static void main(String[] args) throws Exception {
|
public static void main(String[] args) {
|
||||||
String profile = args.length > 0 ? args[0] : System.getProperty("application.profile");
|
String profile = args.length > 0 ? args[0] : System.getProperty("application.profile");
|
||||||
ConfigParams configParams;
|
ConfigParams configParams;
|
||||||
ConfigLoader configLoader;
|
ConfigLoader configLoader;
|
||||||
|
@ -181,7 +179,7 @@ public final class Bootstrap {
|
||||||
.build();
|
.build();
|
||||||
|
|
||||||
WebApplication application = WebApplication.builder()
|
WebApplication application = WebApplication.builder()
|
||||||
.setSettings(settings)
|
//.setSettings(settings)
|
||||||
.setSecret("1088e6b7ad58d64d09961e1357bf95544447051c6ad1332cd626e3a33bb5786b")
|
.setSecret("1088e6b7ad58d64d09961e1357bf95544447051c6ad1332cd626e3a33bb5786b")
|
||||||
.setExecutor(executor)
|
.setExecutor(executor)
|
||||||
.setRouter(httpRouter)
|
.setRouter(httpRouter)
|
||||||
|
|
|
@ -55,7 +55,7 @@ public class Https2Handler extends ChannelDuplexHandler {
|
||||||
.setRemoteAddress((InetSocketAddress) ctx.channel().remoteAddress())
|
.setRemoteAddress((InetSocketAddress) ctx.channel().remoteAddress())
|
||||||
.setStreamId(streamId);
|
.setStreamId(streamId);
|
||||||
if ("PRI".equals(fullHttpRequest.method().name())) {
|
if ("PRI".equals(fullHttpRequest.method().name())) {
|
||||||
nettyHttpServer.dispatch(httpsRequestBuilder, httpsResponseBuilder, HttpResponseStatus.HTTP_VERSION_NOT_SUPPORTED);
|
nettyHttpServer.dispatchError(httpsRequestBuilder, httpsResponseBuilder, HttpResponseStatus.HTTP_VERSION_NOT_SUPPORTED);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
httpsResponseBuilder.shouldClose("close".equalsIgnoreCase(fullHttpRequest.headers().get(HttpHeaderNames.CONNECTION)));
|
httpsResponseBuilder.shouldClose("close".equalsIgnoreCase(fullHttpRequest.headers().get(HttpHeaderNames.CONNECTION)));
|
||||||
|
|
|
@ -34,6 +34,9 @@ public class NettyHttps2ServerMultiRequestLoadTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttps2ServerMultiRequestLoadTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttps2ServerMultiRequestLoadTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttps2ServerMultiRequestLoadTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttps2Load() throws Exception {
|
public void testHttps2Load() throws Exception {
|
||||||
// client HTTP 2.0, server HTTP 2.0
|
// client HTTP 2.0, server HTTP 2.0
|
||||||
|
|
|
@ -34,6 +34,9 @@ public class NettyHttps2ServerTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttps2ServerTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttps2ServerTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttps2ServerTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttps2() throws Exception {
|
public void testHttps2() throws Exception {
|
||||||
// client HTTP 2.0 + server HTTP 2.0 (no upgrade)
|
// client HTTP 2.0 + server HTTP 2.0 (no upgrade)
|
||||||
|
|
|
@ -36,6 +36,9 @@ public class NettyHttpsServerMultiRequestLoadTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpsServerMultiRequestLoadTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpsServerMultiRequestLoadTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpsServerMultiRequestLoadTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttps1Load() throws Exception {
|
public void testHttps1Load() throws Exception {
|
||||||
// client HTTP 1.1, server HTTP 1.1 (no upgrade)
|
// client HTTP 1.1, server HTTP 1.1 (no upgrade)
|
||||||
|
|
|
@ -39,6 +39,9 @@ public class NettyHttpsServerTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpsServerTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpsServerTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpsServerTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttps1() throws Exception {
|
public void testHttps1() throws Exception {
|
||||||
// client HTTP 1.1 + server HTTP 1.1 (no upgrade)
|
// client HTTP 1.1 + server HTTP 1.1 (no upgrade)
|
||||||
|
|
|
@ -189,7 +189,7 @@ public class NettyHttpServer implements HttpServer {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void dispatch(HttpRequestBuilder requestBuilder,
|
public void dispatchError(HttpRequestBuilder requestBuilder,
|
||||||
HttpResponseBuilder responseBuilder,
|
HttpResponseBuilder responseBuilder,
|
||||||
HttpResponseStatus responseStatus) {
|
HttpResponseStatus responseStatus) {
|
||||||
Callable<?> callable = (Callable<Object>) () -> {
|
Callable<?> callable = (Callable<Object>) () -> {
|
||||||
|
|
|
@ -17,6 +17,9 @@ import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
|
|
||||||
public class HttpRequestTest {
|
public class HttpRequestTest {
|
||||||
|
|
||||||
|
public HttpRequestTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testFormAsMultiMap() {
|
public void testFormAsMultiMap() {
|
||||||
Parameter parameter = Parameter.builder().domain(Parameter.Domain.FORM)
|
Parameter parameter = Parameter.builder().domain(Parameter.Domain.FORM)
|
||||||
|
|
|
@ -32,6 +32,9 @@ public class NettyHttp2ServerMultiRequestLoadTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttp2ServerMultiRequestLoadTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttp2ServerMultiRequestLoadTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttp2ServerMultiRequestLoadTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttp2Multi() throws Exception {
|
public void testHttp2Multi() throws Exception {
|
||||||
|
|
||||||
|
|
|
@ -31,6 +31,9 @@ public class NettyHttp2ServerTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttp2ServerTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttp2ServerTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttp2ServerTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttp2() throws Exception {
|
public void testHttp2() throws Exception {
|
||||||
// note that h2c in cleartext is very uncommon, browser do not support this.
|
// note that h2c in cleartext is very uncommon, browser do not support this.
|
||||||
|
|
|
@ -30,6 +30,9 @@ public class NettyHttpServerBodyTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpServerBodyTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpServerBodyTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpServerBodyTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttp() throws Exception {
|
public void testHttp() throws Exception {
|
||||||
URL url = URL.from("http://localhost:8008/domain/");
|
URL url = URL.from("http://localhost:8008/domain/");
|
||||||
|
|
|
@ -36,6 +36,9 @@ public class NettyHttpServerFailureTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpServerTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpServerTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpServerFailureTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testBadRequest() throws Exception {
|
public void testBadRequest() throws Exception {
|
||||||
URL url = URL.from("http://localhost:8008/domain/");
|
URL url = URL.from("http://localhost:8008/domain/");
|
||||||
|
|
|
@ -39,6 +39,9 @@ public class NettyHttpServerFileUploadTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpServerFileUploadTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpServerFileUploadTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpServerFileUploadTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testSimpleFileUpload() throws Exception {
|
public void testSimpleFileUpload() throws Exception {
|
||||||
URL url = URL.from("http://localhost:8008/");
|
URL url = URL.from("http://localhost:8008/");
|
||||||
|
|
|
@ -32,6 +32,9 @@ public class NettyHttpServerMultiRequestLoadTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpServerMultiRequestLoadTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpServerMultiRequestLoadTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpServerMultiRequestLoadTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttp1Multi() throws Exception {
|
public void testHttp1Multi() throws Exception {
|
||||||
|
|
||||||
|
|
|
@ -35,6 +35,9 @@ public class NettyHttpServerRequestTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpServerRequestTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpServerRequestTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpServerRequestTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttpRequest() throws Exception {
|
public void testHttpRequest() throws Exception {
|
||||||
URL url = URL.from("http://localhost:8008/test/");
|
URL url = URL.from("http://localhost:8008/test/");
|
||||||
|
|
|
@ -35,6 +35,9 @@ public class NettyHttpServerTest {
|
||||||
|
|
||||||
private static final Logger logger = Logger.getLogger(NettyHttpServerTest.class.getName());
|
private static final Logger logger = Logger.getLogger(NettyHttpServerTest.class.getName());
|
||||||
|
|
||||||
|
public NettyHttpServerTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testHttp() throws Exception {
|
public void testHttp() throws Exception {
|
||||||
URL url = URL.from("http://localhost:8008/domain/");
|
URL url = URL.from("http://localhost:8008/domain/");
|
||||||
|
|
|
@ -144,7 +144,7 @@ public class NioHttpServer implements HttpServer {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void dispatch(org.xbib.net.http.server.HttpRequestBuilder requestBuilder,
|
public void dispatchError(org.xbib.net.http.server.HttpRequestBuilder requestBuilder,
|
||||||
org.xbib.net.http.server.HttpResponseBuilder responseBuilder,
|
org.xbib.net.http.server.HttpResponseBuilder responseBuilder,
|
||||||
HttpResponseStatus responseStatus) {
|
HttpResponseStatus responseStatus) {
|
||||||
HttpRouterContext httpRouterContext = builder.application.createContext(null, requestBuilder, responseBuilder);
|
HttpRouterContext httpRouterContext = builder.application.createContext(null, requestBuilder, responseBuilder);
|
||||||
|
|
|
@ -8,6 +8,10 @@ import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
import static org.junit.jupiter.api.Assertions.assertThrows;
|
import static org.junit.jupiter.api.Assertions.assertThrows;
|
||||||
|
|
||||||
public class ByteArrayTest {
|
public class ByteArrayTest {
|
||||||
|
|
||||||
|
public ByteArrayTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void should_return_inserted_data_when_insert_some_bytes_and_call_getCopyArray_given_a_ByteArray() {
|
public void should_return_inserted_data_when_insert_some_bytes_and_call_getCopyArray_given_a_ByteArray() {
|
||||||
ByteArray byteArray = new ByteArray();
|
ByteArray byteArray = new ByteArray();
|
||||||
|
|
|
@ -17,6 +17,9 @@ import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||||
|
|
||||||
public class HttpRequestParserTest {
|
public class HttpRequestParserTest {
|
||||||
|
|
||||||
|
public HttpRequestParserTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void should_parse_get_request_success() {
|
public void should_parse_get_request_success() {
|
||||||
HttpRequestParser parser = new HttpRequestParser();
|
HttpRequestParser parser = new HttpRequestParser();
|
||||||
|
|
|
@ -22,6 +22,9 @@ import java.nio.charset.StandardCharsets;
|
||||||
|
|
||||||
public class NioHttpServerTest {
|
public class NioHttpServerTest {
|
||||||
|
|
||||||
|
public NioHttpServerTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Disabled
|
@Disabled
|
||||||
@Test
|
@Test
|
||||||
public void nioServerTest() throws Exception {
|
public void nioServerTest() throws Exception {
|
||||||
|
|
|
@ -146,7 +146,7 @@ public class SimpleHttpServer implements HttpServer {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void dispatch(org.xbib.net.http.server.HttpRequestBuilder requestBuilder,
|
public void dispatchError(org.xbib.net.http.server.HttpRequestBuilder requestBuilder,
|
||||||
org.xbib.net.http.server.HttpResponseBuilder responseBuilder,
|
org.xbib.net.http.server.HttpResponseBuilder responseBuilder,
|
||||||
HttpResponseStatus responseStatus) {
|
HttpResponseStatus responseStatus) {
|
||||||
HttpRouterContext httpRouterContext = builder.application.createContext(null, requestBuilder, responseBuilder);
|
HttpRouterContext httpRouterContext = builder.application.createContext(null, requestBuilder, responseBuilder);
|
||||||
|
|
|
@ -27,6 +27,9 @@ import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||||
|
|
||||||
public class HttpRouterTest {
|
public class HttpRouterTest {
|
||||||
|
|
||||||
|
public HttpRouterTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void routerTest() throws Exception {
|
public void routerTest() throws Exception {
|
||||||
URL url = URL.http().host("localhost").port(8008).build();
|
URL url = URL.http().host("localhost").port(8008).build();
|
||||||
|
|
|
@ -22,6 +22,9 @@ import java.nio.charset.StandardCharsets;
|
||||||
|
|
||||||
public class SimpleHttpServerTest {
|
public class SimpleHttpServerTest {
|
||||||
|
|
||||||
|
public SimpleHttpServerTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Disabled
|
@Disabled
|
||||||
@Test
|
@Test
|
||||||
public void simpleServerTest() throws Exception {
|
public void simpleServerTest() throws Exception {
|
||||||
|
|
|
@ -92,6 +92,7 @@ public abstract class BaseHttpResponseBuilder implements HttpResponseBuilder {
|
||||||
*/
|
*/
|
||||||
protected Attributes attributes;
|
protected Attributes attributes;
|
||||||
|
|
||||||
|
@SuppressWarnings("this-escape")
|
||||||
protected BaseHttpResponseBuilder() {
|
protected BaseHttpResponseBuilder() {
|
||||||
reset();
|
reset();
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,13 +13,12 @@ public interface HttpServer extends Closeable {
|
||||||
|
|
||||||
void loop() throws IOException;
|
void loop() throws IOException;
|
||||||
|
|
||||||
|
Collection<HttpDomain> getDomains();
|
||||||
|
|
||||||
void dispatch(HttpRequestBuilder requestBuilder,
|
void dispatch(HttpRequestBuilder requestBuilder,
|
||||||
HttpResponseBuilder responseBuilder);
|
HttpResponseBuilder responseBuilder);
|
||||||
|
|
||||||
void dispatch(HttpRequestBuilder requestBuilder,
|
void dispatchError(HttpRequestBuilder requestBuilder,
|
||||||
HttpResponseBuilder responseBuilder,
|
HttpResponseBuilder responseBuilder,
|
||||||
HttpResponseStatus responseStatus);
|
HttpResponseStatus responseStatus);
|
||||||
|
|
||||||
Collection<HttpDomain> getDomains();
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,7 +18,6 @@ import org.xbib.net.http.server.executor.Executor;
|
||||||
import org.xbib.net.http.server.route.HttpRouter;
|
import org.xbib.net.http.server.route.HttpRouter;
|
||||||
import org.xbib.net.http.server.session.SessionListener;
|
import org.xbib.net.http.server.session.SessionListener;
|
||||||
import org.xbib.net.mime.MimeTypeService;
|
import org.xbib.net.mime.MimeTypeService;
|
||||||
import org.xbib.settings.Settings;
|
|
||||||
|
|
||||||
public interface Application extends SessionListener, Resolver<Path>, Closeable {
|
public interface Application extends SessionListener, Resolver<Path>, Closeable {
|
||||||
|
|
||||||
|
@ -28,10 +27,14 @@ public interface Application extends SessionListener, Resolver<Path>, Closeable
|
||||||
|
|
||||||
Path getHome();
|
Path getHome();
|
||||||
|
|
||||||
|
String getPrefix();
|
||||||
|
|
||||||
Collection<HttpDomain> getDomains();
|
Collection<HttpDomain> getDomains();
|
||||||
|
|
||||||
Set<HttpAddress> getAddresses();
|
Set<HttpAddress> getAddresses();
|
||||||
|
|
||||||
|
boolean shouldNegotiateLocale();
|
||||||
|
|
||||||
Locale getLocale();
|
Locale getLocale();
|
||||||
|
|
||||||
ZoneId getZoneId();
|
ZoneId getZoneId();
|
||||||
|
@ -40,8 +43,6 @@ public interface Application extends SessionListener, Resolver<Path>, Closeable
|
||||||
|
|
||||||
String getContextPath();
|
String getContextPath();
|
||||||
|
|
||||||
Settings getSettings();
|
|
||||||
|
|
||||||
void addModule(ApplicationModule applicationModule);
|
void addModule(ApplicationModule applicationModule);
|
||||||
|
|
||||||
Collection<ApplicationModule> getModules();
|
Collection<ApplicationModule> getModules();
|
||||||
|
|
|
@ -13,6 +13,8 @@ public interface ApplicationBuilder {
|
||||||
|
|
||||||
ApplicationBuilder setHome(Path home);
|
ApplicationBuilder setHome(Path home);
|
||||||
|
|
||||||
|
ApplicationBuilder setPrefix(String prefix);
|
||||||
|
|
||||||
ApplicationBuilder setContextPath(String contextPath);
|
ApplicationBuilder setContextPath(String contextPath);
|
||||||
|
|
||||||
ApplicationBuilder setSecret(String hexSecret);
|
ApplicationBuilder setSecret(String hexSecret);
|
||||||
|
@ -21,6 +23,8 @@ public interface ApplicationBuilder {
|
||||||
|
|
||||||
ApplicationBuilder setSessionsEnabled(boolean sessionsEnabled);
|
ApplicationBuilder setSessionsEnabled(boolean sessionsEnabled);
|
||||||
|
|
||||||
|
ApplicationBuilder shouldNegotiateLocale(boolean shouldNegotiate);
|
||||||
|
|
||||||
ApplicationBuilder setLocale(Locale locale);
|
ApplicationBuilder setLocale(Locale locale);
|
||||||
|
|
||||||
ApplicationBuilder setZoneId(ZoneId zoneId);
|
ApplicationBuilder setZoneId(ZoneId zoneId);
|
||||||
|
|
|
@ -9,7 +9,6 @@ import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
import java.util.Map;
|
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
|
@ -41,7 +40,6 @@ import org.xbib.net.http.server.auth.MemoryPropertiesUserProfileCodec;
|
||||||
import org.xbib.net.http.server.validate.HttpRequestValidator;
|
import org.xbib.net.http.server.validate.HttpRequestValidator;
|
||||||
import org.xbib.net.mime.MimeTypeService;
|
import org.xbib.net.mime.MimeTypeService;
|
||||||
import org.xbib.net.util.RandomUtil;
|
import org.xbib.net.util.RandomUtil;
|
||||||
import org.xbib.settings.Settings;
|
|
||||||
|
|
||||||
public class BaseApplication implements Application {
|
public class BaseApplication implements Application {
|
||||||
|
|
||||||
|
@ -49,8 +47,6 @@ public class BaseApplication implements Application {
|
||||||
|
|
||||||
protected BaseApplicationBuilder builder;
|
protected BaseApplicationBuilder builder;
|
||||||
|
|
||||||
protected final String sessionName;
|
|
||||||
|
|
||||||
private final HttpResponseRenderer httpResponseRenderer;
|
private final HttpResponseRenderer httpResponseRenderer;
|
||||||
|
|
||||||
private final Attributes attributes;
|
private final Attributes attributes;
|
||||||
|
@ -61,30 +57,9 @@ public class BaseApplication implements Application {
|
||||||
|
|
||||||
protected BaseApplication(BaseApplicationBuilder builder) {
|
protected BaseApplication(BaseApplicationBuilder builder) {
|
||||||
this.builder = builder;
|
this.builder = builder;
|
||||||
this.sessionName = builder.settings.get("session.name", "SESS");
|
|
||||||
this.httpResponseRenderer = newResponseRenderer();
|
|
||||||
this.attributes = newAttributes();
|
this.attributes = newAttributes();
|
||||||
this.applicationModuleList = new ArrayList<>();
|
this.applicationModuleList = new ArrayList<>();
|
||||||
for (Map.Entry<String, Settings> entry : builder.settings.getGroups("module").entrySet()) {
|
this.httpResponseRenderer = newResponseRenderer();
|
||||||
String moduleName = entry.getKey();
|
|
||||||
Settings moduleSettings = entry.getValue();
|
|
||||||
if (moduleSettings.getAsBoolean("enabled", true)) {
|
|
||||||
try {
|
|
||||||
String className = moduleSettings.get("class");
|
|
||||||
@SuppressWarnings("unchecked")
|
|
||||||
Class<ApplicationModule> clazz =
|
|
||||||
(Class<ApplicationModule>) Class.forName(className, true, builder.classLoader);
|
|
||||||
ApplicationModule applicationModule = clazz.getConstructor(Application.class, String.class, Settings.class)
|
|
||||||
.newInstance(this, moduleName, moduleSettings);
|
|
||||||
applicationModuleList.add(applicationModule);
|
|
||||||
} catch (Exception e) {
|
|
||||||
logger.log(Level.WARNING, e.getMessage(), e);
|
|
||||||
throw new IllegalArgumentException("class not found or not loadable: " + e.getMessage());
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
logger.log(Level.WARNING, "disabled module: " + moduleName);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public static BaseApplicationBuilder builder() {
|
public static BaseApplicationBuilder builder() {
|
||||||
|
@ -111,6 +86,16 @@ public class BaseApplication implements Application {
|
||||||
return builder.home;
|
return builder.home;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getPrefix() {
|
||||||
|
return builder.prefix;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean shouldNegotiateLocale() {
|
||||||
|
return builder.shouldNegotiateLocale;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Locale getLocale() {
|
public Locale getLocale() {
|
||||||
return builder.locale;
|
return builder.locale;
|
||||||
|
@ -131,19 +116,6 @@ public class BaseApplication implements Application {
|
||||||
return builder.contextPath;
|
return builder.contextPath;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public Settings getSettings() {
|
|
||||||
return builder.settings;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getSecret() {
|
|
||||||
return builder.secret;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Set<String> getStaticFileSuffixes() {
|
|
||||||
return builder.staticFileSuffixes;
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Collection<ApplicationModule> getModules() {
|
public Collection<ApplicationModule> getModules() {
|
||||||
return applicationModuleList;
|
return applicationModuleList;
|
||||||
|
@ -195,6 +167,18 @@ public class BaseApplication implements Application {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public String getSessionName() {
|
||||||
|
return "SESS_" + getProfile().toLowerCase(Locale.ROOT);
|
||||||
|
}
|
||||||
|
|
||||||
|
public String getSecret() {
|
||||||
|
return builder.secret;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Set<String> getStaticFileSuffixes() {
|
||||||
|
return builder.staticFileSuffixes;
|
||||||
|
}
|
||||||
|
|
||||||
protected HttpRequestValidator newRequestValidator() {
|
protected HttpRequestValidator newRequestValidator() {
|
||||||
return new HttpRequestValidator();
|
return new HttpRequestValidator();
|
||||||
}
|
}
|
||||||
|
@ -216,7 +200,7 @@ public class BaseApplication implements Application {
|
||||||
}
|
}
|
||||||
|
|
||||||
protected Codec<Session> newSessionCodec(HttpRouterContext httpRouterContext) {
|
protected Codec<Session> newSessionCodec(HttpRouterContext httpRouterContext) {
|
||||||
return new MemoryPropertiesSessionCodec(sessionName,this, 1024, Duration.ofDays(1));
|
return new MemoryPropertiesSessionCodec(getSessionName(),this, 1024, Duration.ofDays(1));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected Codec<UserProfile> newUserProfileCodec(HttpRouterContext httpRouterContext) {
|
protected Codec<UserProfile> newUserProfileCodec(HttpRouterContext httpRouterContext) {
|
||||||
|
@ -227,7 +211,7 @@ public class BaseApplication implements Application {
|
||||||
return new IncomingContextHandler(userProfileCodec,
|
return new IncomingContextHandler(userProfileCodec,
|
||||||
getSecret(),
|
getSecret(),
|
||||||
"HmacSHA1",
|
"HmacSHA1",
|
||||||
sessionName,
|
getSessionName(),
|
||||||
sessionCodec,
|
sessionCodec,
|
||||||
getStaticFileSuffixes(),
|
getStaticFileSuffixes(),
|
||||||
() -> RandomUtil.randomString(16));
|
() -> RandomUtil.randomString(16));
|
||||||
|
@ -237,7 +221,7 @@ public class BaseApplication implements Application {
|
||||||
return new OutgoingContextHandler(
|
return new OutgoingContextHandler(
|
||||||
getSecret(),
|
getSecret(),
|
||||||
"HmacSHA1",
|
"HmacSHA1",
|
||||||
sessionName,
|
getSessionName(),
|
||||||
getStaticFileSuffixes(),
|
getStaticFileSuffixes(),
|
||||||
Duration.ofDays(1),
|
Duration.ofDays(1),
|
||||||
true,
|
true,
|
||||||
|
@ -254,13 +238,13 @@ public class BaseApplication implements Application {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onCreated(Session session) {
|
public void onCreated(Session session) {
|
||||||
logger.log(Level.FINER, "session name = " + sessionName + " created = " + session);
|
logger.log(Level.FINER, "session created = " + session);
|
||||||
applicationModuleList.forEach(module -> module.onOpen(session));
|
applicationModuleList.forEach(module -> module.onOpen(session));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onDestroy(Session session) {
|
public void onDestroy(Session session) {
|
||||||
logger.log(Level.FINER, "session name = " + sessionName + " destroyed = " + session);
|
logger.log(Level.FINER, "session destroyed = " + session);
|
||||||
if (throwable != null) {
|
if (throwable != null) {
|
||||||
applicationModuleList.forEach(module -> module.onFail(session, throwable));
|
applicationModuleList.forEach(module -> module.onFail(session, throwable));
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -12,7 +12,6 @@ import org.xbib.net.http.server.executor.BaseExecutor;
|
||||||
import org.xbib.net.http.server.executor.Executor;
|
import org.xbib.net.http.server.executor.Executor;
|
||||||
import org.xbib.net.http.server.route.HttpRouter;
|
import org.xbib.net.http.server.route.HttpRouter;
|
||||||
import org.xbib.net.mime.MimeTypeService;
|
import org.xbib.net.mime.MimeTypeService;
|
||||||
import org.xbib.settings.Settings;
|
|
||||||
|
|
||||||
public class BaseApplicationBuilder implements ApplicationBuilder {
|
public class BaseApplicationBuilder implements ApplicationBuilder {
|
||||||
|
|
||||||
|
@ -25,9 +24,9 @@ public class BaseApplicationBuilder implements ApplicationBuilder {
|
||||||
|
|
||||||
protected Path home;
|
protected Path home;
|
||||||
|
|
||||||
protected ClassLoader classLoader;
|
protected String prefix;
|
||||||
|
|
||||||
protected Settings settings;
|
protected ClassLoader classLoader;
|
||||||
|
|
||||||
protected String contextPath;
|
protected String contextPath;
|
||||||
|
|
||||||
|
@ -37,6 +36,8 @@ public class BaseApplicationBuilder implements ApplicationBuilder {
|
||||||
|
|
||||||
protected boolean sessionsEnabled;
|
protected boolean sessionsEnabled;
|
||||||
|
|
||||||
|
protected boolean shouldNegotiateLocale;
|
||||||
|
|
||||||
protected Locale locale;
|
protected Locale locale;
|
||||||
|
|
||||||
protected ZoneId zoneId;
|
protected ZoneId zoneId;
|
||||||
|
@ -62,14 +63,16 @@ public class BaseApplicationBuilder implements ApplicationBuilder {
|
||||||
this.profile = profile;
|
this.profile = profile;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public BaseApplicationBuilder setHome(Path home) {
|
public BaseApplicationBuilder setHome(Path home) {
|
||||||
this.home = home;
|
this.home = home;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public BaseApplicationBuilder setSettings(Settings settings) {
|
@Override
|
||||||
this.settings = settings;
|
public BaseApplicationBuilder setPrefix(String prefix) {
|
||||||
|
this.prefix = prefix;
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -102,6 +105,12 @@ public class BaseApplicationBuilder implements ApplicationBuilder {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public ApplicationBuilder shouldNegotiateLocale(boolean shouldNegotiateLocale) {
|
||||||
|
this.shouldNegotiateLocale = shouldNegotiateLocale;
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public ApplicationBuilder setLocale(Locale locale) {
|
public ApplicationBuilder setLocale(Locale locale) {
|
||||||
this.locale = locale;
|
this.locale = locale;
|
||||||
|
@ -150,8 +159,8 @@ public class BaseApplicationBuilder implements ApplicationBuilder {
|
||||||
if (this.home == null) {
|
if (this.home == null) {
|
||||||
this.home = Paths.get(System.getProperty("application.home", "."));
|
this.home = Paths.get(System.getProperty("application.home", "."));
|
||||||
}
|
}
|
||||||
if (this.settings == null) {
|
if (this.prefix == null) {
|
||||||
this.settings = Settings.emptySettings();
|
this.prefix = "/";
|
||||||
}
|
}
|
||||||
if (this.classLoader == null) {
|
if (this.classLoader == null) {
|
||||||
this.classLoader = getClass().getClassLoader();
|
this.classLoader = getClass().getClassLoader();
|
||||||
|
@ -177,6 +186,26 @@ public class BaseApplicationBuilder implements ApplicationBuilder {
|
||||||
if (executor == null) {
|
if (executor == null) {
|
||||||
this.executor = BaseExecutor.builder().build();
|
this.executor = BaseExecutor.builder().build();
|
||||||
}
|
}
|
||||||
|
/*for (Map.Entry<String, Settings> entry : settings.getGroups("module").entrySet()) {
|
||||||
|
String moduleName = entry.getKey();
|
||||||
|
Settings moduleSettings = entry.getValue();
|
||||||
|
if (moduleSettings.getAsBoolean("enabled", true)) {
|
||||||
|
try {
|
||||||
|
String className = moduleSettings.get("class");
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
Class<ApplicationModule> clazz =
|
||||||
|
(Class<ApplicationModule>) Class.forName(className, true, builder.classLoader);
|
||||||
|
ApplicationModule applicationModule = clazz.getConstructor(Application.class, String.class, Settings.class)
|
||||||
|
.newInstance(this, moduleName, moduleSettings);
|
||||||
|
applicationModuleList.add(applicationModule);
|
||||||
|
} catch (Exception e) {
|
||||||
|
logger.log(Level.WARNING, e.getMessage(), e);
|
||||||
|
throw new IllegalArgumentException("class not found or not loadable: " + e.getMessage());
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
logger.log(Level.WARNING, "disabled module: " + moduleName);
|
||||||
|
}
|
||||||
|
}*/
|
||||||
return new BaseApplication(this);
|
return new BaseApplication(this);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,8 +1,6 @@
|
||||||
package org.xbib.net.http.server.ldap;
|
package org.xbib.net.http.server.ldap;
|
||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.security.PrivilegedActionException;
|
|
||||||
import java.security.PrivilegedExceptionAction;
|
|
||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
|
@ -12,7 +10,6 @@ import javax.naming.directory.InitialDirContext;
|
||||||
import javax.naming.ldap.InitialLdapContext;
|
import javax.naming.ldap.InitialLdapContext;
|
||||||
import javax.naming.ldap.StartTlsRequest;
|
import javax.naming.ldap.StartTlsRequest;
|
||||||
import javax.naming.ldap.StartTlsResponse;
|
import javax.naming.ldap.StartTlsResponse;
|
||||||
import javax.security.auth.Subject;
|
|
||||||
import javax.security.auth.login.Configuration;
|
import javax.security.auth.login.Configuration;
|
||||||
import javax.security.auth.login.LoginContext;
|
import javax.security.auth.login.LoginContext;
|
||||||
import javax.security.auth.login.LoginException;
|
import javax.security.auth.login.LoginException;
|
||||||
|
@ -135,15 +132,13 @@ public class LdapContextFactory {
|
||||||
try {
|
try {
|
||||||
LoginContext lc = new LoginContext(getClass().getName(), new CallbackHandlerImpl(principal, credentials));
|
LoginContext lc = new LoginContext(getClass().getName(), new CallbackHandlerImpl(principal, credentials));
|
||||||
lc.login();
|
lc.login();
|
||||||
initialDirContext = Subject.doAs(lc.getSubject(), (PrivilegedExceptionAction<InitialDirContext>) () -> {
|
|
||||||
Properties env = new Properties();
|
Properties env = new Properties();
|
||||||
env.put(Context.INITIAL_CONTEXT_FACTORY, factory);
|
env.put(Context.INITIAL_CONTEXT_FACTORY, factory);
|
||||||
env.put(Context.PROVIDER_URL, providerUrl);
|
env.put(Context.PROVIDER_URL, providerUrl);
|
||||||
env.put(Context.REFERRAL, referral);
|
env.put(Context.REFERRAL, referral);
|
||||||
logger.log(Level.FINE, "new initial LDAP context: " + env);
|
logger.log(Level.FINE, "new initial LDAP context: " + env);
|
||||||
return new InitialLdapContext(env, null);
|
initialDirContext = new InitialLdapContext(env, null);
|
||||||
});
|
} catch (LoginException e) {
|
||||||
} catch (LoginException | PrivilegedActionException e) {
|
|
||||||
NamingException namingException = new NamingException(e.getMessage());
|
NamingException namingException = new NamingException(e.getMessage());
|
||||||
namingException.initCause(e);
|
namingException.initCause(e);
|
||||||
throw namingException;
|
throw namingException;
|
||||||
|
|
|
@ -54,7 +54,7 @@ public class HtmlTemplateResource implements HttpServerResource {
|
||||||
this.templateResourceHandler = templateResourceHandler;
|
this.templateResourceHandler = templateResourceHandler;
|
||||||
this.application = httpRouterContext.getAttributes().get(Application.class, "application");
|
this.application = httpRouterContext.getAttributes().get(Application.class, "application");
|
||||||
Objects.requireNonNull(application);
|
Objects.requireNonNull(application);
|
||||||
this.shouldNegotiateLocale = application.getSettings().getAsBoolean("negotiateLocale", false);
|
this.shouldNegotiateLocale = application.shouldNegotiateLocale();
|
||||||
this.responseBuilder = httpRouterContext.getAttributes().get(HttpResponseBuilder.class, "responsebuilder");
|
this.responseBuilder = httpRouterContext.getAttributes().get(HttpResponseBuilder.class, "responsebuilder");
|
||||||
Objects.requireNonNull(responseBuilder);
|
Objects.requireNonNull(responseBuilder);
|
||||||
Path root = templateResourceHandler.getRoot();
|
Path root = templateResourceHandler.getRoot();
|
||||||
|
@ -64,17 +64,18 @@ public class HtmlTemplateResource implements HttpServerResource {
|
||||||
}
|
}
|
||||||
this.resourcePath = httpRouterContext.getRequestBuilder().getRequestPath().substring(1);
|
this.resourcePath = httpRouterContext.getRequestBuilder().getRequestPath().substring(1);
|
||||||
this.path = !resourcePath.isEmpty() ? root.resolve(resourcePath) : root;
|
this.path = !resourcePath.isEmpty() ? root.resolve(resourcePath) : root;
|
||||||
|
String indexFileName = templateResourceHandler.getIndexFileName();
|
||||||
logger.log(Level.FINEST, "class = " + getClass().getName() +
|
logger.log(Level.FINEST, "class = " + getClass().getName() +
|
||||||
" root = " + root +
|
" root = " + root +
|
||||||
" resource path = " + resourcePath +
|
" resource path = " + resourcePath +
|
||||||
" path = " + path +
|
" path = " + path +
|
||||||
" index file name = " + templateResourceHandler.getIndexFileName());
|
" index file name = " + indexFileName);
|
||||||
this.name = path.getFileName().toString();
|
this.name = path.getFileName().toString();
|
||||||
this.baseName = AbstractResourceHandler.basename(name);
|
this.baseName = AbstractResourceHandler.basename(name);
|
||||||
this.suffix = AbstractResourceHandler.suffix(name);
|
this.suffix = AbstractResourceHandler.suffix(name);
|
||||||
if (Files.isDirectory(path)) {
|
if (Files.isDirectory(path)) {
|
||||||
if (getIndexFileName() != null) {
|
if (indexFileName != null) {
|
||||||
Path indexPath = path.resolve(templateResourceHandler.getIndexFileName());
|
Path indexPath = path.resolve(indexFileName);
|
||||||
logger.log(Level.FINEST, "resolved to index path = " + indexPath);
|
logger.log(Level.FINEST, "resolved to index path = " + indexPath);
|
||||||
if (Files.exists(indexPath)) {
|
if (Files.exists(indexPath)) {
|
||||||
logger.log(Level.FINEST, "index path exists");
|
logger.log(Level.FINEST, "index path exists");
|
||||||
|
@ -191,11 +192,14 @@ public class HtmlTemplateResource implements HttpServerResource {
|
||||||
}
|
}
|
||||||
|
|
||||||
public String url(HttpRequest request, String rel, boolean absolute) {
|
public String url(HttpRequest request, String rel, boolean absolute) {
|
||||||
String webPrefix = application.getSettings().get("web.prefix", "/");
|
String prefix = application.getPrefix();
|
||||||
if (!webPrefix.endsWith("/")) {
|
if (prefix == null) {
|
||||||
webPrefix = webPrefix + "/";
|
prefix = "/";
|
||||||
}
|
}
|
||||||
URL url = request.getBaseURL().resolve(webPrefix).resolve(rel);
|
if (!prefix.endsWith("/")) {
|
||||||
|
prefix = prefix + "/";
|
||||||
|
}
|
||||||
|
URL url = request.getBaseURL().resolve(prefix).resolve(rel);
|
||||||
return absolute ? url.toExternalForm() : toOrigin(url);
|
return absolute ? url.toExternalForm() : toOrigin(url);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -21,9 +21,9 @@ public class LocaleNegotiator {
|
||||||
}
|
}
|
||||||
lang = lang.trim();
|
lang = lang.trim();
|
||||||
if ((pos = lang.indexOf('-')) == -1) {
|
if ((pos = lang.indexOf('-')) == -1) {
|
||||||
locale = new Locale(lang, Locale.getDefault().getCountry());
|
locale = Locale.of(lang, Locale.getDefault().getCountry());
|
||||||
} else {
|
} else {
|
||||||
locale = new Locale(lang.substring(0, pos), lang.substring(pos + 1));
|
locale = Locale.of(lang.substring(0, pos), lang.substring(pos + 1));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -59,16 +59,17 @@ public class BaseHttpRoute implements HttpRoute {
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getPrefix() {
|
public final String getPrefix() {
|
||||||
return prefix;
|
return prefix;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getPath() {
|
public final String getPath() {
|
||||||
return path;
|
return path;
|
||||||
}
|
}
|
||||||
|
|
||||||
public String getEffectivePath() {
|
@Override
|
||||||
|
public final String getEffectivePath() {
|
||||||
String path = getPath();
|
String path = getPath();
|
||||||
if (getPrefix() != null && !getPrefix().isEmpty()) {
|
if (getPrefix() != null && !getPrefix().isEmpty()) {
|
||||||
path = path.replaceFirst(getPrefix(), "");
|
path = path.replaceFirst(getPrefix(), "");
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
package org.xbib.net.http.server.route;
|
package org.xbib.net.http.server.route;
|
||||||
|
|
||||||
|
import java.security.KeyStoreException;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
@ -7,8 +8,17 @@ import java.util.Map;
|
||||||
import java.util.Objects;
|
import java.util.Objects;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.logging.Logger;
|
import java.util.logging.Logger;
|
||||||
|
|
||||||
|
import org.xbib.net.URL;
|
||||||
|
import org.xbib.net.http.HttpAddress;
|
||||||
|
import org.xbib.net.http.HttpMethod;
|
||||||
|
import org.xbib.net.http.HttpVersion;
|
||||||
import org.xbib.net.http.server.HttpHandler;
|
import org.xbib.net.http.server.HttpHandler;
|
||||||
|
import org.xbib.net.http.server.HttpServiceBuilder;
|
||||||
|
import org.xbib.net.http.server.domain.BaseHttpDomain;
|
||||||
import org.xbib.net.http.server.domain.HttpDomain;
|
import org.xbib.net.http.server.domain.HttpDomain;
|
||||||
|
import org.xbib.net.http.server.domain.HttpDomainBuilder;
|
||||||
|
import org.xbib.net.http.server.domain.HttpSecurityDomain;
|
||||||
import org.xbib.net.http.server.handler.BadRequestHandler;
|
import org.xbib.net.http.server.handler.BadRequestHandler;
|
||||||
import org.xbib.net.http.server.handler.ForbiddenHandler;
|
import org.xbib.net.http.server.handler.ForbiddenHandler;
|
||||||
import org.xbib.net.http.server.handler.InternalServerErrorHandler;
|
import org.xbib.net.http.server.handler.InternalServerErrorHandler;
|
||||||
|
@ -16,7 +26,11 @@ import org.xbib.net.http.server.handler.NotFoundHandler;
|
||||||
import org.xbib.net.http.server.handler.NotImplementedHandler;
|
import org.xbib.net.http.server.handler.NotImplementedHandler;
|
||||||
import org.xbib.net.http.server.handler.UnauthorizedHandler;
|
import org.xbib.net.http.server.handler.UnauthorizedHandler;
|
||||||
import org.xbib.net.http.server.handler.VersionNotSupportedHandler;
|
import org.xbib.net.http.server.handler.VersionNotSupportedHandler;
|
||||||
|
import org.xbib.net.http.server.service.BaseHttpService;
|
||||||
import org.xbib.net.http.server.service.HttpService;
|
import org.xbib.net.http.server.service.HttpService;
|
||||||
|
import org.xbib.settings.Settings;
|
||||||
|
|
||||||
|
import javax.net.ssl.SSLException;
|
||||||
|
|
||||||
public class BaseHttpRouterBuilder implements HttpRouterBuilder {
|
public class BaseHttpRouterBuilder implements HttpRouterBuilder {
|
||||||
|
|
||||||
|
@ -31,16 +45,17 @@ public class BaseHttpRouterBuilder implements HttpRouterBuilder {
|
||||||
protected HttpRouteResolver<HttpService> httpRouteResolver;
|
protected HttpRouteResolver<HttpService> httpRouteResolver;
|
||||||
|
|
||||||
protected BaseHttpRouterBuilder() {
|
protected BaseHttpRouterBuilder() {
|
||||||
prefix = "";
|
this.prefix = "";
|
||||||
domains = new ArrayList<>();
|
this.domains = new ArrayList<>();
|
||||||
handlers = new HashMap<>();
|
this.handlers = new HashMap<>();
|
||||||
handlers.put(400, new BadRequestHandler());
|
// default handlers
|
||||||
handlers.put(401, new UnauthorizedHandler());
|
this.handlers.put(400, new BadRequestHandler());
|
||||||
handlers.put(403, new ForbiddenHandler());
|
this.handlers.put(401, new UnauthorizedHandler());
|
||||||
handlers.put(404, new NotFoundHandler());
|
this.handlers.put(403, new ForbiddenHandler());
|
||||||
handlers.put(500, new InternalServerErrorHandler());
|
this.handlers.put(404, new NotFoundHandler());
|
||||||
handlers.put(501, new NotImplementedHandler());
|
this.handlers.put(500, new InternalServerErrorHandler());
|
||||||
handlers.put(505, new VersionNotSupportedHandler());
|
this.handlers.put(501, new NotImplementedHandler());
|
||||||
|
this.handlers.put(505, new VersionNotSupportedHandler());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -55,7 +70,9 @@ public class BaseHttpRouterBuilder implements HttpRouterBuilder {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public BaseHttpRouterBuilder setHandler(Integer code, HttpHandler httpHandler) {
|
public BaseHttpRouterBuilder setHandler(Integer code, HttpHandler httpHandler) {
|
||||||
|
if (httpHandler != null) {
|
||||||
handlers.put(code, httpHandler);
|
handlers.put(code, httpHandler);
|
||||||
|
}
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -71,6 +88,31 @@ public class BaseHttpRouterBuilder implements HttpRouterBuilder {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public HttpRouterBuilder fromSettings(Settings settings) {
|
||||||
|
fromSettings(settings, null);
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public HttpRouterBuilder fromSettings(Settings settings,
|
||||||
|
Map<String, HttpSecurityDomain> securityDomainMap) {
|
||||||
|
// global prefix
|
||||||
|
if (settings.containsSetting("prefix")) {
|
||||||
|
setPrefix(settings.get("prefix"));
|
||||||
|
}
|
||||||
|
// global handlers
|
||||||
|
for (Map.Entry<String, Settings> entry : settings.getGroups("handler").entrySet()) {
|
||||||
|
String codeString = entry.getKey();
|
||||||
|
Settings handlerSettings = entry.getValue();
|
||||||
|
setHandler(Integer.parseInt(codeString), createHttpHandler(handlerSettings));
|
||||||
|
}
|
||||||
|
// handler domains
|
||||||
|
for (Map.Entry<String, Settings> entry : settings.getGroups("domain").entrySet()) {
|
||||||
|
addDomain(createHttpDomain(entry.getValue(), securityDomainMap));
|
||||||
|
}
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public BaseHttpRouter build() {
|
public BaseHttpRouter build() {
|
||||||
if (domains.isEmpty()) {
|
if (domains.isEmpty()) {
|
||||||
|
@ -95,4 +137,79 @@ public class BaseHttpRouterBuilder implements HttpRouterBuilder {
|
||||||
}
|
}
|
||||||
return new BaseHttpRouter(this);
|
return new BaseHttpRouter(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private HttpDomain createHttpDomain(Settings settings,
|
||||||
|
Map<String, HttpSecurityDomain> securityDomainMap) {
|
||||||
|
if (settings.getAsBoolean("enabled", true)) {
|
||||||
|
try {
|
||||||
|
HttpDomainBuilder httpDomainBuilder = BaseHttpDomain.builder();
|
||||||
|
httpDomainBuilder.setHttpAddress(createHttpAddress(settings));
|
||||||
|
for (String name : settings.getAsArray("name")) {
|
||||||
|
httpDomainBuilder.addName(name);
|
||||||
|
}
|
||||||
|
for (Map.Entry<String, Settings> entry : settings.getGroups("service").entrySet()) {
|
||||||
|
httpDomainBuilder.addService(createHttpService(securityDomainMap, prefix, entry.getKey(), entry.getValue()));
|
||||||
|
}
|
||||||
|
return httpDomainBuilder.build();
|
||||||
|
} catch (Exception e) {
|
||||||
|
logger.log(Level.WARNING, e.getMessage(), e);
|
||||||
|
throw new IllegalArgumentException("class not found or not loadable: " + e.getMessage());
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
logger.log(Level.WARNING, "disabled: " + settings.getAsMap());
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
private HttpAddress createHttpAddress(Settings settings) throws KeyStoreException, SSLException {
|
||||||
|
HttpAddress.Builder httpAddressBuilder = HttpAddress.builder();
|
||||||
|
if (settings.containsSetting("url")) {
|
||||||
|
URL url = URL.create(settings.get("url"));
|
||||||
|
httpAddressBuilder.setHost(url.getHost());
|
||||||
|
httpAddressBuilder.setPort(url.getPort());
|
||||||
|
httpAddressBuilder.setSecure("https".equals(url.getScheme()) || "h2".equals(url.getScheme()));
|
||||||
|
httpAddressBuilder.setVersion(url.getScheme().startsWith("http") ? HttpVersion.HTTP_1_1 : HttpVersion.HTTP_2_0);
|
||||||
|
} else {
|
||||||
|
httpAddressBuilder.setHost(settings.get("host", "localhost"));
|
||||||
|
boolean isSecure = settings.getAsBoolean("secure", false);
|
||||||
|
httpAddressBuilder.setSecure(isSecure);
|
||||||
|
httpAddressBuilder.setPort(settings.getAsInt("port", isSecure ? 443 : 80));
|
||||||
|
httpAddressBuilder.setVersion(HttpVersion.valueOf(settings.get("version", "HTTP_1_1")));
|
||||||
|
}
|
||||||
|
return httpAddressBuilder.build();
|
||||||
|
}
|
||||||
|
|
||||||
|
private HttpService createHttpService(Map<String, HttpSecurityDomain> securityDomainMap,
|
||||||
|
String prefix,
|
||||||
|
String path,
|
||||||
|
Settings settings) {
|
||||||
|
HttpServiceBuilder httpServiceBuilder = BaseHttpService.builder();
|
||||||
|
if (settings.containsSetting("securitydomain")) {
|
||||||
|
if (securityDomainMap != null) {
|
||||||
|
httpServiceBuilder.setSecurityDomain(securityDomainMap.get(settings.get("securitydomain")));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
httpServiceBuilder.setPrefix(prefix);
|
||||||
|
httpServiceBuilder.setPath(path);
|
||||||
|
httpServiceBuilder.setMethod(HttpMethod.valueOf(settings.get("method", "GET")));
|
||||||
|
httpServiceBuilder.setHandler(createHttpHandler(settings));
|
||||||
|
return httpServiceBuilder.build();
|
||||||
|
}
|
||||||
|
|
||||||
|
private HttpHandler createHttpHandler(Settings settings) {
|
||||||
|
if (settings.getAsBoolean("enabled", true)) {
|
||||||
|
try {
|
||||||
|
String className = settings.get("class");
|
||||||
|
@SuppressWarnings("unchecked")
|
||||||
|
Class<HttpHandler> clazz = (Class<HttpHandler>) Class.forName(className, true, getClass().getClassLoader());
|
||||||
|
return clazz.getConstructor().newInstance();
|
||||||
|
} catch (Exception e) {
|
||||||
|
logger.log(Level.WARNING, e.getMessage(), e);
|
||||||
|
throw new IllegalArgumentException("class not found or not loadable: " + e.getMessage());
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
logger.log(Level.WARNING, "disabled: " + settings.getAsMap());
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,7 +2,11 @@ package org.xbib.net.http.server.route;
|
||||||
|
|
||||||
import org.xbib.net.http.server.HttpHandler;
|
import org.xbib.net.http.server.HttpHandler;
|
||||||
import org.xbib.net.http.server.domain.HttpDomain;
|
import org.xbib.net.http.server.domain.HttpDomain;
|
||||||
|
import org.xbib.net.http.server.domain.HttpSecurityDomain;
|
||||||
import org.xbib.net.http.server.service.HttpService;
|
import org.xbib.net.http.server.service.HttpService;
|
||||||
|
import org.xbib.settings.Settings;
|
||||||
|
|
||||||
|
import java.util.Map;
|
||||||
|
|
||||||
public interface HttpRouterBuilder {
|
public interface HttpRouterBuilder {
|
||||||
|
|
||||||
|
@ -14,5 +18,10 @@ public interface HttpRouterBuilder {
|
||||||
|
|
||||||
HttpRouterBuilder setRouteResolver(HttpRouteResolver<HttpService> httpRouteResolver);
|
HttpRouterBuilder setRouteResolver(HttpRouteResolver<HttpService> httpRouteResolver);
|
||||||
|
|
||||||
|
HttpRouterBuilder fromSettings(Settings settings);
|
||||||
|
|
||||||
|
HttpRouterBuilder fromSettings(Settings settings,
|
||||||
|
Map<String, HttpSecurityDomain> securityDomainMap);
|
||||||
|
|
||||||
HttpRouter build();
|
HttpRouter build();
|
||||||
}
|
}
|
||||||
|
|
|
@ -131,7 +131,7 @@ public class BaseSession implements Session {
|
||||||
|
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
@Override
|
@Override
|
||||||
public Object put(String key, Object value) {
|
public final Object put(String key, Object value) {
|
||||||
Object v = value;
|
Object v = value;
|
||||||
if (key.startsWith(CACHE_PREFIX)) {
|
if (key.startsWith(CACHE_PREFIX)) {
|
||||||
if (value instanceof Map) {
|
if (value instanceof Map) {
|
||||||
|
@ -147,7 +147,7 @@ public class BaseSession implements Session {
|
||||||
|
|
||||||
@SuppressWarnings({"unchecked", "rawtypes"})
|
@SuppressWarnings({"unchecked", "rawtypes"})
|
||||||
@Override
|
@Override
|
||||||
public void putAll(Map map) {
|
public final void putAll(Map map) {
|
||||||
if (map == null) {
|
if (map == null) {
|
||||||
throw new NullPointerException("unexpected null map for putAll");
|
throw new NullPointerException("unexpected null map for putAll");
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,8 @@ module org.xbib.net.http.server.test {
|
||||||
requires org.xbib.net;
|
requires org.xbib.net;
|
||||||
requires org.xbib.net.http;
|
requires org.xbib.net.http;
|
||||||
requires org.xbib.net.http.server;
|
requires org.xbib.net.http.server;
|
||||||
|
requires org.xbib.datastructures.json.tiny;
|
||||||
|
requires org.xbib.settings.api;
|
||||||
exports org.xbib.net.http.server.test.base;
|
exports org.xbib.net.http.server.test.base;
|
||||||
exports org.xbib.net.http.server.test.ldap;
|
exports org.xbib.net.http.server.test.ldap;
|
||||||
exports org.xbib.net.http.server.test.session;
|
exports org.xbib.net.http.server.test.session;
|
||||||
|
|
|
@ -14,6 +14,9 @@ import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
|
|
||||||
public class BaseHttpRouteResolverTest {
|
public class BaseHttpRouteResolverTest {
|
||||||
|
|
||||||
|
public BaseHttpRouteResolverTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
public void testEmptyRouteResolver() {
|
public void testEmptyRouteResolver() {
|
||||||
BaseHttpRouteResolver.Builder<Integer> builder = BaseHttpRouteResolver.builder();
|
BaseHttpRouteResolver.Builder<Integer> builder = BaseHttpRouteResolver.builder();
|
||||||
|
|
|
@ -0,0 +1,21 @@
|
||||||
|
package org.xbib.net.http.server.test.base;
|
||||||
|
|
||||||
|
import org.junit.jupiter.api.Test;
|
||||||
|
import org.xbib.net.http.server.route.BaseHttpRouter;
|
||||||
|
import org.xbib.net.http.server.route.HttpRouter;
|
||||||
|
import org.xbib.settings.Settings;
|
||||||
|
|
||||||
|
public class RouterBuilderTest {
|
||||||
|
|
||||||
|
public RouterBuilderTest() {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
void buildFromSettings() {
|
||||||
|
// java.lang.NullPointerException: Cannot invoke "org.xbib.settings.SettingsBuilder.build()" because the return value of "org.xbib.settings.Settings$Holder.createBuilder()" is null
|
||||||
|
Settings settings = Settings.emptySettings();
|
||||||
|
HttpRouter httpRouter = BaseHttpRouter.builder()
|
||||||
|
.fromSettings(settings)
|
||||||
|
.build();
|
||||||
|
}
|
||||||
|
}
|
|
@ -20,6 +20,8 @@ import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||||
|
|
||||||
public class LdapRealmTest {
|
public class LdapRealmTest {
|
||||||
|
|
||||||
|
public LdapRealmTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Disabled
|
@Disabled
|
||||||
@Test
|
@Test
|
||||||
|
|
|
@ -13,6 +13,9 @@ import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||||
|
|
||||||
public class LdapTest {
|
public class LdapTest {
|
||||||
|
|
||||||
|
public LdapTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Disabled
|
@Disabled
|
||||||
@Test
|
@Test
|
||||||
public void testLdap() {
|
public void testLdap() {
|
||||||
|
|
|
@ -15,6 +15,9 @@ import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
|
|
||||||
public class JsonSessionTest {
|
public class JsonSessionTest {
|
||||||
|
|
||||||
|
public JsonSessionTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testJsonSession() throws IOException {
|
void testJsonSession() throws IOException {
|
||||||
Codec<Session> sessionCodec = newSessionCodec();
|
Codec<Session> sessionCodec = newSessionCodec();
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
package org.xbib.net.http.server.test.userprofile;
|
package org.xbib.net.http.server.test.userprofile;
|
||||||
|
|
||||||
import org.junit.jupiter.api.Test;
|
import org.junit.jupiter.api.Test;
|
||||||
|
import org.xbib.datastructures.json.tiny.JsonBuilder;
|
||||||
import org.xbib.net.UserProfile;
|
import org.xbib.net.UserProfile;
|
||||||
import org.xbib.net.http.server.persist.Codec;
|
import org.xbib.net.http.server.persist.Codec;
|
||||||
import org.xbib.net.http.server.auth.FileJsonUserProfileCodec;
|
import org.xbib.net.http.server.auth.FileJsonUserProfileCodec;
|
||||||
|
@ -12,6 +13,8 @@ import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
|
|
||||||
public class JsonUserProfileTest {
|
public class JsonUserProfileTest {
|
||||||
|
|
||||||
|
public JsonUserProfileTest() {
|
||||||
|
}
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
void testJsonUserProfile() throws IOException {
|
void testJsonUserProfile() throws IOException {
|
||||||
|
|
|
@ -115,16 +115,19 @@ public abstract class DefaultMarkupTemplate extends BaseTemplate {
|
||||||
}
|
}
|
||||||
|
|
||||||
public String url(String rel, boolean absolute) {
|
public String url(String rel, boolean absolute) {
|
||||||
String webPrefix = application.getSettings().get("web.prefix", "/");
|
String prefix = application.getPrefix();
|
||||||
if (!webPrefix.endsWith("/")) {
|
if (prefix == null) {
|
||||||
webPrefix = webPrefix + "/";
|
prefix = "/";
|
||||||
|
}
|
||||||
|
if (!prefix.endsWith("/")) {
|
||||||
|
prefix = prefix + "/";
|
||||||
}
|
}
|
||||||
if (request != null) {
|
if (request != null) {
|
||||||
URL url = request.getBaseURL().resolve(webPrefix).resolve(rel);
|
URL url = request.getBaseURL().resolve(prefix).resolve(rel);
|
||||||
return absolute ? url.toExternalForm() : toOrigin(url);
|
return absolute ? url.toExternalForm() : toOrigin(url);
|
||||||
} else {
|
} else {
|
||||||
logger.log(Level.WARNING, "request is null, returning " + webPrefix + rel);
|
logger.log(Level.WARNING, "request is null, returning " + prefix + rel);
|
||||||
return webPrefix + rel;
|
return prefix + rel;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -72,7 +72,7 @@ public class GroovyMarkupTemplateHandler implements HttpHandler {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected TemplateConfiguration createConfiguration(Class<? extends BaseTemplate> templateClass,
|
protected final TemplateConfiguration createConfiguration(Class<? extends BaseTemplate> templateClass,
|
||||||
Locale locale,
|
Locale locale,
|
||||||
boolean autoEscape,
|
boolean autoEscape,
|
||||||
boolean autoIndent,
|
boolean autoIndent,
|
||||||
|
|
|
@ -7,8 +7,6 @@ import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
/**
|
|
||||||
*/
|
|
||||||
public class HttpHeaders implements Headers {
|
public class HttpHeaders implements Headers {
|
||||||
|
|
||||||
private final List<Pair<String, String>> list;
|
private final List<Pair<String, String>> list;
|
||||||
|
|
|
@ -35,7 +35,7 @@ public class DefaultCookie implements Cookie {
|
||||||
throw new IllegalArgumentException("empty name");
|
throw new IllegalArgumentException("empty name");
|
||||||
}
|
}
|
||||||
if (value != null) {
|
if (value != null) {
|
||||||
setValue(value);
|
this.value = Objects.requireNonNull(value, "value");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue