diff --git a/.gitattributes b/.gitattributes index 3f0ee056c1d9..28ecad0f6ecc 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1,11 +1,60 @@ -*.sh eol=lf +# Shell Scripts *.bat eol=crlf -*.txt eol=lf -*.properties eol=lf +*.sh eol=lf + +# Sources +*.groovy eol=lf *.java eol=lf + +# Configuration +*.dtd eol=lf +*.ini eol=lf +*.json eol=lf *.mod eol=lf -*.adoc eol=lf +*.properties eol=lf +*.sql eol=lf +*.xsl eol=lf +*.xslt eol=lf *.xml eol=lf -Jenkinsfile eol=lf +*.yaml eol=lf +*.yml eol=lf + +# Text / Documentation +*.adoc eol=lf +*.dot eol=lf +*.txt eol=lf +*.TXT eol=lf +*.md eol=lf +*.pdf binary + +# Web +*.gif binary +*.htm eol=lf +*.html eol=lf +*.ico binary +*.jar binary +*.jpg binary +*.jpeg binary *.js eol=lf +*.jsp eol=lf +*.jspf eol=lf +*.png binary +*.svg eol=lf +*.svgz binary +*.tga binary +*.tif binary +*.tiff binary +*.ttf binary +*.war binary + +# Build Files +Jenkinsfile eol=lf + +# Binaries *.raw binary +*.gz binary +*.zip binary +*.br binary +*.brotli binary +*.bz2 binary + diff --git a/.github/dependabot.yml b/.github/dependabot.yml index e1d1cc748c60..981dc2d3d04a 100644 --- a/.github/dependabot.yml +++ b/.github/dependabot.yml @@ -4,7 +4,34 @@ updates: directory: "/" schedule: interval: "weekly" + target-branch: "jetty-9.4.x" + - package-ecosystem: "github-actions" directory: "/" schedule: interval: "weekly" + target-branch: "jetty-9.4.x" + + - package-ecosystem: "maven" + directory: "/" + schedule: + interval: "weekly" + target-branch: "jetty-10.0.x" + + - package-ecosystem: "github-actions" + directory: "/" + schedule: + interval: "weekly" + target-branch: "jetty-10.0.x" + + - package-ecosystem: "maven" + directory: "/" + schedule: + interval: "weekly" + target-branch: "jetty-11.0.x" + + - package-ecosystem: "github-actions" + directory: "/" + schedule: + interval: "weekly" + target-branch: "jetty-11.0.x" diff --git a/.github/release-config.yml b/.github/release-config.yml new file mode 100644 index 000000000000..ee0590090e4b --- /dev/null +++ b/.github/release-config.yml @@ -0,0 +1,61 @@ +# Emoji reference: https://gitmoji.carloscuesta.me/ +categories: + - title: ":boom: Breaking changes" + labels: + - breaking + - title: 🚨 Removed + label: removed + - title: ":tada: Major features and improvements" + labels: + - major-enhancement + - major-rfe + - title: 🐛 Major bug fixes + labels: + - major-bug + - title: ⚠️ Deprecated + label: deprecated + - title: 🚀 New features and improvements + labels: + - enhancement + - feature + - rfe + - title: 🐛 Bug Fixes + labels: + - bug + - Bug + - fix + - bugfix + - regression + - title: ":construction_worker: Changes for plugin developers" + labels: + - developer + # Default label used by Dependabot + - title: 📦 Dependency updates + label: dependencies + - title: 📝 Documentation updates + label: documentation + - title: 👻 Maintenance + labels: + - chore + - internal + - Build + - build + - title: 🚦 Tests + labels: + - test + - tests + - Test + - Tests +exclude-labels: + - reverted + - no-changelog + - skip-changelog + - invalid + +change-template: '- $TITLE @$AUTHOR (#$NUMBER)' +# Disable certain characters in title from being interpreted as markdown +change-title-escapes: '\<*_&#' + +template: | + + $CHANGES diff --git a/VERSION.txt b/VERSION.txt index 1e4bc845b913..54b31beeba40 100644 --- a/VERSION.txt +++ b/VERSION.txt @@ -1,4 +1,53 @@ -jetty-9.4.32-SNAPSHOT +jetty-9.4.33-SNAPSHOT + +jetty-9.4.32.v20200930 - 30 September 2020 + + 2796 HTTP/2 max local stream count exceeded when request fails + + 3766 Introduce HTTP/2 API to batch frames + + 3916 multipart/byterange output is invalid to RFC7233 + + 4809 Set a max number of requests per connection + + 4824 WebSocket server outgoing message queue memory growth + + 4888 Request getSession() method throws IllegalStateException when Session + exists + + 4954 Simplify ability to get Byte Counts about requests + + 5032 Introduce Listeners to aid in tracking timings within ServletContext + and WebApp + + 5079 :authority header for IPv6 address not having square brackets + + 5103 Proxy sets protocol version to 2.0 instead of 1.1 when accessed from H2 + client + + 5104 AbstractProxyServlet include incorrect protocol version in Via header + when accessed over H2 + + 5105 Graceful shutdown does not wait for resumed requests + + 5108 Improve SessionTracker scalability + + 5121 Add if (LOG.isDebugEnabled()) in CompressExtension.decompress + + 5122 Retrieving websocket connections via jmx + + 5129 No jars added when using a folder in extraClasspath of the webapp + context xml file + + 5147 Set MaxUsageCount with existing connection pool changing the behavior + + 5150 Zero connection timeout is not supported in HTTP client with + non-blocking connect + + 5152 HttpClient should handle unsolicited responses + + 5162 DecoratingListener raises a NullPointerException + + 5165 Wrong messagesIn count for HttpClient + + 5170 NullPointerException in HttpReceiverOverHTTP during WebSocket client + Upgrade + + 5185 Introduce DoSFilter Listener for Alert messages + + 5193 WebSocket unimplemented BINARY message handling can result in TEXT + message delivery to fail + + 5201 QueuedThreadPool setDetailedDump gives less detail + + 5204 SNI does not work with PKIX + + 5214 Servlet HEAD doesn't support content-length over Integer.MAX_VALUE + + 5217 Review RoundRobinConnectionPool + + 5224 HttpServletRequest.getServerName can include port when using + ForwardedRequestCustomizer + + 5233 Bad/Unsupported HTTP version should return 505 not 400 + + 5246 GzipHandler's DeflaterPool should be dumpable + + 5247 Improve ForwardRequestCustomizer authority priority + + 5268 WARN Ignoring eviction setting: 0 + + 5285 Per RFC7694, if a Content-Encoding isn't recognized, reject with 415 + Unsupported Media Type + + 5362 Default ProxyServlet cannot proxy to https urls + + 5365 org.eclipse.jetty.server.Request throws NullPointerException if + SessionHandler newHttpSession returns null jetty-9.4.31.v20200723 - 23 July 2020 + 1100 JSR356 Encoder#init is not called when created on demand diff --git a/aggregates/jetty-all-compact3/pom.xml b/aggregates/jetty-all-compact3/pom.xml index 1bf2833e8dfa..c49d0e0f5ee5 100644 --- a/aggregates/jetty-all-compact3/pom.xml +++ b/aggregates/jetty-all-compact3/pom.xml @@ -2,14 +2,13 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../../pom.xml 4.0.0 org.eclipse.jetty.aggregate jetty-all-compact3 Jetty :: Aggregate :: All core Jetty suitable for Java 8 compact 3 profile - http://www.eclipse.org/jetty ${project.groupId}.all.compact3 @@ -87,7 +86,9 @@ org.apache.maven.plugins maven-javadoc-plugin - -Xdoclint:none --allow-script-in-comments + + -Xdoclint:none + -Xdoclint:none diff --git a/aggregates/jetty-all/pom.xml b/aggregates/jetty-all/pom.xml index 55e8af71cac6..8f263feb531c 100644 --- a/aggregates/jetty-all/pom.xml +++ b/aggregates/jetty-all/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../../pom.xml 4.0.0 @@ -11,7 +11,6 @@ Jetty :: Aggregate :: All core Jetty UberJar for Core Jetty features pom - http://www.eclipse.org/jetty ${project.build.directory}/${project.artifactId}-${project.version}-uber.jar ${project.build.directory}/gen-resources diff --git a/aggregates/jetty-websocket-all/pom.xml b/aggregates/jetty-websocket-all/pom.xml index 9c5b1bb3e13f..6ef3b0ef5e43 100644 --- a/aggregates/jetty-websocket-all/pom.xml +++ b/aggregates/jetty-websocket-all/pom.xml @@ -9,7 +9,6 @@ org.eclipse.jetty.aggregate jetty-websocket-all Jetty :: Aggregate :: All WebSocket Server + Client Classes - http://www.eclipse.org/jetty ${project.build.directory}/sources @@ -66,7 +65,7 @@ development - http://eclipse.org/jetty + https://eclipse.org/jetty ${user.name} org.eclipse.jetty https://raw.githubusercontent.com/eclipse/jetty.project/master/NOTICE.txt diff --git a/apache-jsp/pom.xml b/apache-jsp/pom.xml index 495f63d467c7..854e17b1c1cc 100644 --- a/apache-jsp/pom.xml +++ b/apache-jsp/pom.xml @@ -2,12 +2,11 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 apache-jsp Jetty :: Apache JSP Implementation - http://www.eclipse.org/jetty jar ${project.groupId}.apache-jsp diff --git a/apache-jstl/pom.xml b/apache-jstl/pom.xml index 6625b5b60da2..a509e7347fc8 100644 --- a/apache-jstl/pom.xml +++ b/apache-jstl/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 apache-jstl diff --git a/build-resources/pom.xml b/build-resources/pom.xml index 5449274cb1e3..6448abaea33a 100644 --- a/build-resources/pom.xml +++ b/build-resources/pom.xml @@ -2,7 +2,7 @@ 4.0.0 org.eclipse.jetty build-resources - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT jar Jetty :: Build Resources diff --git a/examples/async-rest/async-rest-jar/pom.xml b/examples/async-rest/async-rest-jar/pom.xml index ac7d94362fcc..d5f1a93946db 100644 --- a/examples/async-rest/async-rest-jar/pom.xml +++ b/examples/async-rest/async-rest-jar/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty example-async-rest - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/examples/async-rest/async-rest-webapp/pom.xml b/examples/async-rest/async-rest-webapp/pom.xml index 62884a0f2fc7..ee6c25bb017e 100644 --- a/examples/async-rest/async-rest-webapp/pom.xml +++ b/examples/async-rest/async-rest-webapp/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty example-async-rest - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/examples/async-rest/pom.xml b/examples/async-rest/pom.xml index d13e7681e022..452fa9bc3886 100644 --- a/examples/async-rest/pom.xml +++ b/examples/async-rest/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty.examples examples-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/examples/embedded/pom.xml b/examples/embedded/pom.xml index 8bef9fafb889..39eb524874b2 100644 --- a/examples/embedded/pom.xml +++ b/examples/embedded/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty.examples examples-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 @@ -10,7 +10,6 @@ example-jetty-embedded Example :: Jetty Embedded Jetty Embedded Examples - http://www.eclipse.org/jetty ${project.groupId}.embedded diff --git a/examples/pom.xml b/examples/pom.xml index 32ebfafc78d1..62c9d2b2253e 100644 --- a/examples/pom.xml +++ b/examples/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-alpn/jetty-alpn-client/pom.xml b/jetty-alpn/jetty-alpn-client/pom.xml index 2765e8fb44bb..b3764fa1d3fb 100644 --- a/jetty-alpn/jetty-alpn-client/pom.xml +++ b/jetty-alpn/jetty-alpn-client/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-alpn-client diff --git a/jetty-alpn/jetty-alpn-conscrypt-client/pom.xml b/jetty-alpn/jetty-alpn-conscrypt-client/pom.xml index 2f52b6b0324d..36d01fd98c80 100644 --- a/jetty-alpn/jetty-alpn-conscrypt-client/pom.xml +++ b/jetty-alpn/jetty-alpn-conscrypt-client/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-alpn/jetty-alpn-conscrypt-client/src/test/java/org/eclipse/jetty/alpn/java/client/ConscryptHTTP2ClientTest.java b/jetty-alpn/jetty-alpn-conscrypt-client/src/test/java/org/eclipse/jetty/alpn/java/client/ConscryptHTTP2ClientTest.java index 1c57340be4fc..d383f3ff2e83 100644 --- a/jetty-alpn/jetty-alpn-conscrypt-client/src/test/java/org/eclipse/jetty/alpn/java/client/ConscryptHTTP2ClientTest.java +++ b/jetty-alpn/jetty-alpn-conscrypt-client/src/test/java/org/eclipse/jetty/alpn/java/client/ConscryptHTTP2ClientTest.java @@ -60,7 +60,7 @@ public void testConscryptHTTP2Client() throws Exception Security.insertProviderAt(new OpenSSLProvider(), 1); SslContextFactory sslContextFactory = new SslContextFactory.Client(); sslContextFactory.setProvider("Conscrypt"); - Conscrypt.setDefaultHostnameVerifier((hostname, session) -> true); + Conscrypt.setDefaultHostnameVerifier((certs, hostname, session) -> true); HTTP2Client client = new HTTP2Client(); try diff --git a/jetty-alpn/jetty-alpn-conscrypt-server/pom.xml b/jetty-alpn/jetty-alpn-conscrypt-server/pom.xml index 04da360fef6c..09d20d6881d3 100644 --- a/jetty-alpn/jetty-alpn-conscrypt-server/pom.xml +++ b/jetty-alpn/jetty-alpn-conscrypt-server/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-alpn/jetty-alpn-java-client/pom.xml b/jetty-alpn/jetty-alpn-java-client/pom.xml index bdca9c57bf11..bb0ebdefc79d 100644 --- a/jetty-alpn/jetty-alpn-java-client/pom.xml +++ b/jetty-alpn/jetty-alpn-java-client/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-alpn/jetty-alpn-java-server/pom.xml b/jetty-alpn/jetty-alpn-java-server/pom.xml index 4cfdc85f5e2a..2cebd2307d3d 100644 --- a/jetty-alpn/jetty-alpn-java-server/pom.xml +++ b/jetty-alpn/jetty-alpn-java-server/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-alpn/jetty-alpn-openjdk8-client/pom.xml b/jetty-alpn/jetty-alpn-openjdk8-client/pom.xml index 07e3649079b5..0590cf9994ff 100644 --- a/jetty-alpn/jetty-alpn-openjdk8-client/pom.xml +++ b/jetty-alpn/jetty-alpn-openjdk8-client/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-alpn/jetty-alpn-openjdk8-server/pom.xml b/jetty-alpn/jetty-alpn-openjdk8-server/pom.xml index e7b17cac0ab4..d4724682e96c 100644 --- a/jetty-alpn/jetty-alpn-openjdk8-server/pom.xml +++ b/jetty-alpn/jetty-alpn-openjdk8-server/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-alpn/jetty-alpn-server/pom.xml b/jetty-alpn/jetty-alpn-server/pom.xml index 30095f367236..e77a402f56b9 100644 --- a/jetty-alpn/jetty-alpn-server/pom.xml +++ b/jetty-alpn/jetty-alpn-server/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-alpn-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-alpn-server diff --git a/jetty-alpn/pom.xml b/jetty-alpn/pom.xml index ad4e8c5328b1..757cf8c01703 100644 --- a/jetty-alpn/pom.xml +++ b/jetty-alpn/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-alpn-parent diff --git a/jetty-annotations/pom.xml b/jetty-annotations/pom.xml index d9a27c8713ec..e85a86247f3a 100644 --- a/jetty-annotations/pom.xml +++ b/jetty-annotations/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-annotations Jetty :: Servlet Annotations Annotation support for deploying servlets in jetty. - http://www.eclipse.org/jetty ${project.groupId}.annotations diff --git a/jetty-annotations/src/main/java/org/eclipse/jetty/annotations/WebListenerAnnotation.java b/jetty-annotations/src/main/java/org/eclipse/jetty/annotations/WebListenerAnnotation.java index dc151ff3f1d8..794764cbd7b9 100644 --- a/jetty-annotations/src/main/java/org/eclipse/jetty/annotations/WebListenerAnnotation.java +++ b/jetty-annotations/src/main/java/org/eclipse/jetty/annotations/WebListenerAnnotation.java @@ -23,6 +23,7 @@ import javax.servlet.ServletContextListener; import javax.servlet.ServletRequestAttributeListener; import javax.servlet.ServletRequestListener; +import javax.servlet.annotation.WebListener; import javax.servlet.http.HttpSessionAttributeListener; import javax.servlet.http.HttpSessionIdListener; import javax.servlet.http.HttpSessionListener; @@ -84,6 +85,7 @@ public void apply() ListenerHolder h = _context.getServletHandler().newListenerHolder(new Source(Source.Origin.ANNOTATION, clazz.getName())); h.setHeldClass(clazz); _context.getServletHandler().addListener(h); + metaData.setOrigin(clazz.getName() + ".listener", clazz.getAnnotation(WebListener.class), clazz); } } else diff --git a/jetty-ant/pom.xml b/jetty-ant/pom.xml index 1bd543e8da47..30740a93145c 100644 --- a/jetty-ant/pom.xml +++ b/jetty-ant/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-ant diff --git a/jetty-bom/pom.xml b/jetty-bom/pom.xml index 093889dc5e29..8ef029b4785a 100644 --- a/jetty-bom/pom.xml +++ b/jetty-bom/pom.xml @@ -3,13 +3,13 @@ jetty-bom Jetty :: Bom Jetty BOM artifact - http://www.eclipse.org/jetty + https://eclipse.org/jetty pom org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT @@ -53,336 +53,336 @@ org.eclipse.jetty apache-jsp - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty apache-jstl - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-java-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-java-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-openjdk8-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-openjdk8-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-conscrypt-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-conscrypt-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-alpn-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-annotations - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-ant - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-continuation - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-deploy - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-distribution - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT zip org.eclipse.jetty jetty-distribution - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT tar.gz org.eclipse.jetty.fcgi fcgi-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.fcgi fcgi-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.gcloud jetty-gcloud-session-manager - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-home - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT zip org.eclipse.jetty jetty-home - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT tar.gz org.eclipse.jetty jetty-http - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.http2 http2-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.http2 http2-common - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.http2 http2-hpack - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.http2 http2-http-client-transport - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.http2 http2-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-http-spi - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty infinispan-common - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty infinispan-remote-query - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty infinispan-embedded-query - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-hazelcast - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-io - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-jaas - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-jaspi - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-jmx - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-jndi - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.memcached jetty-memcached-sessions - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-nosql - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.osgi jetty-osgi-boot - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.osgi jetty-osgi-boot-jsp - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.osgi jetty-osgi-boot-warurl - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.osgi jetty-httpservice - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-plus - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-proxy - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-quickstart - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-rewrite - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-security - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-openid - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-servlet - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-servlets - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-spring - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-unixsocket - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-util - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-util-ajax - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-webapp - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.websocket javax-websocket-client-impl - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.websocket javax-websocket-server-impl - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.websocket websocket-api - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.websocket websocket-client - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.websocket websocket-common - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.websocket websocket-server - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty.websocket websocket-servlet - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT org.eclipse.jetty jetty-xml - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT diff --git a/jetty-cdi/pom.xml b/jetty-cdi/pom.xml index f1dd8a4b8a19..33f2b9955b31 100644 --- a/jetty-cdi/pom.xml +++ b/jetty-cdi/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 org.eclipse.jetty jetty-cdi Jetty :: CDI - http://www.eclipse.org/jetty jar ${project.groupId}.cdi diff --git a/jetty-client/pom.xml b/jetty-client/pom.xml index 61ae6b802c23..88f2cff93365 100644 --- a/jetty-client/pom.xml +++ b/jetty-client/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-client Jetty :: Asynchronous HTTP Client - http://www.eclipse.org/jetty ${project.groupId}.client target/test-policy @@ -121,7 +120,7 @@ org.apache.kerby kerb-simplekdc - 1.1.1 + 2.0.1 test diff --git a/jetty-client/src/main/java/org/eclipse/jetty/client/HttpExchange.java b/jetty-client/src/main/java/org/eclipse/jetty/client/HttpExchange.java index 94d204fe5594..f90feaa12155 100644 --- a/jetty-client/src/main/java/org/eclipse/jetty/client/HttpExchange.java +++ b/jetty-client/src/main/java/org/eclipse/jetty/client/HttpExchange.java @@ -290,11 +290,11 @@ public String toString() { synchronized (this) { - return String.format("%s@%x req=%s/%s@%h res=%s/%s@%h", + return String.format("%s@%x{req=%s[%s/%s] res=%s[%s/%s]}", HttpExchange.class.getSimpleName(), hashCode(), - requestState, requestFailure, requestFailure, - responseState, responseFailure, responseFailure); + request, requestState, requestFailure, + response, responseState, responseFailure); } } diff --git a/jetty-client/src/main/java/org/eclipse/jetty/client/HttpReceiver.java b/jetty-client/src/main/java/org/eclipse/jetty/client/HttpReceiver.java index 271273887685..35df5596fdcc 100644 --- a/jetty-client/src/main/java/org/eclipse/jetty/client/HttpReceiver.java +++ b/jetty-client/src/main/java/org/eclipse/jetty/client/HttpReceiver.java @@ -187,7 +187,7 @@ protected boolean responseBegin(HttpExchange exchange) { handlerListener = protocolHandler.getResponseListener(); if (LOG.isDebugEnabled()) - LOG.debug("Found protocol handler {}", protocolHandler); + LOG.debug("Response {} found protocol handler {}", response, protocolHandler); } exchange.getConversation().updateResponseListeners(handlerListener); @@ -218,19 +218,8 @@ protected boolean responseBegin(HttpExchange exchange) */ protected boolean responseHeader(HttpExchange exchange, HttpField field) { - while (true) - { - ResponseState current = responseState.get(); - if (current == ResponseState.BEGIN || current == ResponseState.HEADER) - { - if (updateResponseState(current, ResponseState.TRANSIENT)) - break; - } - else - { - return false; - } - } + if (!updateResponseState(ResponseState.BEGIN, ResponseState.HEADER, ResponseState.TRANSIENT)) + return false; HttpResponse response = exchange.getResponse(); ResponseNotifier notifier = getHttpDestination().getResponseNotifier(); @@ -296,19 +285,8 @@ protected void storeCookie(URI uri, HttpField field) */ protected boolean responseHeaders(HttpExchange exchange) { - while (true) - { - ResponseState current = responseState.get(); - if (current == ResponseState.BEGIN || current == ResponseState.HEADER) - { - if (updateResponseState(current, ResponseState.TRANSIENT)) - break; - } - else - { - return false; - } - } + if (!updateResponseState(ResponseState.BEGIN, ResponseState.HEADER, ResponseState.TRANSIENT)) + return false; HttpResponse response = exchange.getResponse(); if (LOG.isDebugEnabled()) @@ -342,7 +320,7 @@ protected boolean responseHeaders(HttpExchange exchange) { boolean hasDemand = hasDemandOrStall(); if (LOG.isDebugEnabled()) - LOG.debug("Response headers {}, hasDemand={}", response, hasDemand); + LOG.debug("Response headers hasDemand={} {}", hasDemand, response); return hasDemand; } @@ -363,71 +341,39 @@ protected boolean responseHeaders(HttpExchange exchange) */ protected boolean responseContent(HttpExchange exchange, ByteBuffer buffer, Callback callback) { - while (true) - { - ResponseState current = responseState.get(); - if (current == ResponseState.HEADERS || current == ResponseState.CONTENT) - { - if (updateResponseState(current, ResponseState.TRANSIENT)) - break; - } - else - { - callback.failed(new IllegalStateException("Invalid response state " + current)); - return false; - } - } - - boolean proceed = true; + if (LOG.isDebugEnabled()) + LOG.debug("Response content {}{}{}", exchange.getResponse(), System.lineSeparator(), BufferUtil.toDetailString(buffer)); if (demand() <= 0) { callback.failed(new IllegalStateException("No demand for response content")); - proceed = false; + return false; } + if (decoder == null) + return plainResponseContent(exchange, buffer, callback); + else + return decodeResponseContent(buffer, callback); + } - HttpResponse response = exchange.getResponse(); - if (proceed) + private boolean plainResponseContent(HttpExchange exchange, ByteBuffer buffer, Callback callback) + { + if (!updateResponseState(ResponseState.HEADERS, ResponseState.CONTENT, ResponseState.TRANSIENT)) { - if (LOG.isDebugEnabled()) - LOG.debug("Response content {}{}{}", response, System.lineSeparator(), BufferUtil.toDetailString(buffer)); - if (contentListeners.isEmpty()) - { - callback.succeeded(); - } - else - { - if (decoder == null) - { - contentListeners.notifyContent(response, buffer, callback); - } - else - { - try - { - proceed = decoder.decode(buffer, callback); - } - catch (Throwable x) - { - callback.failed(x); - proceed = false; - } - } - } + callback.failed(new IllegalStateException("Invalid response state " + responseState)); + return false; } + HttpResponse response = exchange.getResponse(); + if (contentListeners.isEmpty()) + callback.succeeded(); + else + contentListeners.notifyContent(response, buffer, callback); + if (updateResponseState(ResponseState.TRANSIENT, ResponseState.CONTENT)) { - if (proceed) - { - boolean hasDemand = hasDemandOrStall(); - if (LOG.isDebugEnabled()) - LOG.debug("Response content {}, hasDemand={}", response, hasDemand); - return hasDemand; - } - else - { - return false; - } + boolean hasDemand = hasDemandOrStall(); + if (LOG.isDebugEnabled()) + LOG.debug("Response content {}, hasDemand={}", response, hasDemand); + return hasDemand; } dispose(); @@ -435,6 +381,11 @@ protected boolean responseContent(HttpExchange exchange, ByteBuffer buffer, Call return false; } + private boolean decodeResponseContent(ByteBuffer buffer, Callback callback) + { + return decoder.decode(buffer, callback); + } + /** * Method to be invoked when the response is successful. *

@@ -614,15 +565,42 @@ public boolean abort(HttpExchange exchange, Throwable failure) } } + private boolean updateResponseState(ResponseState from1, ResponseState from2, ResponseState to) + { + while (true) + { + ResponseState current = responseState.get(); + if (current == from1 || current == from2) + { + if (updateResponseState(current, to)) + return true; + } + else + { + if (LOG.isDebugEnabled()) + LOG.debug("State update failed: [{},{}] -> {}: {}", from1, from2, to, current); + return false; + } + } + } + private boolean updateResponseState(ResponseState from, ResponseState to) { - boolean updated = responseState.compareAndSet(from, to); - if (!updated) + while (true) { - if (LOG.isDebugEnabled()) - LOG.debug("State update failed: {} -> {}: {}", from, to, responseState.get()); + ResponseState current = responseState.get(); + if (current == from) + { + if (responseState.compareAndSet(current, to)) + return true; + } + else + { + if (LOG.isDebugEnabled()) + LOG.debug("State update failed: {} -> {}: {}", from, to, current); + return false; + } } - return updated; } @Override @@ -778,14 +756,62 @@ private Decoder(HttpExchange exchange, ContentDecoder decoder) private boolean decode(ByteBuffer encoded, Callback callback) { + // Store the buffer to decode in case the + // decoding produces multiple decoded buffers. this.encoded = encoded; this.callback = callback; - return decode(); + + HttpResponse response = exchange.getResponse(); + if (LOG.isDebugEnabled()) + LOG.debug("Response content decoding {} with {}{}{}", response, decoder, System.lineSeparator(), BufferUtil.toDetailString(encoded)); + + boolean needInput = decode(); + if (!needInput) + return false; + + boolean hasDemand = hasDemandOrStall(); + if (LOG.isDebugEnabled()) + LOG.debug("Response content decoded, hasDemand={} {}", hasDemand, response); + return hasDemand; } private boolean decode() { while (true) + { + if (!updateResponseState(ResponseState.HEADERS, ResponseState.CONTENT, ResponseState.TRANSIENT)) + { + callback.failed(new IllegalStateException("Invalid response state " + responseState)); + return false; + } + + DecodeResult result = decodeChunk(); + + if (updateResponseState(ResponseState.TRANSIENT, ResponseState.CONTENT)) + { + if (result == DecodeResult.NEED_INPUT) + return true; + if (result == DecodeResult.ABORT) + return false; + + boolean hasDemand = hasDemandOrStall(); + if (LOG.isDebugEnabled()) + LOG.debug("Response content decoded chunk, hasDemand={} {}", hasDemand, exchange.getResponse()); + if (hasDemand) + continue; + else + return false; + } + + dispose(); + terminateResponse(exchange); + return false; + } + } + + private DecodeResult decodeChunk() + { + try { ByteBuffer buffer; while (true) @@ -798,27 +824,30 @@ private boolean decode() callback.succeeded(); encoded = null; callback = null; - return true; + return DecodeResult.NEED_INPUT; } } + ByteBuffer decoded = buffer; + HttpResponse response = exchange.getResponse(); if (LOG.isDebugEnabled()) - LOG.debug("Response content decoded ({}) {}{}{}", decoder, exchange, System.lineSeparator(), BufferUtil.toDetailString(decoded)); + LOG.debug("Response content decoded chunk {}{}{}", response, System.lineSeparator(), BufferUtil.toDetailString(decoded)); - contentListeners.notifyContent(exchange.getResponse(), decoded, Callback.from(() -> decoder.release(decoded), callback::failed)); + contentListeners.notifyContent(response, decoded, Callback.from(() -> decoder.release(decoded), callback::failed)); - boolean hasDemand = hasDemandOrStall(); - if (LOG.isDebugEnabled()) - LOG.debug("Response content decoded {}, hasDemand={}", exchange, hasDemand); - if (!hasDemand) - return false; + return DecodeResult.DECODE; + } + catch (Throwable x) + { + callback.failed(x); + return DecodeResult.ABORT; } } private void resume() { if (LOG.isDebugEnabled()) - LOG.debug("Response content resuming decoding {}", exchange); + LOG.debug("Response content resume decoding {} with {}", exchange.getResponse(), decoder); // The content and callback may be null // if there is no initial content demand. @@ -828,40 +857,9 @@ private void resume() return; } - while (true) - { - ResponseState current = responseState.get(); - if (current == ResponseState.HEADERS || current == ResponseState.CONTENT) - { - if (updateResponseState(current, ResponseState.TRANSIENT)) - break; - } - else - { - callback.failed(new IllegalStateException("Invalid response state " + current)); - return; - } - } - - boolean decoded = false; - try - { - decoded = decode(); - } - catch (Throwable x) - { - callback.failed(x); - } - - if (updateResponseState(ResponseState.TRANSIENT, ResponseState.CONTENT)) - { - if (decoded) - receive(); - return; - } - - dispose(); - terminateResponse(exchange); + boolean needInput = decode(); + if (needInput) + receive(); } @Override @@ -871,4 +869,9 @@ public void destroy() ((Destroyable)decoder).destroy(); } } + + private enum DecodeResult + { + DECODE, NEED_INPUT, ABORT + } } diff --git a/jetty-client/src/main/java/org/eclipse/jetty/client/http/HttpReceiverOverHTTP.java b/jetty-client/src/main/java/org/eclipse/jetty/client/http/HttpReceiverOverHTTP.java index 9dae09c1d51d..c06a609a6977 100644 --- a/jetty-client/src/main/java/org/eclipse/jetty/client/http/HttpReceiverOverHTTP.java +++ b/jetty-client/src/main/java/org/eclipse/jetty/client/http/HttpReceiverOverHTTP.java @@ -47,6 +47,7 @@ public class HttpReceiverOverHTTP extends HttpReceiver implements HttpParser.Res private boolean shutdown; private boolean complete; private boolean unsolicited; + private int status; public HttpReceiverOverHTTP(HttpChannelOverHTTP channel) { @@ -118,15 +119,17 @@ private void releaseNetworkBuffer() protected ByteBuffer onUpgradeFrom() { + ByteBuffer upgradeBuffer = null; if (networkBuffer.hasRemaining()) { - ByteBuffer upgradeBuffer = BufferUtil.allocate(networkBuffer.remaining()); + upgradeBuffer = BufferUtil.allocate(networkBuffer.remaining()); BufferUtil.clearToFill(upgradeBuffer); BufferUtil.put(networkBuffer.getBuffer(), upgradeBuffer); BufferUtil.flipToFlush(upgradeBuffer, 0); - return upgradeBuffer; } - return null; + + releaseNetworkBuffer(); + return upgradeBuffer; } private void process() @@ -145,12 +148,11 @@ private void process() return; } - // Connection may be closed or upgraded in a parser callback. - boolean upgraded = connection != endPoint.getConnection(); - if (connection.isClosed() || upgraded) + // Connection may be closed in a parser callback. + if (connection.isClosed()) { if (LOG.isDebugEnabled()) - LOG.debug("{} {}", upgraded ? "Upgraded" : "Closed", connection); + LOG.debug("Closed {}", connection); releaseNetworkBuffer(); return; } @@ -215,6 +217,14 @@ private boolean parse() if (LOG.isDebugEnabled()) LOG.debug("Parse complete={}, remaining {} {}", complete, networkBuffer.remaining(), parser); + if (complete) + { + int status = this.status; + this.status = 0; + if (status == HttpStatus.SWITCHING_PROTOCOLS_101) + return true; + } + if (networkBuffer.isEmpty()) return false; @@ -269,6 +279,7 @@ public boolean startResponse(HttpVersion version, int status, String reason) if (exchange == null) return false; + this.status = status; String method = exchange.getRequest().getMethod(); parser.setHeadResponse(HttpMethod.HEAD.is(method) || (HttpMethod.CONNECT.is(method) && status == HttpStatus.OK_200)); diff --git a/jetty-client/src/test/java/org/eclipse/jetty/client/HttpClientGZIPTest.java b/jetty-client/src/test/java/org/eclipse/jetty/client/HttpClientGZIPTest.java index e29f0a3b573a..3120a97619d9 100644 --- a/jetty-client/src/test/java/org/eclipse/jetty/client/HttpClientGZIPTest.java +++ b/jetty-client/src/test/java/org/eclipse/jetty/client/HttpClientGZIPTest.java @@ -20,6 +20,7 @@ import java.io.ByteArrayOutputStream; import java.io.IOException; +import java.io.InputStream; import java.io.InterruptedIOException; import java.nio.charset.StandardCharsets; import java.util.Arrays; @@ -32,11 +33,14 @@ import javax.servlet.http.HttpServletResponse; import org.eclipse.jetty.client.api.ContentResponse; +import org.eclipse.jetty.client.api.Response; +import org.eclipse.jetty.client.util.InputStreamResponseListener; import org.eclipse.jetty.http.HttpHeader; import org.eclipse.jetty.http.HttpStatus; import org.eclipse.jetty.io.ByteBufferPool; import org.eclipse.jetty.io.MappedByteBufferPool; import org.eclipse.jetty.server.Request; +import org.eclipse.jetty.util.IO; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.ArgumentsSource; @@ -266,6 +270,47 @@ protected void service(String target, Request jettyRequest, HttpServletRequest r assertThat(heapMemory, lessThan((long)content.length)); } + @ParameterizedTest + @ArgumentsSource(ScenarioProvider.class) + public void testLargeGZIPContentAsync(Scenario scenario) throws Exception + { + String digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; + Random random = new Random(); + byte[] content = new byte[32 * 1024 * 1024]; + for (int i = 0; i < content.length; ++i) + { + content[i] = (byte)digits.charAt(random.nextInt(digits.length())); + } + start(scenario, new EmptyServerHandler() + { + @Override + protected void service(String target, Request jettyRequest, HttpServletRequest request, HttpServletResponse response) throws IOException + { + response.setContentType("text/plain;charset=" + StandardCharsets.US_ASCII.name()); + response.setHeader(HttpHeader.CONTENT_ENCODING.asString(), "gzip"); + GZIPOutputStream gzip = new GZIPOutputStream(response.getOutputStream()); + gzip.write(content); + gzip.finish(); + } + }); + + InputStreamResponseListener listener = new InputStreamResponseListener(); + client.newRequest("localhost", connector.getLocalPort()) + .scheme(scenario.getScheme()) + .timeout(5, TimeUnit.SECONDS) + .send(listener); + + Response response = listener.get(5, TimeUnit.SECONDS); + assertEquals(HttpStatus.OK_200, response.getStatus()); + + ByteArrayOutputStream output = new ByteArrayOutputStream(); + try (InputStream input = listener.getInputStream()) + { + IO.copy(input, output); + } + assertArrayEquals(content, output.toByteArray()); + } + private static void sleep(long ms) throws IOException { try diff --git a/jetty-continuation/pom.xml b/jetty-continuation/pom.xml index 72bef742af00..bef7cfe39e50 100644 --- a/jetty-continuation/pom.xml +++ b/jetty-continuation/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-continuation Jetty :: Continuation Asynchronous API - http://www.eclipse.org/jetty ${project.groupId}.continuation diff --git a/jetty-deploy/pom.xml b/jetty-deploy/pom.xml index 58afdbdd869c..a43dfed05458 100644 --- a/jetty-deploy/pom.xml +++ b/jetty-deploy/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-deploy Jetty :: Deployers Jetty deployers - http://www.eclipse.org/jetty ${project.groupId}.deploy diff --git a/jetty-distribution/pom.xml b/jetty-distribution/pom.xml index 8696feecec9e..8884ac22f6de 100644 --- a/jetty-distribution/pom.xml +++ b/jetty-distribution/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-distribution diff --git a/jetty-distribution/src/main/resources/README.TXT b/jetty-distribution/src/main/resources/README.TXT index 4f9d64bcacd0..7c0dba2253e7 100644 --- a/jetty-distribution/src/main/resources/README.TXT +++ b/jetty-distribution/src/main/resources/README.TXT @@ -4,7 +4,7 @@ JETTY The Jetty project is a 100% Java HTTP Server, HTTP Client and Servlet Container from the eclipse foundation - http://www.eclipse.org/jetty/ + https://www.eclipse.org/jetty/ Jetty is open source and is dual licensed using the Apache 2.0 and Eclipse Public License 1.0. You may choose either license when diff --git a/jetty-distribution/src/main/resources/demo-base/webapps/ROOT/index.html b/jetty-distribution/src/main/resources/demo-base/webapps/ROOT/index.html index 87e0fd2a7d1d..9c4613995129 100644 --- a/jetty-distribution/src/main/resources/demo-base/webapps/ROOT/index.html +++ b/jetty-distribution/src/main/resources/demo-base/webapps/ROOT/index.html @@ -16,13 +16,14 @@

Welcome to Jetty 9

- The Jetty project is a 100% Java Servlet - Container which supports asynchronous server and client - implementations of the HTTP, - Websocket and HTTP/2 protocols. The - project is 100% Open Source and hosted by the Eclipse Foundation at http://www.eclipse.org/jetty. + The Jetty project is a 100% Java Servlet + Container which supports asynchronous server and client + implementations of the HTTP, + Websocket and HTTP/2 protocols. The + project is 100% Open Source and hosted by the + Eclipse Foundation at https://www.eclipse.org/jetty/.

@@ -42,22 +43,21 @@

tests ...

information ...

- +

getting help ...

- + diff --git a/jetty-distribution/src/main/resources/start.ini b/jetty-distribution/src/main/resources/start.ini index bd7e62c583ab..83189279f91e 100644 --- a/jetty-distribution/src/main/resources/start.ini +++ b/jetty-distribution/src/main/resources/start.ini @@ -7,7 +7,7 @@ # of making changes to this {jetty.home} directory. # # See documentation about {jetty.base} at -# http://www.eclipse.org/jetty/documentation/current/startup.html +# https://www.eclipse.org/jetty/documentation/current/startup.html # # A demo-base directory has been provided as an example of # this sort of setup. diff --git a/jetty-documentation/pom.xml b/jetty-documentation/pom.xml index 92572588188b..01d4f05f4126 100644 --- a/jetty-documentation/pom.xml +++ b/jetty-documentation/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT jetty-documentation Jetty :: Documentation @@ -59,8 +59,8 @@ true true ${project.version} - http://www.eclipse.org/jetty/javadoc/${javadoc.version} - http://download.eclipse.org/jetty/stable-9/xref + https://eclipse.org/jetty/javadoc/${javadoc.version} + https://download.eclipse.org/jetty/stable-9/xref ${basedir}/.. https://github.com/eclipse/jetty.project/tree/jetty-9.4.x https://repo1.maven.org/maven2 @@ -223,10 +223,10 @@ true true ${project.version} - http://download.eclipse.org/jetty/stable-9/apidocs - http://download.eclipse.org/jetty/stable-9/xref + https://download.eclipse.org/jetty/stable-9/apidocs + https://download.eclipse.org/jetty/stable-9/xref ${basedir}/../jetty.project/ - https://github.com/eclipse/jetty.project/master + https://github.com/eclipse/jetty.project/tree/jetty-9.4.x font diff --git a/jetty-documentation/src/main/asciidoc/administration/extras/statistics-handler.adoc b/jetty-documentation/src/main/asciidoc/administration/extras/statistics-handler.adoc index c342ab7436d7..39a06d1b5738 100644 --- a/jetty-documentation/src/main/asciidoc/administration/extras/statistics-handler.adoc +++ b/jetty-documentation/src/main/asciidoc/administration/extras/statistics-handler.adoc @@ -29,83 +29,79 @@ [[statistics-handler-usage]] ==== Usage -Jetty currently has two levels of request statistic collection: +Jetty currently has two main statistics collection mechanisms: -* Subclasses of `AbstractConnector` class optionally can collect statistics about connections as well as number of requests. -* The `StatisticsHandler` class may be used to collect request statistics. +* Instances of `ConnectionStatistics` can collect statistics for each connection of a connector. +* The `StatisticsHandler` class may be used to collect statistics for HTTP requests. -In addition to these, subclasses of the `SessionHandler` and `DefaultSessionCache` classes optionally can collect session statistics. +The `StatisticsHandler` and `ConnectionStatistics` are not included in the default Jetty configuration, these need to be configured manually or enabled using the Jetty `stats` module on the command line. +[source, screen, subs="{sub-order}"] +.... +$ java -jar {$jetty.home}/start.jar --add-to-start=stats +.... -`AbstractConnector`, `SessionHandler` and `DefaultSessionCache` statistics are turned off by default and must either be configured manually for each instance or turned on via JMX interface. -The `StatisticsHandler` is not included in default Jetty configuration, and needs to be configured manually. +In addition to these, the `SessionHandler` and `DefaultSessionCache` classes collect statistics for sessions. +These statistics are enabled by default and are accessible via JMX interface. _____ [NOTE] To view statistics, you have to be able to connect to Jetty using either JConsole or some other JMX agent. See xref:using-jmx[] for more information. _____ -[[connector-statistics]] -==== Connector statistics +[[request-statistics]] +==== Request Statistics -Detailed statistics on connection duration and number of requests are only collated when a connection is closed. -The current and maximum number of connections are the only "live" statistics. -//To learn how to turn on connector statistics please see the Jetty Statistics tutorial, although this is not recommended and it is best to use a JMX agent to select statistics only when needed. +To collect request statistics a `StatisticsHandler` must be configured as one of the handlers of the server. +Typically this can be done as the top level handler, but you may choose to configure a statistics handler for just one context by creating a context configuration file. +You can enable the `StatisticsHandler` by activating the `stats` modules on the command line. -The following example shows how to turn on connector statistics in Jetty xml. -This example comes from within `jetty-http.xml`. +Alternately, if you are making multiple changes to the Jetty configuration, you could include statistics handler configuration into your own Jetty xml configuration. +The following fragment shows how to configure a top level statistics handler: [source, xml, subs="{sub-order}"] ---- - + + - - - - - - - - - - - - - - 30000 - - - - - - - + + ---- -[[request-statistics]] -==== Request Statistics +[[connection-statistics]] +==== Connection Statistics -To collect request statistics a `StatisticsHandler` must be configured as one of the handlers of the server. -Typically this can be done as the top level handler, but you may choose to configure a statistics handler for just one context by creating a context configuration file. -You can enable the `StatisticsHandler` by activating the `stats` modules on the command line. +Detailed statistics on connection duration and number of messages are only collated when a connection is closed. +The current and maximum number of connections are the only "live" statistics. -[source, screen, subs="{sub-order}"] -.... -$ java -jar {$jetty.home}/start.jar --add-to-start=stats -.... +The following example shows how to turn on connection statistics in the Jetty XML format. -Alternately, if you are making multiple changes to the Jetty configuration, you could include statistics handler configuration into your own Jetty xml configuration. -The following fragment shows how to configure a top level statistics handler: +[source, xml, subs="{sub-order}"] +---- + + + + + + + +---- + +A special variant of `ConnectionStatistics` called `IncludeExcludeConnectionStatistics` allows you to refine which types of connection you want to collect statistics for. +The following example shows how this can be used to record statistics only for WebSocket connections. [source, xml, subs="{sub-order}"] ---- - - - - - - + + + + + + + + + ---- [[session-statistics]] diff --git a/jetty-documentation/src/main/asciidoc/administration/startup/images/modules-9.3-simplified.dot b/jetty-documentation/src/main/asciidoc/administration/startup/images/modules-9.3-simplified.dot index ecc2962020be..dfa40ef487b3 100644 --- a/jetty-documentation/src/main/asciidoc/administration/startup/images/modules-9.3-simplified.dot +++ b/jetty-documentation/src/main/asciidoc/administration/startup/images/modules-9.3-simplified.dot @@ -1,7 +1,7 @@ /* * GraphViz Graph of Jetty Modules * - * Jetty: http://eclipse.org/jetty/ + * Jetty: https://eclipse.org/jetty/ * GraphViz: http://graphviz.org/ * * To Generate Graph image using graphviz: diff --git a/jetty-documentation/src/main/asciidoc/configuring/security/jaas-support.adoc b/jetty-documentation/src/main/asciidoc/configuring/security/jaas-support.adoc index 3d9cc8b9ec7b..9e4c311dc92b 100644 --- a/jetty-documentation/src/main/asciidoc/configuring/security/jaas-support.adoc +++ b/jetty-documentation/src/main/asciidoc/configuring/security/jaas-support.adoc @@ -411,4 +411,4 @@ public class FooLoginModule extends AbstractLoginModule An example webapp using JAAS can be found in the Jetty GitHub repository: -* link:{GITBROWSEURL}/tests/test-webapps/test-jaas-webapp[https://github.com/eclipse/jetty.project/tree/master/tests/test-webapps/test-jaas-webapp] +* link:{GITBROWSEURL}/tests/test-webapps/test-jaas-webapp[https://github.com/eclipse/jetty.project/tree/jetty-9.4.x/tests/test-webapps/test-jaas-webapp] diff --git a/jetty-documentation/src/main/asciidoc/configuring/security/jetty-home-and-jetty-base.adoc b/jetty-documentation/src/main/asciidoc/configuring/security/jetty-home-and-jetty-base.adoc index 4f17253d3c6e..96e7f9acb5e4 100644 --- a/jetty-documentation/src/main/asciidoc/configuring/security/jetty-home-and-jetty-base.adoc +++ b/jetty-documentation/src/main/asciidoc/configuring/security/jetty-home-and-jetty-base.adoc @@ -65,18 +65,20 @@ Adding modules in this way will append the associated module properties to the ` .... [my-base]$ java -jar /home/user/jetty-distribution-{VERSION}/start.jar --add-to-start=http,https,deploy -ssl initialised in ${jetty.base}/start.ini (appended) -ssl enabled in ${jetty.base}/start.ini -DOWNLOAD: https://github.com/eclipse/jetty.project/raw/master/jetty-server/src/main/config/etc/keystore to etc/keystore -server initialised in ${jetty.base}/start.ini (appended) -server enabled in ${jetty.base}/start.ini -http initialised in ${jetty.base}/start.ini (appended) -http enabled in ${jetty.base}/start.ini -server enabled in ${jetty.base}/start.ini -deploy initialised in ${jetty.base}/start.ini (appended) -deploy enabled in ${jetty.base}/start.ini -MKDIR: ${jetty.base}/webapps -server enabled in ${jetty.base}/start.ini +INFO : webapp transitively enabled, ini template available with --add-to-start=webapp +INFO : server transitively enabled, ini template available with --add-to-start=server +INFO : security transitively enabled +INFO : servlet transitively enabled +INFO : http initialized in ${jetty.base}/start.ini +INFO : https initialized in ${jetty.base}/start.ini +INFO : threadpool transitively enabled, ini template available with --add-to-start=threadpool +INFO : ssl transitively enabled, ini template available with --add-to-start=ssl +INFO : bytebufferpool transitively enabled, ini template available with --add-to-start=bytebufferpool +INFO : deploy initialized in ${jetty.base}/start.ini +MKDIR : ${jetty.base}/etc +COPY : ${jetty.home}/modules/ssl/keystore to ${jetty.base}/etc/keystore +MKDIR : ${jetty.base}/webapps +INFO : Base directory was modified .... 3. Look at your directory. + diff --git a/jetty-documentation/src/main/asciidoc/development/continuations/continuations-patterns.adoc b/jetty-documentation/src/main/asciidoc/development/continuations/continuations-patterns.adoc index 5911afdea643..22107b3651b1 100644 --- a/jetty-documentation/src/main/asciidoc/development/continuations/continuations-patterns.adoc +++ b/jetty-documentation/src/main/asciidoc/development/continuations/continuations-patterns.adoc @@ -104,7 +104,8 @@ If many responses are to be sent (e.g., a chat room), then writing one response ==== Examples -* The https://github.com/eclipse/jetty.project/blob/jetty-8/test-jetty-webapp/src/main/java/com/acme/ChatServlet.java[ChatServlet example] shows how the suspend/resume style can be used to directly code a chat room (See similar https://github.com/eclipse/jetty.project/blob/master/tests/test-webapps/test-jetty-webapp/src/main/java/com/acme/ChatServlet.java[example] using Async Servlets). +* The https://github.com/eclipse/jetty.project/blob/jetty-9.4.x/tests/test-webapps/test-jetty-webapp/src/main/java/com/acme/ChatServlet.java[ChatServlet example] +shows how to make a chat room using Async Servlets. The same principles are applied to frameworks like http://cometd.org/[cometd] which provide an richer environment for such applications, based on Continuations. * The link:{JDURL}/org/eclipse/jetty/servlets/QoSFilter.html[QoSFilter] uses suspend/resume style to limit the number of requests simultaneously within the filter. diff --git a/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-deploying.adoc b/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-deploying.adoc index 2a8e10bd71b0..87ebcfe58e8f 100644 --- a/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-deploying.adoc +++ b/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-deploying.adoc @@ -40,33 +40,33 @@ If you have a standard web application, you can hot deploy it into Jetty by copy The demo-base/webapps directory contains the following deployable and auxiliary files: `ROOT/`:: - A directory of static content that is deployed to the root context / due to it's name. - Contains the Jetty demo welcome page. +A directory of static content that is deployed to the root context / due to it's name. +Contains the Jetty demo welcome page. `test.d`:: - A directory containing additional configuration files used by `test.xml` to inject extra configuration into `test.war`. +A directory containing additional configuration files used by `test.xml` to inject extra configuration into `test.war`. `test.xml`:: - A context configuration file that configures and deploys `test.war.` - The additional configuration includes the context path as well as setting additional descriptors found in the `test.d` directory. +A context configuration file that configures and deploys `test.war.` +The additional configuration includes the context path as well as setting additional descriptors found in the `test.d` directory. `test.war`:: - The demonstration web application that is configured and deployed by `test.xml`. +The demonstration web application that is configured and deployed by `test.xml`. `async-rest.war`:: - A web application demonstration of asynchronous REST to eBay, automatically deployed to /async-rest based on the file name. +A web application demonstration of asynchronous REST to eBay, automatically deployed to /async-rest based on the file name. `test-jaas.war`:: - A demonstration web application utilizing link:#jaas-support[JAAS] for authentication. +A demonstration web application utilizing link:#jaas-support[JAAS] for authentication. `test-jaas.xml`:: - A context configuration file that configures `test-jaas.war`. - Additional configuration includes setting up the link:#configuring-login-service[LoginService] for authentication and authorization. +A context configuration file that configures `test-jaas.war`. +Additional configuration includes setting up the link:#configuring-login-service[LoginService] for authentication and authorization. `test-jndi.war`:: - A demonstration web application showing the use of link:#jndi[JNDI]. +A demonstration web application showing the use of link:#jndi[JNDI]. `test-jndi.xml`:: - A context configuration file that configures `test-jndi.war`. - Additional configuration includes defining objects in the naming space that can be referenced from the webapp. +A context configuration file that configures `test-jndi.war`. +Additional configuration includes defining objects in the naming space that can be referenced from the webapp. `test-spec.war`:: - A demonstration web application that shows the use of annotations, fragments, `ServletContainerInitializers` and other Servlet Specification 3.0/3.1 features. +A demonstration web application that shows the use of annotations, fragments, `ServletContainerInitializers` and other Servlet Specification 3.0/3.1 features. `test-spec.xml`:: - A context configuration file that configures `test-spec.war`. - Additional configuration includes setting up some objects in the naming space that can be referenced by annotations. +A context configuration file that configures `test-spec.war`. +Additional configuration includes setting up some objects in the naming space that can be referenced by annotations. `javadoc-proxy.war`:: - A demonstration web application that uses a transparent proxy to serve the Jetty source link:{JDURL}/[Javadoc] from the http://www.eclipse.org/jetty[Eclipse Jetty website]. +A demonstration web application that uses a transparent proxy to serve the Jetty source link:{JDURL}/[Javadoc] from the https://www.eclipse.org/jetty/[Eclipse Jetty website]. `example-moved.xml`:: - A demonstration context configuration file that shows how to use the link:#moved-context-handler[`MovedContextHandler`] to redirect from one path to another. +A demonstration context configuration file that shows how to use the link:#moved-context-handler[`MovedContextHandler`] to redirect from one path to another. diff --git a/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-running.adoc b/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-running.adoc index 30e6b55d67c0..7a5228a3be6d 100644 --- a/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-running.adoc +++ b/jetty-documentation/src/main/asciidoc/quick-start/getting-started/jetty-running.adoc @@ -25,11 +25,11 @@ Jetty has no GUI (Graphical User Interface), so running the server and performin Once you have access to your system's command line, navigate to the directory where you unpacked your copy of the Jetty distribution. To start Jetty on the default port of 8080, run the following command: -[source, screen, subs="{sub-order}"] +[source,screen,subs="{sub-order}"] ---- $ java -jar start.jar 2017-09-20 15:45:11.986:INFO::main: Logging initialized @683ms to org.eclipse.jetty.util.log.StdErrLog -2017-09-20 15:45:12.197:WARN:oejs.HomeBaseWarning:main: This instance of Jetty is not running from a separate {jetty.base} directory, this is not recommended. See documentation at http://www.eclipse.org/jetty/documentation/current/startup.html +2017-09-20 15:45:12.197:WARN:oejs.HomeBaseWarning:main: This instance of Jetty is not running from a separate {jetty.base} directory, this is not recommended. See documentation at https://www.eclipse.org/jetty/documentation/current/startup.html 2017-09-20 15:45:12.243:INFO:oejs.Server:main: {VERSION} 2017-09-20 15:45:12.266:INFO:oejdp.ScanningAppProvider:main: Deployment monitor [file:///installs/repository/jetty/webapps/] at interval 1 2017-09-20 15:45:12.298:INFO:oejs.AbstractConnector:main: Started ServerConnector@39c0f4a{HTTP/1.1,[http/1.1]}{0.0.0.0:8080} diff --git a/jetty-documentation/src/main/asciidoc/reference/contributing/chapter.adoc b/jetty-documentation/src/main/asciidoc/reference/contributing/chapter.adoc index 7a2b3e8188ec..0e5c8108cc99 100644 --- a/jetty-documentation/src/main/asciidoc/reference/contributing/chapter.adoc +++ b/jetty-documentation/src/main/asciidoc/reference/contributing/chapter.adoc @@ -28,6 +28,5 @@ include::source-build.adoc[] include::coding-standards.adoc[] include::bugs.adoc[] include::patches.adoc[] -include::security.adoc[] include::releasing-jetty.adoc[] include::release-testing.adoc[] diff --git a/jetty-documentation/src/main/asciidoc/reference/contributing/community.adoc b/jetty-documentation/src/main/asciidoc/reference/contributing/community.adoc index b40dffe75e76..72a396247331 100644 --- a/jetty-documentation/src/main/asciidoc/reference/contributing/community.adoc +++ b/jetty-documentation/src/main/asciidoc/reference/contributing/community.adoc @@ -30,16 +30,16 @@ We have a number of options for people that wish to subscribe to our mailing lis * Jetty Developers List ** Join - https://dev.eclipse.org/mailman/listinfo/jetty-dev -** Archives - http://dev.eclipse.org/mhonarc/lists/jetty-dev/ +** Archives - https://dev.eclipse.org/mhonarc/lists/jetty-dev/ * Jetty Users List ** Join - https://dev.eclipse.org/mailman/listinfo/jetty-users -** Archives - http://dev.eclipse.org/mhonarc/lists/jetty-users/ +** Archives - https://dev.eclipse.org/mhonarc/lists/jetty-users/ * Jetty Announcements List ** Join - https://dev.eclipse.org/mailman/listinfo/jetty-announce -** Archives - http://dev.eclipse.org/mhonarc/lists/jetty-announce/ +** Archives - https://dev.eclipse.org/mhonarc/lists/jetty-announce/ * Jetty Commit List ** Join - https://dev.eclipse.org/mailman/listinfo/jetty-commit -** Archives - http://dev.eclipse.org/mhonarc/lists/jetty-commit/ +** Archives - https://dev.eclipse.org/mhonarc/lists/jetty-commit/ [[community-irc]] ==== Internet Relay Chat - IRC @@ -48,5 +48,5 @@ Much of our conversations about Jetty occur on IRC in one location or another. Users are always welcome to come join our IRC channels and talk with us, other users, or just lurk. irc.freenode.org - #jetty:: - Our primary location, we recommend that if your looking to find folks on IRC you try here. - We also have commit notifications coming to this channel on the bottom and top of the hour. +Our primary location, we recommend that if your looking to find folks on IRC you try here. +We also have commit notifications coming to this channel on the bottom and top of the hour. diff --git a/jetty-documentation/src/main/asciidoc/reference/contributing/releasing-jetty.adoc b/jetty-documentation/src/main/asciidoc/reference/contributing/releasing-jetty.adoc index 5d330353b770..c098790779c9 100644 --- a/jetty-documentation/src/main/asciidoc/reference/contributing/releasing-jetty.adoc +++ b/jetty-documentation/src/main/asciidoc/reference/contributing/releasing-jetty.adoc @@ -230,28 +230,28 @@ These files will then be visible from http://download.eclipse.org/jetty/updates/ [[releasing-documentation]] ==== Release Documentation -There are two git repositories you need to be aware of for releasing jetty-documentation. The jetty-documentation is located in our github repository and the jetty-website is located at eclipse. +There are two git repositories you need to be aware of for releasing jetty-documentation.The jetty-documentation is located in our github repository and the jetty-website is located at eclipse. jetty-documentation:: - https://github.com/jetty-project/jetty-documentation +https://github.com/jetty-project/jetty-documentation jetty-website:: - http://git.eclipse.org/c/www.eclipse.org/jetty.git +http://git.eclipse.org/c/www.eclipse.org/jetty.git Do the following steps to publish documentation for the release: -1. Checkout the jetty-documentation repository. -2. Edit the of the jetty-documentation pom.xml and change it _locally_ to be the release number, eg 9.2.6.v20141205 -3. Build the documentation with mvn clean install -4. Checkout the jetty-website -5. Inside the documentation/ directory, make a directory named the same as the release number, eg 9.2.6.v20141205/ -6. Copy the built `documentation` from jetty-documentation/target/docbkx/html/jetty into the new directory -7. Edit the `index.html` file in the `documentation` directory and add the newly released documentation url. +1. Checkout the jetty-documentation repository. +2. Edit the of the jetty-documentation pom.xml and change it _locally_ to be the release number, eg 9.2.6.v20141205 +3. Build the documentation with mvn clean install +4. Checkout the jetty-website +5. Inside the documentation/ directory, make a directory named the same as the release number, eg 9.2.6.v20141205/ +6. Copy the built `documentation` from jetty-documentation/target/docbkx/html/jetty into the new directory +7. Edit the `index.html` file in the `documentation` directory and add the newly released documentation url. Make sure you follow the other examples and include the `rel="nofollow"` attribute on the link so that search engines do not crawl newly created documentation, otherwise we are subject to duplicate content penalties in SEO. -8. Commit the changes to the jetty-website project +8. Commit the changes to the jetty-website project ____ [NOTE] -There is a separate Jenkins build job that publishes documentation to http://www.eclipse.org/jetty/documentation/current triggered by a push of changed files to the jetty-documentation project. +There is a separate Jenkins build job that publishes documentation to https://www.eclipse.org/jetty/documentation/current triggered by a push of changed files to the jetty-documentation project. If you commit your change to the number from step 2, then these builds will use the same release version number. It is preferable if you _don't_ commit that version number change, or better yet, ensure that it is set to the next -SNAPSHOT version number for your jetty major release number. ____ diff --git a/jetty-documentation/src/main/asciidoc/reference/contributing/security.adoc b/jetty-documentation/src/main/asciidoc/reference/contributing/security.adoc deleted file mode 100644 index aa3c79fb28b8..000000000000 --- a/jetty-documentation/src/main/asciidoc/reference/contributing/security.adoc +++ /dev/null @@ -1,32 +0,0 @@ -// -// ======================================================================== -// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others. -// ======================================================================== -// All rights reserved. This program and the accompanying materials -// are made available under the terms of the Eclipse Public License v1.0 -// and Apache License v2.0 which accompanies this distribution. -// -// The Eclipse Public License is available at -// http://www.eclipse.org/legal/epl-v10.html -// -// The Apache License v2.0 is available at -// http://www.opensource.org/licenses/apache2.0.php -// -// You may elect to redistribute this code under either of these licenses. -// ======================================================================== -// - -[[security-reporting]] -=== Reporting Security Issues - -There are a number of avenues for reporting security issues to the Jetty project available. -If the issue is directly related to Jetty itself then reporting to the Jetty developers is encouraged. -The most direct method is to mail _security@webtide.com_. -Since Webtide is comprised of the active committers of the Jetty project this is our preferred reporting method. -We are generally flexible in how we work with reporters of security issues but we reserve the right to act in the interests of the Jetty project in all circumstances. - -If the issue is related to Eclipse or its Jetty integration then we encourage you to reach out to _security@eclipse.org_. - -If the issue is related to integrations with Jetty we are happy to work with you to identify the proper entity and either of the approaches above is fine. - -We prefer that security issues are reported directly to Jetty developers as opposed through GitHub Issues since it has no facility to tag issues as _private_. diff --git a/jetty-documentation/src/main/asciidoc/reference/troubleshooting/security-reports.adoc b/jetty-documentation/src/main/asciidoc/reference/troubleshooting/security-reports.adoc index 484a3a5dbdf4..a652b69b2812 100644 --- a/jetty-documentation/src/main/asciidoc/reference/troubleshooting/security-reports.adoc +++ b/jetty-documentation/src/main/asciidoc/reference/troubleshooting/security-reports.adoc @@ -19,147 +19,21 @@ [[security-reports]] === Jetty Security Reports -The following sections provide information about Jetty security issues. +==== List of Security Reports -If you would like to report a security issue please follow these link:#security-reporting[instructions]. +A current list of Jetty security reports can be viewed on the link:https://www.eclipse.org/jetty/security-reports.htmlhttps://www.eclipse.org/jetty/security-reports.html[Project Home Page.] -.Resolved Issues -[width="99%",cols="11%,19%,14%,9%,14%,14%,19%",options="header",] -|======================================================================= -|yyyy/mm/dd |ID |Exploitable |Severity |Affects |Fixed Version |Comment +==== Reporting Security Issues -|2019/08/13 |CVE-2019-9518 |Med |Med |< = 9.4.20 |9.4.21 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-9518[Some HTTP/2 implementations are vulnerable to a flood of empty frames, potentially leading to a denial of service.] +There are a number of avenues for reporting security issues to the Jetty project available. -|2019/08/13 |CVE-2019-9516 |Med |Med |< = 9.4.20 |9.4.21 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-9516[Some HTTP/2 implementations are vulnerable to a header leak, potentially leading to a denial of service.] +If the issue is directly related to Jetty itself then reporting to the Jetty developers is encouraged. +The most direct method is to mail _security@webtide.com_. +Since Webtide is comprised of the active committers of the Jetty project this is our preferred reporting method. +We are generally flexible in how we work with reporters of security issues but we reserve the right to act in the interests of the Jetty project in all circumstances. -|2019/08/13 |CVE-2019-9515 |Med |Med |< = 9.4.20 |9.4.21 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-9515[Some HTTP/2 implementations are vulnerable to a settings flood, potentially leading to a denial of service when an attacker sent a stream of SETTINGS frames to the peer.] +If the issue is related to Eclipse or its Jetty integration then we encourage you to reach out to _security@eclipse.org_. -|2019/08/13 |CVE-2019-9514 |Med |Med |< = 9.4.20 |9.4.21 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-9514[Some HTTP/2 implementations are vulnerable to a reset flood, potentially leading to a denial of service.] +If the issue is related to integrations with Jetty we are happy to work with you to identify the proper entity and either of the approaches above is fine. -|2019/08/13 |CVE-2019-9512 |Low |Low |< = 9.4.20 |9.4.21 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-9512[Some HTTP/2 implementations are vulnerable to ping floods which could lead to a denial of service.] - -|2019/08/13 |CVE-2019-9511 |Low |Low |< = 9.4.20 |9.4.21 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-9511[Some HTTP/2 implementations are vulnerable to window size manipulation and stream prioritization manipulation which could lead to a denial of service.] - -|2019/04/11 |CVE-2019-10247 |Med |Med |< = 9.4.16 |9.2.28, 9.3.27, 9.4.17 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-10247[If no webapp was mounted to the root namespace and a 404 was encountered, an HTML page would be generated displaying the fully qualified base resource location for each context.] - -|2019/04/11 |CVE-2019-10246 |High |High |< = 9.4.16 |9.2.28, 9.3.27, 9.4.17 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-10246[Use of `DefaultServlet` or `ResourceHandler` with indexing was vulnerable to XSS behaviors to expose the directory listing on Windows operating systems.] - -|2019/04/11 |CVE-2019-10241 |High |High |< = 9.4.15 |9.2.27, 9.3.26, 9.4.16 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2019-10241[Use of `DefaultServlet` or `ResourceHandler` with indexing was vulnerable to XSS behaviors to expose the directory listing.] - -|2018/06/25 |CVE-2018-12538 |High |High |>= 9.4.0, < = 9.4.8 |9.4.9 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2018-12538[`HttpSessions` present specifically in the FileSystem’s storage could be hijacked/accessed by an unauthorized user.] - -|2018/06/25 |CVE-2018-12536 |High |See https://cwe.mitre.org/data/definitions/209.html[CWE-202] |< = 9.4.10 |9.2.25, 9.3.24, 9.4.11 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2018-12536[`InvalidPathException` Message reveals webapp system path.] - -|2018/06/25 |CVE-2017-7658 |See https://cwe.mitre.org/data/definitions/444.html[CWE-444] |See https://cwe.mitre.org/data/definitions/444.html[CWE-444] |< = 9.4.10 |9.2.25, 9.3.24, 9.4.11 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=2017-7658[Too Tolerant Parser, Double Content-Length + Transfer-Encoding + Whitespace.] - -|2018/06/25 |CVE-2017-7657 |See https://cwe.mitre.org/data/definitions/444.html[CWE-444] |See https://cwe.mitre.org/data/definitions/444.html[CWE-444] |< = 9.4.10 |9.2.25, 9.3.24, 9.4.11 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2017-7657[HTTP/1.1 Request smuggling with carefully crafted body content (Does not apply to HTTP/1.0 or HTTP/2).] - -|2018/06/25 |CVE-2017-7656 |See https://cwe.mitre.org/data/definitions/444.html[CWE-444] |See https://cwe.mitre.org/data/definitions/444.html[CWE-444] |< = 9.4.10 |9.2.25, 9.3.24, 9.4.11 -|https://cve.mitre.org/cgi-bin/cvename.cgi?name=2017-7656[HTTP Request Smuggling when used with invalid request headers (for HTTP/0.9).] - -|2016/05/31 |CVE-2016-4800 |high |high |>= 9.3.0, < = 9.3.8 |9.3.9 -|http://www.ocert.org/advisories/ocert-2016-001.html[Alias vulnerability allowing access to protected resources within a webapp on Windows.] - -|2015/02/24 |http://blog.gdssecurity.com/labs/2015/2/25/jetleak-vulnerability-remote-leakage-of-shared-buffers-in-je.html[CVE-2015-2080] |high |high |>=9.2.3 <9.2.9 |9.2.9 -|JetLeak exposure of past buffers during HttpParser error - -|2013/11/27 |http://en.securitylab.ru/lab/PT-2013-65[PT-2013-65] |medium -|high |>=9.0.0 <9.0.5 |9.0.6 -https://bugs.eclipse.org/bugs/show_bug.cgi?id=418014[418014] |Alias checking disabled by NTFS errors on Windows. - -|2013/07/24 -|https://bugs.eclipse.org/bugs/show_bug.cgi?id=413684[413684] |low -|medium |>=7.6.9 <9.0.5 |7.6.13,8.1.13,9.0.5 -https://bugs.eclipse.org/bugs/show_bug.cgi?id=413684[413684] -|Constraints bypassed if Unix symlink alias checker used on Windows. - -|2011/12/29 -|http://www.ocert.org/advisories/ocert-2011-003.html[CERT2011-003] http://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2011-4461[CVE-2011-4461] -|high |medium |All versions |7.6.0.RCO -https://bugs.eclipse.org/bugs/show_bug.cgi?id=367638[Jetty-367638] -|Added ContextHandler.setMaxFormKeys (intkeys) to limit the number of parameters (default 1000). - -|2009/11/05 -|http://www.kb.cert.org/vuls/id/120541[CERT2011-003] http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2009-3555[CERT2011-003] -|medium |high |JVM<1.6u19 |jetty-7.01.v20091125, jetty-6.1.22 |Work -around by turning off SSL renegotiation in Jetty. If using JVM > 1.6u19 -setAllowRenegotiate(true) may be called on connectors. - -|2009/06/18 |Jetty-1042 |low -|high |< = 6.1.18, < = 7.0.0.M4 |6.1.19, 7.0.0.Rc0 |Cookie leak between -requests sharing a connection. - -|2009/04/30 |http://www.kb.cert.org/vuls/id/402580[CERT402580] |medium -|high |< = 6.1.16, < = 7.0.0.M2 a| -5.1.15, 6.1.18, 7.0.0.M2 - -Jetty-1004 - - |View arbitrary disk content in some specific configurations. - -|2007/12/22 -|http://www.kb.cert.org/vuls/id/553235[CERT553235] http://web.nvd.nist.gov/view/vuln/detail?vulnId=CVE-2007-6672[CVE-2007-6672] -|high |medium |6.1.rrc0-6.1.6 a| -6.1.7 - -CERT553235 - - |Static content visible in WEB-INF and past security constraints. - -|2007/11/05 -|http://www.kb.cert.org/vuls/id/438616[CERT438616] http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2007-5614[CVE-2007-5614] -|low |low |<6.1.6 |6.1.6rc1 (patch in CVS for jetty5) |Single quote in -cookie name. - -|2007/11/05 -|http://www.kb.cert.org/vuls/id/237888[CERT237888>] http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2007-5613[CVE-2007-5613] -|low |low |<6.1.6 |6.1.6rc0 (patch in CVS for jetty5) |XSS in demo dup -servlet. - -|2007/11/03 |http://www.kb.cert.org/vuls/id/212984[CERT212984 ->] http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2007-5615[CVE-2007-5615] -|medium |medium |<6.1.6 |6.1.6rc0 (patch in CVS for jetty5) |CRLF -Response splitting. - -|2006/11/22 -|http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2006-6969[CVE-2006-6969] -|low |high |<6.1.0, <6.0.2, <5.1.12, <4.2.27 |6.1.0pre3, 6.0.2, 5.1.12, -4.2.27 |Session ID predictability. - -|2006/06/01 -|http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2006-2759[CVE-2006-2759] -|medium |medium |<6.0.*, <6.0.0Beta17 |6.0.0Beta17 |JSP source -visibility. - -|2006/01/05 | |medium |medium |<5.1.10 |5.1.10 |Fixed //security -constraint bypass on Windows. - -|2005/11/18 -|http://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2006-2758[CVE-2006-2758] -|medium |medium |<5.1.6 |5.1.6, 6.0.0Beta4 |JSP source visibility. - -|2004/02/04 |JSSE 1.0.3_01 |medium |medium |<4.2.7 |4.2.7 |Upgraded JSSE -to obtain downstream security fix. - -|2002/09/22 | |high |high |<4.1.0 |4.1.0 |Fixed CGI servlet remove -exploit. - -|2002/03/12 | |medium | |<3.1.7 |4.0.RC2, 3.1.7 |Fixed // security -constraint bypass. - -|2001/10/21 |medium | |high |<3.1.3 |3.1.3 |Fixed trailing null security -constraint bypass. -|======================================================================= +We prefer that security issues are reported directly to Jetty developers as opposed through GitHub Issues since it currently has *no* facility to tag issues as _private_. diff --git a/jetty-documentation/src/main/docbkx-stylesheet/html/docbook.xsl b/jetty-documentation/src/main/docbkx-stylesheet/html/docbook.xsl index 03e2a2b6e0b9..9d8ab67149e1 100644 --- a/jetty-documentation/src/main/docbkx-stylesheet/html/docbook.xsl +++ b/jetty-documentation/src/main/docbkx-stylesheet/html/docbook.xsl @@ -1,19 +1,16 @@ - + - - + + @@ -120,7 +117,9 @@ xmlns:date="http://exslt.org/dates-and-times"
- Jetty Logo + + Jetty Logo +
diff --git a/jetty-fcgi/fcgi-client/pom.xml b/jetty-fcgi/fcgi-client/pom.xml index 66be03675e0d..1d91abc004f8 100644 --- a/jetty-fcgi/fcgi-client/pom.xml +++ b/jetty-fcgi/fcgi-client/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.fcgi fcgi-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-fcgi/fcgi-server/pom.xml b/jetty-fcgi/fcgi-server/pom.xml index 6c4e19fa67f4..7d0bdab29463 100644 --- a/jetty-fcgi/fcgi-server/pom.xml +++ b/jetty-fcgi/fcgi-server/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.fcgi fcgi-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-fcgi/pom.xml b/jetty-fcgi/pom.xml index a11798bbc434..5301060db5c2 100644 --- a/jetty-fcgi/pom.xml +++ b/jetty-fcgi/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-gcloud/jetty-gcloud-session-manager/pom.xml b/jetty-gcloud/jetty-gcloud-session-manager/pom.xml index 490c775a32fb..a49620011476 100644 --- a/jetty-gcloud/jetty-gcloud-session-manager/pom.xml +++ b/jetty-gcloud/jetty-gcloud-session-manager/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.gcloud gcloud-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 @@ -31,32 +31,6 @@ - - - io.grpc - grpc-core - compile - - - com.google.auto.value - auto-value - 1.2 - - - com.google.protobuf - protobuf-java - 3.2.0 - - - com.google.http-client - google-http-client-jackson2 - 1.21.0 - - - com.google.code.findbugs - jsr305 - 3.0.0 - org.eclipse.jetty jetty-webapp diff --git a/jetty-gcloud/pom.xml b/jetty-gcloud/pom.xml index e4ce3146b4b3..406af262ae52 100644 --- a/jetty-gcloud/pom.xml +++ b/jetty-gcloud/pom.xml @@ -3,7 +3,7 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 @@ -13,7 +13,7 @@ Jetty :: GCloud - 1.0.0 + 1.105.0 diff --git a/jetty-hazelcast/pom.xml b/jetty-hazelcast/pom.xml index 7c67b481b31a..d2b894d8b6f4 100644 --- a/jetty-hazelcast/pom.xml +++ b/jetty-hazelcast/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-home/pom.xml b/jetty-home/pom.xml index 9bb98df7a701..3781a0583001 100644 --- a/jetty-home/pom.xml +++ b/jetty-home/pom.xml @@ -3,7 +3,7 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-home diff --git a/jetty-http-spi/pom.xml b/jetty-http-spi/pom.xml index db510b6af732..8dc9c80fd421 100644 --- a/jetty-http-spi/pom.xml +++ b/jetty-http-spi/pom.xml @@ -2,12 +2,11 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-http-spi Jetty :: Http Service Provider Interface - http://www.eclipse.org/jetty ${project.groupId}.http.spi @@ -90,7 +89,7 @@ com.sun.xml.ws jaxws-rt - 2.3.0.2 + 2.3.3 test diff --git a/jetty-http/pom.xml b/jetty-http/pom.xml index 1cac9851bda3..5721af22b7aa 100644 --- a/jetty-http/pom.xml +++ b/jetty-http/pom.xml @@ -3,12 +3,11 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-http Jetty :: Http Utility - http://www.eclipse.org/jetty ${project.groupId}.http diff --git a/jetty-http2/http2-alpn-tests/pom.xml b/jetty-http2/http2-alpn-tests/pom.xml index a75b7fdf322d..c7072e65f4da 100644 --- a/jetty-http2/http2-alpn-tests/pom.xml +++ b/jetty-http2/http2-alpn-tests/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.http2 http2-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-http2/http2-client/pom.xml b/jetty-http2/http2-client/pom.xml index dd2f98fe0321..bee654967107 100644 --- a/jetty-http2/http2-client/pom.xml +++ b/jetty-http2/http2-client/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.http2 http2-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-http2/http2-common/pom.xml b/jetty-http2/http2-common/pom.xml index 3cdccbabd7b4..8cb2fb6af3c4 100644 --- a/jetty-http2/http2-common/pom.xml +++ b/jetty-http2/http2-common/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.http2 http2-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-http2/http2-hpack/pom.xml b/jetty-http2/http2-hpack/pom.xml index 384f2b48df9f..b7cdd12e889a 100644 --- a/jetty-http2/http2-hpack/pom.xml +++ b/jetty-http2/http2-hpack/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.http2 http2-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-http2/http2-http-client-transport/pom.xml b/jetty-http2/http2-http-client-transport/pom.xml index dd5673916cc5..8ee2fe0a985e 100644 --- a/jetty-http2/http2-http-client-transport/pom.xml +++ b/jetty-http2/http2-http-client-transport/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.http2 http2-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-http2/http2-server/pom.xml b/jetty-http2/http2-server/pom.xml index ce608c0c6f24..edb874e50e58 100644 --- a/jetty-http2/http2-server/pom.xml +++ b/jetty-http2/http2-server/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.http2 http2-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-http2/pom.xml b/jetty-http2/pom.xml index b45d9ecad10c..7f2bcce37658 100644 --- a/jetty-http2/pom.xml +++ b/jetty-http2/pom.xml @@ -3,7 +3,7 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-infinispan/infinispan-common/pom.xml b/jetty-infinispan/infinispan-common/pom.xml index 494aafcfdf91..026b4909d64a 100644 --- a/jetty-infinispan/infinispan-common/pom.xml +++ b/jetty-infinispan/infinispan-common/pom.xml @@ -2,12 +2,11 @@ org.eclipse.jetty infinispan-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 infinispan-common Jetty :: Infinispan Session Manager Common - http://www.eclipse.org/jetty ${project.groupId}.infinispan.common diff --git a/jetty-infinispan/infinispan-embedded-query/pom.xml b/jetty-infinispan/infinispan-embedded-query/pom.xml index 02f2ce7019f5..846dce0336cc 100644 --- a/jetty-infinispan/infinispan-embedded-query/pom.xml +++ b/jetty-infinispan/infinispan-embedded-query/pom.xml @@ -2,12 +2,11 @@ org.eclipse.jetty infinispan-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 infinispan-embedded-query Jetty :: Infinispan Session Manager Embedded with Querying - http://www.eclipse.org/jetty ${project.groupId}.infinispan.embedded.query diff --git a/jetty-infinispan/infinispan-embedded/pom.xml b/jetty-infinispan/infinispan-embedded/pom.xml index cac032e7070a..071350d2c1ea 100644 --- a/jetty-infinispan/infinispan-embedded/pom.xml +++ b/jetty-infinispan/infinispan-embedded/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty infinispan-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 infinispan-embedded pom Jetty :: Infinispan Session Manager Embedded - http://www.eclipse.org/jetty ${project.groupId}.infinispan.embedded diff --git a/jetty-infinispan/infinispan-remote-query/pom.xml b/jetty-infinispan/infinispan-remote-query/pom.xml index 0e2069dbc0de..35bce86e5b71 100644 --- a/jetty-infinispan/infinispan-remote-query/pom.xml +++ b/jetty-infinispan/infinispan-remote-query/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty infinispan-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 infinispan-remote-query diff --git a/jetty-infinispan/infinispan-remote/pom.xml b/jetty-infinispan/infinispan-remote/pom.xml index e6d377d7e6ca..37421458877e 100644 --- a/jetty-infinispan/infinispan-remote/pom.xml +++ b/jetty-infinispan/infinispan-remote/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty infinispan-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 infinispan-remote pom Jetty :: Infinispan Session Manager Remote - http://www.eclipse.org/jetty ${project.groupId}.infinispan.remote diff --git a/jetty-infinispan/pom.xml b/jetty-infinispan/pom.xml index acdad92db75e..4c26ebd76c40 100644 --- a/jetty-infinispan/pom.xml +++ b/jetty-infinispan/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-io/pom.xml b/jetty-io/pom.xml index 2ebb4fd4c885..b01efa5d3f5e 100644 --- a/jetty-io/pom.xml +++ b/jetty-io/pom.xml @@ -3,12 +3,11 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-io Jetty :: IO Utility - http://www.eclipse.org/jetty ${project.groupId}.io diff --git a/jetty-jaas/pom.xml b/jetty-jaas/pom.xml index 0b944eb48b02..1148a577e2a4 100644 --- a/jetty-jaas/pom.xml +++ b/jetty-jaas/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-jaas diff --git a/jetty-jaspi/pom.xml b/jetty-jaspi/pom.xml index 5ded7d5ad040..cef7eb8bd4ba 100644 --- a/jetty-jaspi/pom.xml +++ b/jetty-jaspi/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 @@ -62,13 +62,13 @@ javax.xml.bind jaxb-api - 2.3.0 + 2.3.1 test org.glassfish.jaxb jaxb-runtime - 2.3.0.1 + 2.3.3 test diff --git a/jetty-jmh/pom.xml b/jetty-jmh/pom.xml index 5b185ad170fd..975e07f70679 100644 --- a/jetty-jmh/pom.xml +++ b/jetty-jmh/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-jmx/pom.xml b/jetty-jmx/pom.xml index cff3a342b679..02475b6b5624 100644 --- a/jetty-jmx/pom.xml +++ b/jetty-jmx/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-jmx Jetty :: JMX Management JMX management artifact for jetty. - http://www.eclipse.org/jetty ${project.groupId}.jmx diff --git a/jetty-jndi/pom.xml b/jetty-jndi/pom.xml index 4a063d93cf01..60a7bb86d90f 100644 --- a/jetty-jndi/pom.xml +++ b/jetty-jndi/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-jndi Jetty :: JNDI Naming JNDI spi impl for java namespace. - http://www.eclipse.org/jetty ${project.groupId}.jndi diff --git a/jetty-jspc-maven-plugin/pom.xml b/jetty-jspc-maven-plugin/pom.xml index a5d5d6b0d8eb..ad7bda6987bd 100644 --- a/jetty-jspc-maven-plugin/pom.xml +++ b/jetty-jspc-maven-plugin/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-jspc-maven-plugin diff --git a/jetty-maven-plugin/pom.xml b/jetty-maven-plugin/pom.xml index 063457788c41..1c2591603166 100644 --- a/jetty-maven-plugin/pom.xml +++ b/jetty-maven-plugin/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-maven-plugin @@ -231,6 +231,118 @@ ${project.version} test zip + + + + org.eclipse.jetty + jetty-alpn-conscrypt-server + + + org.eclipse.jetty + jetty-alpn-openjdk8-server + + + org.eclipse.jetty + jetty-alpn-server + + + org.eclipse.jetty + jetty-cdi + + + org.eclipse.jetty + jetty-continuation + + + org.eclipse.jetty.gcloud + jetty-gcloud-session-manager + + + org.eclipse.jetty + jetty-hazelcast + + + org.eclipse.jetty + jetty-jaas + + + org.eclipse.jetty + jetty-jaspi + + + org.eclipse.jetty.memcached + jetty-memcached-sessions + + + org.eclipse.jetty + jetty-openid + + + org.eclipse.jetty.fcgi + fcgi-server + + + org.eclipse.jetty + jetty-spring + + + org.eclipse.jetty + jetty-start + + + org.eclipse.jetty + jetty-nosql + + + org.eclipse.jetty + jetty-unixsocket + + + org.eclipse.jetty + jetty-infinispan + + + org.eclipse.jetty.http2 + http2-server + + + org.eclipse.jetty + infinispan-embedded + + + org.eclipse.jetty + infinispan-embedded-query + + + org.eclipse.jetty + infinispan-remote + + + org.eclipse.jetty + infinispan-remote-query + + + org.eclipse.jetty.orbit + javax.mail.glassfish + + + org.eclipse.jetty.orbit + javax.security.auth.message + + + org.ow2.asm + asm-tree + + + org.ow2.asm + asm-analysis + + + org.jboss.logging + jboss-logging + + diff --git a/jetty-maven-plugin/src/it/javax-annotation-api/postbuild.groovy b/jetty-maven-plugin/src/it/javax-annotation-api/postbuild.groovy index 9533c9ecc2c4..9ac4dc4de7f9 100644 --- a/jetty-maven-plugin/src/it/javax-annotation-api/postbuild.groovy +++ b/jetty-maven-plugin/src/it/javax-annotation-api/postbuild.groovy @@ -1,21 +1,21 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'all good guys get a good Beer') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'all good guys get a good Beer') diff --git a/jetty-maven-plugin/src/it/jetty-deploy-war-mojo-it/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-deploy-war-mojo-it/postbuild.groovy index b5f4344c4a6c..6a4eba4ef4f2 100644 --- a/jetty-maven-plugin/src/it/jetty-deploy-war-mojo-it/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-deploy-war-mojo-it/postbuild.groovy @@ -1,22 +1,22 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') assert buildLog.text.contains( 'contentCheck') \ No newline at end of file diff --git a/jetty-maven-plugin/src/it/jetty-maven-plugin-provided-module-dep/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-maven-plugin-provided-module-dep/postbuild.groovy index 4c12de49d832..1468c60c52bd 100644 --- a/jetty-maven-plugin/src/it/jetty-maven-plugin-provided-module-dep/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-maven-plugin-provided-module-dep/postbuild.groovy @@ -1,21 +1,21 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) assert buildLog.text.contains( 'ClassNotFoundException') \ No newline at end of file diff --git a/jetty-maven-plugin/src/it/jetty-run-mojo-it/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-run-mojo-it/postbuild.groovy index 323b5da5d72b..7d1099f0eef6 100644 --- a/jetty-maven-plugin/src/it/jetty-run-mojo-it/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-run-mojo-it/postbuild.groovy @@ -1,23 +1,23 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') -assert buildLog.text.contains( 'pingServlet ok') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') +assert buildLog.text.contains( 'pingServlet ok') assert buildLog.text.contains( 'helloServlet') \ No newline at end of file diff --git a/jetty-maven-plugin/src/it/jetty-run-mojo-jar-scan-it/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-run-mojo-jar-scan-it/postbuild.groovy index 87a9e7b26cc4..1e29c1dde2d1 100644 --- a/jetty-maven-plugin/src/it/jetty-run-mojo-jar-scan-it/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-run-mojo-jar-scan-it/postbuild.groovy @@ -1,3 +1,3 @@ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'STARTED[class jettyissue.NormalClass]') +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'STARTED[class jettyissue.NormalClass]') diff --git a/jetty-maven-plugin/src/it/jetty-run-mojo-jsp/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-run-mojo-jsp/postbuild.groovy index 4c4b42e2f2f0..20adc1f87f5d 100644 --- a/jetty-maven-plugin/src/it/jetty-run-mojo-jsp/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-run-mojo-jsp/postbuild.groovy @@ -1,22 +1,22 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') -assert buildLog.text.contains( 'contentCheck') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') +assert buildLog.text.contains( 'contentCheck') diff --git a/jetty-maven-plugin/src/it/jetty-run-war-exploded-mojo-it/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-run-war-exploded-mojo-it/postbuild.groovy index 323b5da5d72b..7d1099f0eef6 100644 --- a/jetty-maven-plugin/src/it/jetty-run-war-exploded-mojo-it/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-run-war-exploded-mojo-it/postbuild.groovy @@ -1,23 +1,23 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') -assert buildLog.text.contains( 'pingServlet ok') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') +assert buildLog.text.contains( 'pingServlet ok') assert buildLog.text.contains( 'helloServlet') \ No newline at end of file diff --git a/jetty-maven-plugin/src/it/jetty-run-war-mojo-it/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-run-war-mojo-it/postbuild.groovy index 323b5da5d72b..7d1099f0eef6 100644 --- a/jetty-maven-plugin/src/it/jetty-run-war-mojo-it/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-run-war-mojo-it/postbuild.groovy @@ -1,23 +1,23 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') -assert buildLog.text.contains( 'pingServlet ok') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') +assert buildLog.text.contains( 'pingServlet ok') assert buildLog.text.contains( 'helloServlet') \ No newline at end of file diff --git a/jetty-maven-plugin/src/it/jetty-start-mojo-it/postbuild.groovy b/jetty-maven-plugin/src/it/jetty-start-mojo-it/postbuild.groovy index 323b5da5d72b..7d1099f0eef6 100644 --- a/jetty-maven-plugin/src/it/jetty-start-mojo-it/postbuild.groovy +++ b/jetty-maven-plugin/src/it/jetty-start-mojo-it/postbuild.groovy @@ -1,23 +1,23 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') -assert buildLog.text.contains( 'pingServlet ok') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') +assert buildLog.text.contains( 'pingServlet ok') assert buildLog.text.contains( 'helloServlet') \ No newline at end of file diff --git a/jetty-maven-plugin/src/it/run-mojo-gwt-it/postbuild.groovy b/jetty-maven-plugin/src/it/run-mojo-gwt-it/postbuild.groovy index b5f4344c4a6c..6a4eba4ef4f2 100644 --- a/jetty-maven-plugin/src/it/run-mojo-gwt-it/postbuild.groovy +++ b/jetty-maven-plugin/src/it/run-mojo-gwt-it/postbuild.groovy @@ -1,22 +1,22 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one - * or more contributor license agreements. See the NOTICE file - * distributed with this work for additional information - * regarding copyright ownership. The ASF licenses this file - * to you under the Apache License, Version 2.0 (the - * "License"); you may not use this file except in compliance - * with the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, - * software distributed under the License is distributed on an - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY - * KIND, either express or implied. See the License for the - * specific language governing permissions and limitations - * under the License. - */ -File buildLog = new File( basedir, 'build.log' ) -assert buildLog.text.contains( 'Started Jetty Server' ) -assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') +/* + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, + * software distributed under the License is distributed on an + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY + * KIND, either express or implied. See the License for the + * specific language governing permissions and limitations + * under the License. + */ +File buildLog = new File( basedir, 'build.log' ) +assert buildLog.text.contains( 'Started Jetty Server' ) +assert buildLog.text.contains( 'Running org.eclipse.jetty.maven.plugin.it.TestGetContent') assert buildLog.text.contains( 'contentCheck') \ No newline at end of file diff --git a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyEffectiveWebXml.java b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyEffectiveWebXml.java index fcf0cc8ca00b..64768fc9e04c 100644 --- a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyEffectiveWebXml.java +++ b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyEffectiveWebXml.java @@ -39,7 +39,7 @@ * files. By default, the web.xml is generated to the console output only. Use the effectiveWebXml parameter * to provide a file name into which to save the output. * - * See http://www.eclipse.org/jetty/documentation for more information on this and other jetty plugins. + * See https://www.eclipse.org/jetty/documentation for more information on this and other jetty plugins. * * Runs jetty on the unassembled webapp to generate the effective web.xml */ diff --git a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunDistro.java b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunDistro.java index 59d682ec931f..f22810d45e24 100644 --- a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunDistro.java +++ b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunDistro.java @@ -78,7 +78,7 @@ * * This goal does NOT support the scanIntervalSeconds parameter: the webapp will be deployed only once. * - * See http://www.eclipse.org/jetty/documentation for more information on this and other jetty plugins. + * See https://www.eclipse.org/jetty/documentation for more information on this and other jetty plugins. * * Runs unassembled webapp in a locally installed jetty distro */ diff --git a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunForkedMojo.java b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunForkedMojo.java index 82cc6f14afc3..f34891b635b7 100644 --- a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunForkedMojo.java +++ b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunForkedMojo.java @@ -62,7 +62,7 @@ * By setting the configuration element waitForChild to false, the plugin will terminate after having forked the jetty process. In this case * you can use the jetty:stop goal to terminate the process. *

- * See http://www.eclipse.org/jetty/documentation for more information on this and other jetty plugins. + * See https://www.eclipse.org/jetty/documentation for more information on this and other jetty plugins. * * Runs Jetty in forked JVM on an unassembled webapp */ diff --git a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunMojo.java b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunMojo.java index a826dc23c17e..0922b0a45b32 100644 --- a/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunMojo.java +++ b/jetty-maven-plugin/src/main/java/org/eclipse/jetty/maven/plugin/JettyRunMojo.java @@ -25,7 +25,6 @@ import java.nio.file.PathMatcher; import java.util.ArrayList; import java.util.Collection; -import java.util.Collections; import java.util.Date; import java.util.HashSet; import java.util.List; @@ -40,7 +39,6 @@ import org.apache.maven.plugins.annotations.Mojo; import org.apache.maven.plugins.annotations.Parameter; import org.apache.maven.plugins.annotations.ResolutionScope; -import org.apache.maven.project.MavenProject; import org.eclipse.jetty.maven.plugin.utils.MavenProjectHelper; import org.eclipse.jetty.util.IncludeExcludeSet; import org.eclipse.jetty.util.StringUtil; @@ -63,7 +61,7 @@ * You may also specify the location of a jetty.xml file whose contents will be applied before any plugin configuration. * This can be used, for example, to deploy a static webapp that is not part of your maven build. *

- * There is a reference guide to the configuration parameters for this plugin. + * There is a reference guide to the configuration parameters for this plugin. * * Runs jetty directly from a maven project */ diff --git a/jetty-memcached/jetty-memcached-sessions/pom.xml b/jetty-memcached/jetty-memcached-sessions/pom.xml index b6b04adb8e96..5ffd2b236f35 100644 --- a/jetty-memcached/jetty-memcached-sessions/pom.xml +++ b/jetty-memcached/jetty-memcached-sessions/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.memcached memcached-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-memcached/pom.xml b/jetty-memcached/pom.xml index b52dc131764c..9e6deade9ca1 100644 --- a/jetty-memcached/pom.xml +++ b/jetty-memcached/pom.xml @@ -3,7 +3,7 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-nosql/pom.xml b/jetty-nosql/pom.xml index 22aeaaa15388..95595558e013 100644 --- a/jetty-nosql/pom.xml +++ b/jetty-nosql/pom.xml @@ -2,12 +2,11 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-nosql Jetty :: NoSQL Session Managers - http://www.eclipse.org/jetty ${project.groupId}.nosql diff --git a/jetty-openid/pom.xml b/jetty-openid/pom.xml index 9ed431a9fb19..7ae1cf409b7e 100644 --- a/jetty-openid/pom.xml +++ b/jetty-openid/pom.xml @@ -2,14 +2,13 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-openid Jetty :: OpenID Jetty OpenID Connect infrastructure - http://www.eclipse.org/jetty ${project.groupId}.openid diff --git a/jetty-osgi/jetty-osgi-alpn/pom.xml b/jetty-osgi/jetty-osgi-alpn/pom.xml index 682ad197f8c0..467410a8e344 100644 --- a/jetty-osgi/jetty-osgi-alpn/pom.xml +++ b/jetty-osgi/jetty-osgi-alpn/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-osgi-alpn diff --git a/jetty-osgi/jetty-osgi-boot-jsp/pom.xml b/jetty-osgi/jetty-osgi-boot-jsp/pom.xml index 85c6321eb4fd..27159879afac 100644 --- a/jetty-osgi/jetty-osgi-boot-jsp/pom.xml +++ b/jetty-osgi/jetty-osgi-boot-jsp/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-osgi-boot-jsp Jetty :: OSGi :: Boot JSP Jetty OSGi Boot JSP bundle - http://www.eclipse.org/jetty ${project.groupId}.boot.jsp diff --git a/jetty-osgi/jetty-osgi-boot-warurl/pom.xml b/jetty-osgi/jetty-osgi-boot-warurl/pom.xml index 2b0ad4f10e66..6dc3906c46ba 100644 --- a/jetty-osgi/jetty-osgi-boot-warurl/pom.xml +++ b/jetty-osgi/jetty-osgi-boot-warurl/pom.xml @@ -2,14 +2,13 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 jetty-osgi-boot-warurl Jetty :: OSGi :: Boot :: Warurl Jetty OSGi Boot-Warurl bundle - http://www.eclipse.org/jetty ${project.groupId}.boot.warurl diff --git a/jetty-osgi/jetty-osgi-boot/pom.xml b/jetty-osgi/jetty-osgi-boot/pom.xml index 72bffba05125..a7ac0c209bcd 100644 --- a/jetty-osgi/jetty-osgi-boot/pom.xml +++ b/jetty-osgi/jetty-osgi-boot/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-osgi-boot Jetty :: OSGi :: Boot Jetty OSGi Boot bundle - http://www.eclipse.org/jetty ${project.groupId}.boot diff --git a/jetty-osgi/jetty-osgi-httpservice/pom.xml b/jetty-osgi/jetty-osgi-httpservice/pom.xml index 5f4eaa018b71..7d55bcbc4625 100644 --- a/jetty-osgi/jetty-osgi-httpservice/pom.xml +++ b/jetty-osgi/jetty-osgi-httpservice/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-httpservice Jetty :: OSGi :: HttpService Jetty OSGi HttpService bundle - http://www.eclipse.org/jetty ${project.groupId}.httpservice diff --git a/jetty-osgi/pom.xml b/jetty-osgi/pom.xml index c86cd2b0741a..148acef40968 100644 --- a/jetty-osgi/pom.xml +++ b/jetty-osgi/pom.xml @@ -2,14 +2,13 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 org.eclipse.jetty.osgi jetty-osgi-project Jetty :: OSGi - http://www.eclipse.org/jetty pom diff --git a/jetty-osgi/test-jetty-osgi-context/pom.xml b/jetty-osgi/test-jetty-osgi-context/pom.xml index 714aa142cf6a..4c8e809b1b44 100644 --- a/jetty-osgi/test-jetty-osgi-context/pom.xml +++ b/jetty-osgi/test-jetty-osgi-context/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 test-jetty-osgi-context Jetty :: OSGi :: Test Context Test Jetty OSGi bundle with a ContextHandler - http://www.eclipse.org/jetty ${project.groupId}.testcontext diff --git a/jetty-osgi/test-jetty-osgi-fragment/pom.xml b/jetty-osgi/test-jetty-osgi-fragment/pom.xml index 5682917e55a6..5a5bd738ce46 100644 --- a/jetty-osgi/test-jetty-osgi-fragment/pom.xml +++ b/jetty-osgi/test-jetty-osgi-fragment/pom.xml @@ -2,14 +2,13 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 test-jetty-osgi-fragment Jetty :: OSGi :: WebApp Fragment Test Jetty OSGi Webapp Fragment bundle - http://www.eclipse.org/jetty ${project.groupId}.webapp.fragment diff --git a/jetty-osgi/test-jetty-osgi-server/pom.xml b/jetty-osgi/test-jetty-osgi-server/pom.xml index b42bba43e05f..eed112e3d542 100644 --- a/jetty-osgi/test-jetty-osgi-server/pom.xml +++ b/jetty-osgi/test-jetty-osgi-server/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 test-jetty-osgi-server Jetty :: OSGi :: Server Test Jetty OSGi bundle with a Server - http://www.eclipse.org/jetty ${project.groupId}.testserver diff --git a/jetty-osgi/test-jetty-osgi-webapp-resources/pom.xml b/jetty-osgi/test-jetty-osgi-webapp-resources/pom.xml index e707c35d6c1a..8e443fe13831 100644 --- a/jetty-osgi/test-jetty-osgi-webapp-resources/pom.xml +++ b/jetty-osgi/test-jetty-osgi-webapp-resources/pom.xml @@ -3,12 +3,11 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 test-jetty-osgi-webapp-resources OSGi Test :: Webapp With Resources - http://www.eclipse.org/jetty war ${project.groupId}.webapp.resources diff --git a/jetty-osgi/test-jetty-osgi-webapp/pom.xml b/jetty-osgi/test-jetty-osgi-webapp/pom.xml index 935871ac853f..54c6bd9bd31e 100644 --- a/jetty-osgi/test-jetty-osgi-webapp/pom.xml +++ b/jetty-osgi/test-jetty-osgi-webapp/pom.xml @@ -2,14 +2,13 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 test-jetty-osgi-webapp Jetty :: OSGi :: Test WebApp Test Jetty OSGi Webapp bundle - http://www.eclipse.org/jetty ${project.groupId}.webapp diff --git a/jetty-osgi/test-jetty-osgi/pom.xml b/jetty-osgi/test-jetty-osgi/pom.xml index ffd1f53eebda..175f5de3c9a0 100644 --- a/jetty-osgi/test-jetty-osgi/pom.xml +++ b/jetty-osgi/test-jetty-osgi/pom.xml @@ -2,17 +2,16 @@ org.eclipse.jetty.osgi jetty-osgi-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 test-jetty-osgi Jetty :: OSGi :: Test Jetty OSGi Integration test - http://www.eclipse.org/jetty ${project.groupId}.boot.test.osgi - http://download.eclipse.org/jetty/orbit/ + https://download.eclipse.org/jetty/orbit/ target/distribution 4.13.1 2.6.1 diff --git a/jetty-osgi/test-jetty-osgi/src/test/java/org/eclipse/jetty/osgi/test/TestJettyOSGiBootHTTP2.java b/jetty-osgi/test-jetty-osgi/src/test/java/org/eclipse/jetty/osgi/test/TestJettyOSGiBootHTTP2.java index 1f971fd0e33c..eefd5b85be27 100644 --- a/jetty-osgi/test-jetty-osgi/src/test/java/org/eclipse/jetty/osgi/test/TestJettyOSGiBootHTTP2.java +++ b/jetty-osgi/test-jetty-osgi/src/test/java/org/eclipse/jetty/osgi/test/TestJettyOSGiBootHTTP2.java @@ -82,7 +82,7 @@ public Option[] config() options.add(mavenBundle().groupId("org.eclipse.jetty.http2").artifactId("http2-http-client-transport").versionAsInProject().start()); options.add(systemProperty("org.ops4j.pax.logging.DefaultServiceLog.level").value(LOG_LEVEL)); - options.add(systemProperty("org.eclipse.jetty.LEVEL").value("DEBUG")); + options.add(systemProperty("org.eclipse.jetty.LEVEL").value("INFO")); options.add(CoreOptions.cleanCaches(true)); return options.toArray(new Option[0]); } @@ -154,7 +154,7 @@ public void testHTTP2() throws Exception httpClient.start(); ContentResponse response = httpClient.GET("https://localhost:" + port + "/jsp/jstl.jsp"); - assertEquals(response.toString(), response.getStatus(), HttpStatus.OK_200); + assertEquals(HttpStatus.OK_200,response.getStatus()); String body = response.getContentAsString(); assertTrue("Body contains \"JSTL Example\": " + body, body.contains("JSTL Example")); } diff --git a/jetty-plus/pom.xml b/jetty-plus/pom.xml index 125efed3cd04..e01afcada408 100644 --- a/jetty-plus/pom.xml +++ b/jetty-plus/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-plus Jetty :: Plus Jetty JavaEE style services - http://www.eclipse.org/jetty ${project.groupId}.plus diff --git a/jetty-proxy/pom.xml b/jetty-proxy/pom.xml index c70142607caa..ed246d35e4e3 100644 --- a/jetty-proxy/pom.xml +++ b/jetty-proxy/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-proxy Jetty :: Proxy Jetty Proxy - http://www.eclipse.org/jetty ${project.groupId}.proxy diff --git a/jetty-proxy/src/main/java/org/eclipse/jetty/proxy/AbstractProxyServlet.java b/jetty-proxy/src/main/java/org/eclipse/jetty/proxy/AbstractProxyServlet.java index 26998e4eae40..022d41d90abf 100644 --- a/jetty-proxy/src/main/java/org/eclipse/jetty/proxy/AbstractProxyServlet.java +++ b/jetty-proxy/src/main/java/org/eclipse/jetty/proxy/AbstractProxyServlet.java @@ -55,6 +55,7 @@ import org.eclipse.jetty.util.StringUtil; import org.eclipse.jetty.util.log.Log; import org.eclipse.jetty.util.log.Logger; +import org.eclipse.jetty.util.ssl.SslContextFactory; import org.eclipse.jetty.util.thread.QueuedThreadPool; /** @@ -362,7 +363,8 @@ protected HttpClient newHttpClient() String value = getServletConfig().getInitParameter("selectors"); if (value != null) selectors = Integer.parseInt(value); - return new HttpClient(new HttpClientTransportOverHTTP(selectors), null); + SslContextFactory.Client clientSsl = new SslContextFactory.Client(); + return new HttpClient(new HttpClientTransportOverHTTP(selectors), clientSsl); } protected HttpClient getHttpClient() diff --git a/jetty-proxy/src/test/java/org/eclipse/jetty/proxy/ProxyServletTest.java b/jetty-proxy/src/test/java/org/eclipse/jetty/proxy/ProxyServletTest.java index eac3637571dc..d3e2de15e623 100644 --- a/jetty-proxy/src/test/java/org/eclipse/jetty/proxy/ProxyServletTest.java +++ b/jetty-proxy/src/test/java/org/eclipse/jetty/proxy/ProxyServletTest.java @@ -76,17 +76,21 @@ import org.eclipse.jetty.http.HttpHeader; import org.eclipse.jetty.http.HttpHeaderValue; import org.eclipse.jetty.http.HttpMethod; +import org.eclipse.jetty.http.HttpScheme; import org.eclipse.jetty.http.HttpStatus; +import org.eclipse.jetty.http.HttpVersion; import org.eclipse.jetty.server.HttpConfiguration; import org.eclipse.jetty.server.HttpConnectionFactory; import org.eclipse.jetty.server.Server; import org.eclipse.jetty.server.ServerConnector; +import org.eclipse.jetty.server.SslConnectionFactory; import org.eclipse.jetty.servlet.FilterHolder; import org.eclipse.jetty.servlet.ServletContextHandler; import org.eclipse.jetty.servlet.ServletHolder; import org.eclipse.jetty.toolchain.test.MavenTestingUtils; import org.eclipse.jetty.util.IO; import org.eclipse.jetty.util.StringUtil; +import org.eclipse.jetty.util.ssl.SslContextFactory; import org.eclipse.jetty.util.thread.QueuedThreadPool; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.Test; @@ -127,6 +131,7 @@ public static Stream impls() private AbstractProxyServlet proxyServlet; private Server server; private ServerConnector serverConnector; + private ServerConnector tlsServerConnector; private void startServer(HttpServlet servlet) throws Exception { @@ -136,6 +141,16 @@ private void startServer(HttpServlet servlet) throws Exception serverConnector = new ServerConnector(server); server.addConnector(serverConnector); + SslContextFactory.Server sslContextFactory = new SslContextFactory.Server(); + String keyStorePath = MavenTestingUtils.getTestResourceFile("server_keystore.p12").getAbsolutePath(); + sslContextFactory.setKeyStorePath(keyStorePath); + sslContextFactory.setKeyStorePassword("storepwd"); + tlsServerConnector = new ServerConnector(server, new SslConnectionFactory( + sslContextFactory, + HttpVersion.HTTP_1_1.asString()), + new HttpConnectionFactory()); + server.addConnector(tlsServerConnector); + ServletContextHandler appCtx = new ServletContextHandler(server, "/", true, false); ServletHolder appServletHolder = new ServletHolder(servlet); appCtx.addServlet(appServletHolder, "/*"); @@ -730,27 +745,80 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws Se public static Stream transparentImpls() { return Stream.of( - ProxyServlet.Transparent.class, - AsyncProxyServlet.Transparent.class, - AsyncMiddleManServlet.Transparent.class + new ProxyServlet.Transparent() + { + @Override + protected HttpClient newHttpClient() + { + return newTrustAllClient(super.newHttpClient()); + } + + @Override + public String toString() + { + return ProxyServlet.Transparent.class.getName(); + } + }, + new AsyncProxyServlet.Transparent() + { + @Override + protected HttpClient newHttpClient() + { + return newTrustAllClient(super.newHttpClient()); + } + + @Override + public String toString() + { + return AsyncProxyServlet.Transparent.class.getName(); + } + }, + new AsyncMiddleManServlet.Transparent() + { + @Override + protected HttpClient newHttpClient() + { + return newTrustAllClient(super.newHttpClient()); + } + + @Override + public String toString() + { + return AsyncMiddleManServlet.Transparent.class.getName(); + } + } ).map(Arguments::of); } + private static HttpClient newTrustAllClient(HttpClient client) + { + SslContextFactory sslContextFactory = client.getSslContextFactory(); + sslContextFactory.setTrustAll(true); + return client; + } + + @ParameterizedTest + @MethodSource("transparentImpls") + public void testTransparentProxy(AbstractProxyServlet proxyServletClass) throws Exception + { + testTransparentProxyWithPrefix(proxyServletClass, "http", "/proxy"); + } + @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxy(Class proxyServletClass) throws Exception + public void testTransparentProxyTls(AbstractProxyServlet proxyServletClass) throws Exception { - testTransparentProxyWithPrefix(proxyServletClass, "/proxy"); + testTransparentProxyWithPrefix(proxyServletClass, "https", "/proxy"); } @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxyWithRootContext(Class proxyServletClass) throws Exception + public void testTransparentProxyWithRootContext(AbstractProxyServlet proxyServletClass) throws Exception { - testTransparentProxyWithPrefix(proxyServletClass, "/"); + testTransparentProxyWithPrefix(proxyServletClass, "http", "/"); } - private void testTransparentProxyWithPrefix(Class proxyServletClass, String prefix) throws Exception + private void testTransparentProxyWithPrefix(AbstractProxyServlet proxyServletClass, String scheme, String prefix) throws Exception { final String target = "/test"; startServer(new HttpServlet() @@ -763,7 +831,10 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws Se resp.setStatus(target.equals(req.getRequestURI()) ? 200 : 404); } }); - String proxyTo = "http://localhost:" + serverConnector.getLocalPort(); + int serverPort = serverConnector.getLocalPort(); + if (HttpScheme.HTTPS.is(scheme)) + serverPort = tlsServerConnector.getLocalPort(); + String proxyTo = scheme + "://localhost:" + serverPort; Map params = new HashMap<>(); params.put("proxyTo", proxyTo); params.put("prefix", prefix); @@ -781,33 +852,33 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws Se @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxyWithQuery(Class proxyServletClass) throws Exception + public void testTransparentProxyWithQuery(AbstractProxyServlet proxyServletClass) throws Exception { testTransparentProxyWithQuery(proxyServletClass, "/foo", "/proxy", "/test"); } @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxyEmptyContextWithQuery(Class proxyServletClass) throws Exception + public void testTransparentProxyEmptyContextWithQuery(AbstractProxyServlet proxyServletClass) throws Exception { testTransparentProxyWithQuery(proxyServletClass, "", "/proxy", "/test"); } @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxyEmptyTargetWithQuery(Class proxyServletClass) throws Exception + public void testTransparentProxyEmptyTargetWithQuery(AbstractProxyServlet proxyServletClass) throws Exception { testTransparentProxyWithQuery(proxyServletClass, "/bar", "/proxy", ""); } @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxyEmptyContextEmptyTargetWithQuery(Class proxyServletClass) throws Exception + public void testTransparentProxyEmptyContextEmptyTargetWithQuery(AbstractProxyServlet proxyServletClass) throws Exception { testTransparentProxyWithQuery(proxyServletClass, "", "/proxy", ""); } - private void testTransparentProxyWithQuery(Class proxyServletClass, String proxyToContext, String prefix, String target) throws Exception + private void testTransparentProxyWithQuery(AbstractProxyServlet proxyServletClass, String proxyToContext, String prefix, String target) throws Exception { final String query = "a=1&b=2"; startServer(new HttpServlet() @@ -851,7 +922,7 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws Se @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxyWithQueryWithSpaces(Class proxyServletClass) throws Exception + public void testTransparentProxyWithQueryWithSpaces(AbstractProxyServlet proxyServletClass) throws Exception { final String target = "/test"; final String query = "a=1&b=2&c=1234%205678&d=hello+world"; @@ -893,7 +964,7 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws Se @ParameterizedTest @MethodSource("transparentImpls") - public void testTransparentProxyWithoutPrefix(Class proxyServletClass) throws Exception + public void testTransparentProxyWithoutPrefix(AbstractProxyServlet proxyServletClass) throws Exception { final String target = "/test"; startServer(new HttpServlet() diff --git a/jetty-quickstart/pom.xml b/jetty-quickstart/pom.xml index a00c09a308f0..71c5151a1492 100644 --- a/jetty-quickstart/pom.xml +++ b/jetty-quickstart/pom.xml @@ -2,14 +2,13 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 org.eclipse.jetty jetty-quickstart Jetty :: Quick Start Jetty Quick Start - http://www.eclipse.org/jetty ${project.groupId}.quickstart diff --git a/jetty-rewrite/pom.xml b/jetty-rewrite/pom.xml index c864e98780f7..e9d242314585 100644 --- a/jetty-rewrite/pom.xml +++ b/jetty-rewrite/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-rewrite Jetty :: Rewrite Handler Jetty Rewrite Handler - http://www.eclipse.org/jetty ${project.groupId}.rewrite diff --git a/jetty-runner/pom.xml b/jetty-runner/pom.xml index e0b9c1821e07..18fd61069dba 100644 --- a/jetty-runner/pom.xml +++ b/jetty-runner/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-runner diff --git a/jetty-security/pom.xml b/jetty-security/pom.xml index a5b3d7bd953f..c4ff5cbdf9d8 100644 --- a/jetty-security/pom.xml +++ b/jetty-security/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-security Jetty :: Security Jetty security infrastructure - http://www.eclipse.org/jetty ${project.groupId}.security diff --git a/jetty-server/pom.xml b/jetty-server/pom.xml index d67b0f7969b0..4a23507e863e 100644 --- a/jetty-server/pom.xml +++ b/jetty-server/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-server Jetty :: Server Core The core jetty server artifact. - http://www.eclipse.org/jetty ${project.groupId}.server diff --git a/jetty-server/src/main/config/modules/ssl.mod b/jetty-server/src/main/config/modules/ssl.mod index b2891c3ec776..d01944675a08 100644 --- a/jetty-server/src/main/config/modules/ssl.mod +++ b/jetty-server/src/main/config/modules/ssl.mod @@ -78,7 +78,7 @@ basehome:modules/ssl/keystore|etc/keystore ### SslContextFactory Configuration ## Note that OBF passwords are not secure, just protected from casual observation -## See http://www.eclipse.org/jetty/documentation/current/configuring-security-secure-passwords.html +## See https://eclipse.org/jetty/documentation/current/configuring-security-secure-passwords.html ## The Endpoint Identification Algorithm ## Same as javax.net.ssl.SSLParameters#setEndpointIdentificationAlgorithm(String) diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/ForwardedRequestCustomizer.java b/jetty-server/src/main/java/org/eclipse/jetty/server/ForwardedRequestCustomizer.java index 2e4a38fd4277..f43ddfecfaba 100644 --- a/jetty-server/src/main/java/org/eclipse/jetty/server/ForwardedRequestCustomizer.java +++ b/jetty-server/src/main/java/org/eclipse/jetty/server/ForwardedRequestCustomizer.java @@ -30,6 +30,7 @@ import org.eclipse.jetty.http.HttpFields; import org.eclipse.jetty.http.HttpHeader; import org.eclipse.jetty.http.HttpScheme; +import org.eclipse.jetty.http.HttpURI; import org.eclipse.jetty.http.QuotedCSVParser; import org.eclipse.jetty.server.HttpConfiguration.Customizer; import org.eclipse.jetty.util.ArrayTrie; @@ -57,8 +58,91 @@ * the request came

*

Headers can also be defined so that forwarded SSL Session IDs and Cipher * suites may be customised

+ *

+ * The Authority (host and port) is updated on the {@link Request} object based + * on the host / port information in the following search order. + *

+ * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + * + *
Request Authority Search Order
#Value OriginHostPortProtocolNotes
1Forwarded Header"{@code host=}" param (Required)"{@code host=:} param (Implied)"{@code proto=}" param (Optional)From left-most relevant parameter (see rfc7239)
2X-Forwarded-Host HeaderRequiredImpliedn/aleft-most value
3X-Forwarded-Port Headern/aRequiredn/aleft-most value (only if {@link #getForwardedPortAsAuthority()} is true)
4X-Forwarded-Server HeaderRequiredOptionaln/aleft-most value
5X-Forwarded-Proto Headern/aImplied from valueRequired + *

left-most value becomes protocol.

+ *
    + *
  • Value of "http" means port=80.
  • + *
  • Value of "{@link HttpConfiguration#getSecureScheme()}" means port={@link HttpConfiguration#getSecurePort()}.
  • + *
+ *
6X-Proxied-Https Headern/aImplied from valueboolean + *

left-most value determines protocol and port.

+ *
    + *
  • Value of "on" means port={@link HttpConfiguration#getSecurePort()}, and protocol={@link HttpConfiguration#getSecureScheme()}).
  • + *
  • Value of "off" means port=80, and protocol=http.
  • + *
+ *
* * @see Wikipedia: X-Forwarded-For + * @see RFC 7239: Forwarded HTTP Extension */ public class ForwardedRequestCustomizer implements Customizer { @@ -151,7 +235,7 @@ public String getForcedHost() */ public void setForcedHost(String hostAndPort) { - _forcedHost = new HostPortHttpField(new ForcedHostPort(hostAndPort)); + _forcedHost = new HostPortHttpField(hostAndPort); } /** @@ -377,13 +461,17 @@ public void customize(Connector connector, HttpConfiguration config, Request req // Do a single pass through the header fields as it is a more efficient single iteration. Forwarded forwarded = new Forwarded(request, config); + boolean match = false; for (HttpField field : httpFields) { try { MethodHandle handle = _handles.get(field.getName()); if (handle != null) + { + match = true; handle.invoke(forwarded, field); + } } catch (Throwable t) { @@ -391,42 +479,78 @@ public void customize(Connector connector, HttpConfiguration config, Request req } } - if (forwarded._proto != null) + if (match) { - request.setScheme(forwarded._proto); - if (forwarded._proto.equalsIgnoreCase(config.getSecureScheme())) + // Is secure status configured from headers? + if (forwarded.isSecure()) + { request.setSecure(true); - } + } - if (forwarded._server != null && forwarded._host instanceof PortSetHostPort) - { - httpFields.put(new HostPortHttpField(forwarded._server, forwarded._host.getPort())); - request.setAuthority(forwarded._server, forwarded._host.getPort()); - } - else if (forwarded._host != null) - { - httpFields.put(new HostPortHttpField(forwarded._host)); - request.setAuthority(forwarded._host.getHost(), forwarded._host.getPort()); - } - else if (forwarded._server != null) - { - httpFields.put(new HostPortHttpField(forwarded._server)); - request.setAuthority(forwarded._server, 0); - } + // Set Scheme from configured protocol + if (forwarded._proto != null) + { + request.setScheme(forwarded._proto); + } + // Set scheme if header implies secure scheme is to be used (see #isSslIsSecure()) + else if (forwarded._secureScheme) + { + request.setScheme(config.getSecureScheme()); + } - if (forwarded._for != null) - { - int port = forwarded._for.getPort() > 0 ? forwarded._for.getPort() : request.getRemotePort(); - request.setRemoteAddr(InetSocketAddress.createUnresolved(forwarded._for.getHost(), port)); + // Use authority from headers, if configured. + if (forwarded._authority != null) + { + String host = forwarded._authority._host; + int port = forwarded._authority._port; + + HttpURI requestURI = request.getMetaData().getURI(); + + if (requestURI != null) + { + // Fall back to request metadata if needed. + if (host == null) + { + host = requestURI.getHost(); + } + + if (port == MutableHostPort.UNSET) // is unset by headers + { + port = requestURI.getPort(); + } + + // Don't change port if port == IMPLIED. + + // Update authority if different from metadata + if (!host.equalsIgnoreCase(requestURI.getHost()) || + port != requestURI.getPort()) + { + httpFields.put(new HostPortHttpField(host, port)); + request.setAuthority(host, port); + } + } + } + + // Set Remote Address + if (forwarded.hasFor()) + { + int forPort = forwarded._for._port > 0 ? forwarded._for._port : request.getRemotePort(); + request.setRemoteAddr(InetSocketAddress.createUnresolved(forwarded._for._host, forPort)); + } } } + protected static int getSecurePort(HttpConfiguration config) + { + return config.getSecurePort() > 0 ? config.getSecurePort() : 443; + } + protected void onError(HttpField field, Throwable t) { throw new BadMessageException("Bad header value for " + field.getName(), t); } - protected String getLeftMost(String headerValue) + protected static String getLeftMost(String headerValue) { if (headerValue == null) return null; @@ -479,23 +603,23 @@ private void updateHandles() size += 128; // experimented good baseline size _handles = new ArrayTrie<>(size); - if (updateForwardedHandle(lookup, getForwardedCipherSuiteHeader(), "handleCipherSuite")) - continue; - if (updateForwardedHandle(lookup, getForwardedSslSessionIdHeader(), "handleSslSessionId")) - continue; if (updateForwardedHandle(lookup, getForwardedHeader(), "handleRFC7239")) continue; - if (updateForwardedHandle(lookup, getForwardedForHeader(), "handleFor")) + if (updateForwardedHandle(lookup, getForwardedHostHeader(), "handleForwardedHost")) continue; - if (updateForwardedHandle(lookup, getForwardedPortHeader(), "handlePort")) + if (updateForwardedHandle(lookup, getForwardedForHeader(), "handleForwardedFor")) continue; - if (updateForwardedHandle(lookup, getForwardedHostHeader(), "handleHost")) + if (updateForwardedHandle(lookup, getForwardedPortHeader(), "handleForwardedPort")) continue; if (updateForwardedHandle(lookup, getForwardedProtoHeader(), "handleProto")) continue; if (updateForwardedHandle(lookup, getForwardedHttpsHeader(), "handleHttps")) continue; - if (updateForwardedHandle(lookup, getForwardedServerHeader(), "handleServer")) + if (updateForwardedHandle(lookup, getForwardedServerHeader(), "handleForwardedServer")) + continue; + if (updateForwardedHandle(lookup, getForwardedCipherSuiteHeader(), "handleCipherSuite")) + continue; + if (updateForwardedHandle(lookup, getForwardedSslSessionIdHeader(), "handleSslSessionId")) continue; break; } @@ -516,40 +640,98 @@ private boolean updateForwardedHandle(MethodHandles.Lookup lookup, String header return !_handles.put(headerName, lookup.findVirtual(Forwarded.class, forwardedMethodName, type)); } - private static class ForcedHostPort extends HostPort + private static class MutableHostPort { - ForcedHostPort(String authority) + public static final int UNSET = -1; + public static final int IMPLIED = 0; + + String _host; + Source _hostSource = Source.UNSET; + int _port = UNSET; + Source _portSource = Source.UNSET; + + public void setHostPort(String host, int port, Source source) { - super(authority); + setHost(host, source); + setPort(port, source); } - } - private static class PossiblyPartialHostPort extends HostPort - { - PossiblyPartialHostPort(String authority) + public void setHost(String host, Source source) { - super(authority); + if (source.priority() > _hostSource.priority()) + { + _host = host; + _hostSource = source; + } } - protected PossiblyPartialHostPort(String host, int port) + public void setPort(int port, Source source) { - super(host, port); + if (source.priority() > _portSource.priority()) + { + _port = port; + _portSource = source; + } } - } - private static class PortSetHostPort extends PossiblyPartialHostPort - { - PortSetHostPort(String host, int port) + public void setHostPort(HostPort hostPort, Source source) { - super(host, port); + if (source.priority() > _hostSource.priority()) + { + _host = hostPort.getHost(); + _hostSource = source; + } + + int port = hostPort.getPort(); + // Is port supplied? + if (port > 0 && source.priority() > _portSource.priority()) + { + _port = hostPort.getPort(); + _portSource = source; + } + // Since we are Host:Port pair, the port could be unspecified + // Meaning it's implied. + // Make sure that we switch the tracked port from unset to implied + else if (_port == UNSET) + { + // set port to implied (with no priority) + _port = IMPLIED; + } + } + + @Override + public String toString() + { + final StringBuilder sb = new StringBuilder("MutableHostPort{"); + sb.append("host='").append(_host).append("'/").append(_hostSource); + sb.append(", port=").append(_port); + sb.append("/").append(_portSource); + sb.append('}'); + return sb.toString(); } } - private static class Rfc7239HostPort extends HostPort + /** + * Ordered Source Enum. + *

+ * Lowest first, Last/Highest priority wins + *

+ */ + public enum Source { - Rfc7239HostPort(String authority) + UNSET, + XPROXIED_HTTPS, + XFORWARDED_PROTO, + XFORWARDED_SERVER, + XFORWARDED_PORT, + XFORWARDED_FOR, + XFORWARDED_HOST, + FORWARDED, + FORCED; + + int priority() { - super(authority); + return ordinal(); } } @@ -558,11 +740,12 @@ private class Forwarded extends QuotedCSVParser HttpConfiguration _config; Request _request; - boolean _protoRfc7239; + MutableHostPort _authority; + MutableHostPort _for; String _proto; - HostPort _for; - HostPort _host; - String _server; + Source _protoSource = Source.UNSET; + Boolean _secure; + boolean _secureScheme = false; public Forwarded(Request request, HttpConfiguration config) { @@ -570,109 +753,145 @@ public Forwarded(Request request, HttpConfiguration config) _request = request; _config = config; if (_forcedHost != null) - _host = _forcedHost.getHostPort(); + { + getAuthority().setHostPort( + _forcedHost.getHostPort().getHost(), + _forcedHost.getHostPort().getPort(), + Source.FORCED); + } + } + + public boolean isSecure() + { + return (_secure != null && _secure); + } + + public boolean hasFor() + { + return _for != null && _for._host != null; + } + + private MutableHostPort getAuthority() + { + if (_authority == null) + { + _authority = new MutableHostPort(); + } + return _authority; } - @SuppressWarnings("unused") + private MutableHostPort getFor() + { + if (_for == null) + { + _for = new MutableHostPort(); + } + return _for; + } + + /** + * Called if header is Proxy-auth-cert + */ public void handleCipherSuite(HttpField field) { _request.setAttribute("javax.servlet.request.cipher_suite", field.getValue()); + + // Is ForwardingRequestCustomizer configured to trigger isSecure and scheme change on this header? if (isSslIsSecure()) { - _request.setSecure(true); - _request.setScheme(_config.getSecureScheme()); + _secure = true; + // track desire for secure scheme, actual protocol will be resolved later. + _secureScheme = true; } } - @SuppressWarnings("unused") + /** + * Called if header is Proxy-Ssl-Id + */ public void handleSslSessionId(HttpField field) { _request.setAttribute("javax.servlet.request.ssl_session_id", field.getValue()); + + // Is ForwardingRequestCustomizer configured to trigger isSecure and scheme change on this header? if (isSslIsSecure()) { - _request.setSecure(true); - _request.setScheme(_config.getSecureScheme()); + _secure = true; + // track desire for secure scheme, actual protocol will be resolved later. + _secureScheme = true; } } - @SuppressWarnings("unused") - public void handleHost(HttpField field) + /** + * Called if header is X-Forwarded-Host + */ + public void handleForwardedHost(HttpField field) { - HostPort hostField = new HostPort(getLeftMost(field.getValue())); + updateAuthority(getLeftMost(field.getValue()), Source.XFORWARDED_HOST); + } - if (getForwardedPortAsAuthority() && !StringUtil.isEmpty(getForwardedPortHeader())) - { - if (_host == null) - _host = new PossiblyPartialHostPort(hostField.getHost(), hostField.getPort()); - else if (_host instanceof PortSetHostPort) - _host = new HostPort(hostField.getHost(), hostField.getPort() > 0 ? hostField.getPort() : _host.getPort()); - } - else if (_host == null) - { - _host = hostField; - } + /** + * Called if header is X-Forwarded-For + */ + public void handleForwardedFor(HttpField field) + { + HostPort hostField = new HostPort(getLeftMost(field.getValue())); + getFor().setHostPort(hostField, Source.XFORWARDED_FOR); } - @SuppressWarnings("unused") - public void handleServer(HttpField field) + /** + * Called if header is X-Forwarded-Server + */ + public void handleForwardedServer(HttpField field) { if (getProxyAsAuthority()) return; - _server = getLeftMost(field.getValue()); + updateAuthority(getLeftMost(field.getValue()), Source.XFORWARDED_SERVER); } - @SuppressWarnings("unused") - public void handleProto(HttpField field) + /** + * Called if header is X-Forwarded-Port + */ + public void handleForwardedPort(HttpField field) { - if (_proto == null) - _proto = getLeftMost(field.getValue()); + int port = HostPort.parsePort(getLeftMost(field.getValue())); + + updatePort(port, Source.XFORWARDED_PORT); } - @SuppressWarnings("unused") - public void handleFor(HttpField field) + /** + * Called if header is X-Forwarded-Proto + */ + public void handleProto(HttpField field) { - String authority = getLeftMost(field.getValue()); - if (!getForwardedPortAsAuthority() && !StringUtil.isEmpty(getForwardedPortHeader())) - { - if (_for == null) - _for = new PossiblyPartialHostPort(authority); - else if (_for instanceof PortSetHostPort) - _for = new HostPort(HostPort.normalizeHost(authority), _for.getPort()); - } - else if (_for == null) - { - _for = new HostPort(authority); - } + updateProto(getLeftMost(field.getValue()), Source.XFORWARDED_PROTO); } - @SuppressWarnings("unused") - public void handlePort(HttpField field) + /** + * Called if header is X-Proxied-Https + */ + public void handleHttps(HttpField field) { - int port = HostPort.parsePort(getLeftMost(field.getValue())); - if (!getForwardedPortAsAuthority()) + if ("on".equalsIgnoreCase(field.getValue()) || "true".equalsIgnoreCase(field.getValue())) + { + _secure = true; + updateProto(HttpScheme.HTTPS.asString(), Source.XPROXIED_HTTPS); + updatePort(getSecurePort(_config), Source.XPROXIED_HTTPS); + } + else if ("off".equalsIgnoreCase(field.getValue()) || "false".equalsIgnoreCase(field.getValue())) { - if (_for == null) - _for = new PortSetHostPort(_request.getRemoteHost(), port); - else if (_for instanceof PossiblyPartialHostPort && _for.getPort() <= 0) - _for = new HostPort(HostPort.normalizeHost(_for.getHost()), port); + _secure = false; + updateProto(HttpScheme.HTTP.asString(), Source.XPROXIED_HTTPS); + updatePort(MutableHostPort.IMPLIED, Source.XPROXIED_HTTPS); } else { - if (_host == null) - _host = new PortSetHostPort(_request.getServerName(), port); - else if (_host instanceof PossiblyPartialHostPort && _host.getPort() <= 0) - _host = new HostPort(HostPort.normalizeHost(_host.getHost()), port); + throw new BadMessageException("Invalid value for " + field.getName()); } } - @SuppressWarnings("unused") - public void handleHttps(HttpField field) - { - if (_proto == null && ("on".equalsIgnoreCase(field.getValue()) || "true".equalsIgnoreCase(field.getValue()))) - _proto = HttpScheme.HTTPS.asString(); - } - - @SuppressWarnings("unused") + /** + * Called if header is Forwarded + */ public void handleRFC7239(HttpField field) { addValue(field.getValue()); @@ -688,34 +907,68 @@ protected void parsedParam(StringBuffer buffer, int valueLength, int paramName, switch (name) { case "by": + { if (!getProxyAsAuthority()) break; if (value.startsWith("_") || "unknown".equals(value)) break; - if (_host == null || !(_host instanceof Rfc7239HostPort)) - _host = new Rfc7239HostPort(value); + HostPort hostField = new HostPort(value); + getAuthority().setHostPort(hostField.getHost(), hostField.getPort(), Source.FORWARDED); break; + } case "for": + { if (value.startsWith("_") || "unknown".equals(value)) break; - if (_for == null || !(_for instanceof Rfc7239HostPort)) - _for = new Rfc7239HostPort(value); + HostPort hostField = new HostPort(value); + getFor().setHostPort(hostField.getHost(), hostField.getPort(), Source.FORWARDED); break; + } case "host": + { if (value.startsWith("_") || "unknown".equals(value)) break; - if (_host == null || !(_host instanceof Rfc7239HostPort)) - _host = new Rfc7239HostPort(value); + HostPort hostField = new HostPort(value); + getAuthority().setHostPort(hostField.getHost(), hostField.getPort(), Source.FORWARDED); break; + } case "proto": - if (_proto == null || !_protoRfc7239) - { - _protoRfc7239 = true; - _proto = value; - } + updateProto(value, Source.FORWARDED); break; } } } + + private void updateAuthority(String value, Source source) + { + HostPort hostField = new HostPort(value); + getAuthority().setHostPort(hostField, source); + } + + private void updatePort(int port, Source source) + { + if (getForwardedPortAsAuthority()) + { + getAuthority().setPort(port, source); + } + else + { + getFor().setPort(port, source); + } + } + + private void updateProto(String proto, Source source) + { + if (source.priority() > _protoSource.priority()) + { + _proto = proto; + _protoSource = source; + + if (_proto.equalsIgnoreCase(_config.getSecureScheme())) + { + _secure = true; + } + } + } } } diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/HomeBaseWarning.java b/jetty-server/src/main/java/org/eclipse/jetty/server/HomeBaseWarning.java index 1efaf1e5bd80..967e78e63ac2 100644 --- a/jetty-server/src/main/java/org/eclipse/jetty/server/HomeBaseWarning.java +++ b/jetty-server/src/main/java/org/eclipse/jetty/server/HomeBaseWarning.java @@ -68,7 +68,7 @@ public HomeBaseWarning() { StringBuilder warn = new StringBuilder(); warn.append("This instance of Jetty is not running from a separate {jetty.base} directory"); - warn.append(", this is not recommended. See documentation at http://www.eclipse.org/jetty/documentation/current/startup.html"); + warn.append(", this is not recommended. See documentation at https://www.eclipse.org/jetty/documentation/current/startup.html"); LOG.warn("{}", warn.toString()); } } diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/Request.java b/jetty-server/src/main/java/org/eclipse/jetty/server/Request.java index 5ca2bc8b9338..c751cfafe0d2 100644 --- a/jetty-server/src/main/java/org/eclipse/jetty/server/Request.java +++ b/jetty-server/src/main/java/org/eclipse/jetty/server/Request.java @@ -195,7 +195,7 @@ public static Request getBaseRequest(ServletRequest request) private String _servletPath; private String _pathInfo; private boolean _secure; - private String _asyncNotSupportedSource = null; + private Object _asyncNotSupportedSource = null; private boolean _newContext; private boolean _cookiesExtracted = false; private boolean _handled = false; @@ -1623,6 +1623,9 @@ public HttpSession getSession(boolean create) throw new IllegalStateException("No SessionManager"); _session = _sessionHandler.newHttpSession(this); + if (_session == null) + throw new IllegalStateException("Create session failed"); + HttpCookie cookie = _sessionHandler.getSessionCookie(_session, getContextPath(), isSecure()); if (cookie != null) _channel.getResponse().replaceCookie(cookie); @@ -1949,7 +1952,7 @@ public void removeEventListener(final EventListener listener) _requestAttributeListeners.remove(listener); } - public void setAsyncSupported(boolean supported, String source) + public void setAsyncSupported(boolean supported, Object source) { _asyncNotSupportedSource = supported ? null : (source == null ? "unknown" : source); } diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/Server.java b/jetty-server/src/main/java/org/eclipse/jetty/server/Server.java index ae3ab7df2a50..404cc69815a5 100644 --- a/jetty-server/src/main/java/org/eclipse/jetty/server/Server.java +++ b/jetty-server/src/main/java/org/eclipse/jetty/server/Server.java @@ -376,7 +376,7 @@ protected void doStart() throws Exception if (!Jetty.STABLE) { LOG.warn("THIS IS NOT A STABLE RELEASE! DO NOT USE IN PRODUCTION!"); - LOG.warn("Download a stable release from http://download.eclipse.org/jetty/"); + LOG.warn("Download a stable release from https://download.eclipse.org/jetty/"); } HttpGenerator.setJettyVersion(HttpConfiguration.SERVER_VERSION); diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/handler/DefaultHandler.java b/jetty-server/src/main/java/org/eclipse/jetty/server/handler/DefaultHandler.java index f1973f8dbfd1..b4b1577e62ff 100644 --- a/jetty-server/src/main/java/org/eclipse/jetty/server/handler/DefaultHandler.java +++ b/jetty-server/src/main/java/org/eclipse/jetty/server/handler/DefaultHandler.java @@ -190,8 +190,8 @@ public void handle(String target, Request baseRequest, HttpServletRequest reques } writer.append("

\n"); - writer.append("\"icon\" "); - writer.append("Powered by Eclipse Jetty:// Server
\n"); + writer.append("\"icon\" "); + writer.append("Powered by Eclipse Jetty:// Server
\n"); writer.append("\n\n"); writer.flush(); byte[] content = outputStream.toByteArray(); diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/handler/gzip/GzipHandler.java b/jetty-server/src/main/java/org/eclipse/jetty/server/handler/gzip/GzipHandler.java index 72b987a7ed9f..516c556b89f0 100644 --- a/jetty-server/src/main/java/org/eclipse/jetty/server/handler/gzip/GzipHandler.java +++ b/jetty-server/src/main/java/org/eclipse/jetty/server/handler/gzip/GzipHandler.java @@ -421,6 +421,7 @@ public void addIncludedPaths(String... pathspecs) protected void doStart() throws Exception { _deflaterPool = newDeflaterPool(_poolCapacity); + addBean(_deflaterPool); _vary = (_agentPatterns.size() > 0) ? GzipHttpOutputInterceptor.VARY_ACCEPT_ENCODING_USER_AGENT : GzipHttpOutputInterceptor.VARY_ACCEPT_ENCODING; super.doStart(); } diff --git a/jetty-server/src/main/java/org/eclipse/jetty/server/session/DefaultSessionCache.java b/jetty-server/src/main/java/org/eclipse/jetty/server/session/DefaultSessionCache.java index 9670dbed621c..4ffd22debfa8 100644 --- a/jetty-server/src/main/java/org/eclipse/jetty/server/session/DefaultSessionCache.java +++ b/jetty-server/src/main/java/org/eclipse/jetty/server/session/DefaultSessionCache.java @@ -92,10 +92,7 @@ public Session doGet(String id) { if (id == null) return null; - - Session session = _sessions.get(id); - - return session; + return _sessions.get(id); } @Override @@ -177,21 +174,18 @@ public void shutdown() @Override public Session newSession(HttpServletRequest request, SessionData data) { - Session s = new Session(getSessionHandler(), request, data); - return s; + return new Session(getSessionHandler(), request, data); } @Override public Session newSession(SessionData data) { - Session s = new Session(getSessionHandler(), data); - return s; + return new Session(getSessionHandler(), data); } @Override public boolean doReplace(String id, Session oldValue, Session newValue) { - boolean result = _sessions.replace(id, oldValue, newValue); - return result; + return _sessions.replace(id, oldValue, newValue); } } diff --git a/jetty-server/src/test/java/org/eclipse/jetty/server/CheckReverseProxyHeadersTest.java b/jetty-server/src/test/java/org/eclipse/jetty/server/CheckReverseProxyHeadersTest.java deleted file mode 100644 index 87dd5ca50b11..000000000000 --- a/jetty-server/src/test/java/org/eclipse/jetty/server/CheckReverseProxyHeadersTest.java +++ /dev/null @@ -1,200 +0,0 @@ -// -// ======================================================================== -// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others. -// ------------------------------------------------------------------------ -// All rights reserved. This program and the accompanying materials -// are made available under the terms of the Eclipse Public License v1.0 -// and Apache License v2.0 which accompanies this distribution. -// -// The Eclipse Public License is available at -// http://www.eclipse.org/legal/epl-v10.html -// -// The Apache License v2.0 is available at -// http://www.opensource.org/licenses/apache2.0.php -// -// You may elect to redistribute this code under either of these licenses. -// ======================================================================== -// - -package org.eclipse.jetty.server; - -import java.io.IOException; -import javax.servlet.ServletException; -import javax.servlet.http.HttpServletRequest; -import javax.servlet.http.HttpServletResponse; - -import org.eclipse.jetty.server.handler.AbstractHandler; -import org.junit.jupiter.api.Test; - -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertFalse; -import static org.junit.jupiter.api.Assertions.assertTrue; - -/** - * - */ -public class CheckReverseProxyHeadersTest -{ - @Test - public void testCheckReverseProxyHeaders() throws Exception - { - // Classic ProxyPass from example.com:80 to localhost:8080 - testRequest("Host: localhost:8080\n" + - "X-Forwarded-For: 10.20.30.40\n" + - "X-Forwarded-Host: example.com", request -> - { - assertEquals("example.com", request.getServerName()); - assertEquals(80, request.getServerPort()); - assertEquals("10.20.30.40", request.getRemoteAddr()); - assertEquals("10.20.30.40", request.getRemoteHost()); - assertEquals("example.com", request.getHeader("Host")); - assertEquals("http", request.getScheme()); - assertFalse(request.isSecure()); - }); - - // IPv6 ProxyPass from example.com:80 to localhost:8080 - testRequest("Host: localhost:8080\n" + - "X-Forwarded-For: 10.20.30.40\n" + - "X-Forwarded-Host: [::1]", request -> - { - assertEquals("[::1]", request.getServerName()); - assertEquals(80, request.getServerPort()); - assertEquals("10.20.30.40", request.getRemoteAddr()); - assertEquals("10.20.30.40", request.getRemoteHost()); - assertEquals("[::1]", request.getHeader("Host")); - assertEquals("http", request.getScheme()); - assertFalse(request.isSecure()); - }); - - // IPv6 ProxyPass from example.com:80 to localhost:8080 - testRequest("Host: localhost:8080\n" + - "X-Forwarded-For: 10.20.30.40\n" + - "X-Forwarded-Host: [::1]:8888", request -> - { - assertEquals("[::1]", request.getServerName()); - assertEquals(8888, request.getServerPort()); - assertEquals("10.20.30.40", request.getRemoteAddr()); - assertEquals("10.20.30.40", request.getRemoteHost()); - assertEquals("[::1]:8888", request.getHeader("Host")); - assertEquals("http", request.getScheme()); - assertFalse(request.isSecure()); - }); - - // ProxyPass from example.com:81 to localhost:8080 - testRequest("Host: localhost:8080\n" + - "X-Forwarded-For: 10.20.30.40\n" + - "X-Forwarded-Host: example.com:81\n" + - "X-Forwarded-Server: example.com\n" + - "X-Forwarded-Proto: https", request -> - { - assertEquals("example.com", request.getServerName()); - assertEquals(81, request.getServerPort()); - assertEquals("10.20.30.40", request.getRemoteAddr()); - assertEquals("10.20.30.40", request.getRemoteHost()); - assertEquals("example.com:81", request.getHeader("Host")); - assertEquals("https", request.getScheme()); - assertTrue(request.isSecure()); - - }); - - // Multiple ProxyPass from example.com:80 to rp.example.com:82 to localhost:8080 - testRequest("Host: localhost:8080\n" + - "X-Forwarded-For: 10.20.30.40, 10.0.0.1\n" + - "X-Forwarded-Host: example.com, rp.example.com:82\n" + - "X-Forwarded-Server: example.com, rp.example.com\n" + - "X-Forwarded-Proto: https, http", request -> - { - assertEquals("example.com", request.getServerName()); - assertEquals(443, request.getServerPort()); - assertEquals("10.20.30.40", request.getRemoteAddr()); - assertEquals("10.20.30.40", request.getRemoteHost()); - assertEquals("example.com", request.getHeader("Host")); - assertEquals("https", request.getScheme()); - assertTrue(request.isSecure()); - }); - } - - private void testRequest(String headers, RequestValidator requestValidator) throws Exception - { - Server server = new Server(); - // Activate reverse proxy headers checking - HttpConnectionFactory http = new HttpConnectionFactory(); - http.getHttpConfiguration().addCustomizer(new ForwardedRequestCustomizer()); - - LocalConnector connector = new LocalConnector(server, http); - - server.setConnectors(new Connector[]{connector}); - ValidationHandler validationHandler = new ValidationHandler(requestValidator); - server.setHandler(validationHandler); - - try - { - server.start(); - connector.getResponse("GET / HTTP/1.1\r\n" + "Connection: close\r\n" + headers + "\r\n\r\n"); - Error error = validationHandler.getError(); - - if (error != null) - { - throw error; - } - } - finally - { - server.stop(); - } - } - - /** - * Interface for validate a wrapped request. - */ - private static interface RequestValidator - { - /** - * Validate the current request. - * - * @param request the request. - */ - void validate(HttpServletRequest request); - } - - /** - * Handler for validation. - */ - private static class ValidationHandler extends AbstractHandler - { - private final RequestValidator _requestValidator; - private Error _error; - - private ValidationHandler(RequestValidator requestValidator) - { - _requestValidator = requestValidator; - } - - /** - * Retrieve the validation error. - * - * @return the validation error or null if there was no error. - */ - public Error getError() - { - return _error; - } - - @Override - public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException - { - try - { - _requestValidator.validate(request); - } - catch (Error e) - { - _error = e; - } - catch (Throwable e) - { - _error = new Error(e); - } - } - } -} diff --git a/jetty-server/src/test/java/org/eclipse/jetty/server/ForwardedRequestCustomizerTest.java b/jetty-server/src/test/java/org/eclipse/jetty/server/ForwardedRequestCustomizerTest.java index 63c0d42ead55..b5e90fad16ec 100644 --- a/jetty-server/src/test/java/org/eclipse/jetty/server/ForwardedRequestCustomizerTest.java +++ b/jetty-server/src/test/java/org/eclipse/jetty/server/ForwardedRequestCustomizerTest.java @@ -32,7 +32,6 @@ import org.eclipse.jetty.server.handler.AbstractHandler; import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.BeforeEach; -import org.junit.jupiter.api.Test; import org.junit.jupiter.params.ParameterizedTest; import org.junit.jupiter.params.provider.Arguments; import org.junit.jupiter.params.provider.MethodSource; @@ -46,8 +45,10 @@ public class ForwardedRequestCustomizerTest private Server server; private RequestHandler handler; private LocalConnector connector; + private LocalConnector connectorAlt; private LocalConnector connectorConfigured; private ForwardedRequestCustomizer customizer; + private ForwardedRequestCustomizer customizerAlt; private ForwardedRequestCustomizer customizerConfigured; private static class Actual @@ -72,21 +73,22 @@ public void init() throws Exception // Default behavior Connector HttpConnectionFactory http = new HttpConnectionFactory(); - http.setInputBufferSize(1024); - http.getHttpConfiguration().setRequestHeaderSize(512); - http.getHttpConfiguration().setResponseHeaderSize(512); - http.getHttpConfiguration().setOutputBufferSize(2048); + http.getHttpConfiguration().setSecurePort(443); customizer = new ForwardedRequestCustomizer(); http.getHttpConfiguration().addCustomizer(customizer); connector = new LocalConnector(server, http); server.addConnector(connector); + // Alternate behavior Connector + HttpConnectionFactory httpAlt = new HttpConnectionFactory(); + httpAlt.getHttpConfiguration().setSecurePort(8443); + customizerAlt = new ForwardedRequestCustomizer(); + httpAlt.getHttpConfiguration().addCustomizer(customizerAlt); + connectorAlt = new LocalConnector(server, httpAlt); + server.addConnector(connectorAlt); + // Configured behavior Connector http = new HttpConnectionFactory(); - http.setInputBufferSize(1024); - http.getHttpConfiguration().setRequestHeaderSize(512); - http.getHttpConfiguration().setResponseHeaderSize(512); - http.getHttpConfiguration().setOutputBufferSize(2048); customizerConfigured = new ForwardedRequestCustomizer(); customizerConfigured.setForwardedHeader("Jetty-Forwarded"); customizerConfigured.setForwardedHostHeader("Jetty-Forwarded-Host"); @@ -132,6 +134,51 @@ public void destroy() throws Exception public static Stream cases() { return Stream.of( + // HTTP 1.0 + Arguments.of( + new Request("HTTP/1.0 - no Host header") + .headers( + "GET /example HTTP/1.0" + ), + new Expectations() + .scheme("http").serverName("0.0.0.0").serverPort(80) + .secure(false) + .requestURL("http://0.0.0.0/example") + ), + Arguments.of( + new Request("HTTP/1.0 - Empty Host header") + .headers( + "GET /example HTTP/1.0", + "Host:" + ), + new Expectations() + .scheme("http").serverName("0.0.0.0").serverPort(80) + .secure(false) + .requestURL("http://0.0.0.0/example") + ), + Arguments.of( + new Request("HTTP/1.0 - No Host header, with X-Forwarded-Host") + .headers( + "GET /example HTTP/1.0", + "X-Forwarded-Host: alt.example.net:7070" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(7070) + .secure(false) + .requestURL("http://alt.example.net:7070/example") + ), + Arguments.of( + new Request("HTTP/1.0 - Empty Host header, with X-Forwarded-Host") + .headers( + "GET /example HTTP/1.0", + "Host:", + "X-Forwarded-Host: alt.example.net:7070" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(7070) + .secure(false) + .requestURL("http://alt.example.net:7070/example") + ), // Host IPv4 Arguments.of( new Request("IPv4 Host Only") @@ -141,6 +188,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("1.2.3.4").serverPort(2222) + .secure(false) .requestURL("http://1.2.3.4:2222/") ), Arguments.of(new Request("IPv6 Host Only") @@ -150,16 +198,18 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("[::1]").serverPort(2222) + .secure(false) .requestURL("http://[::1]:2222/") ), Arguments.of(new Request("IPv4 in Request Line") .headers( - "GET http://1.2.3.4:2222/ HTTP/1.1", + "GET https://1.2.3.4:2222/ HTTP/1.1", "Host: wrong" ), new Expectations() - .scheme("http").serverName("1.2.3.4").serverPort(2222) - .requestURL("http://1.2.3.4:2222/") + .scheme("https").serverName("1.2.3.4").serverPort(2222) + .secure(true) + .requestURL("https://1.2.3.4:2222/") ), Arguments.of(new Request("IPv6 in Request Line") .headers( @@ -168,6 +218,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("[::1]").serverPort(2222) + .secure(false) .requestURL("http://[::1]:2222/") ), @@ -184,6 +235,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("[2001:db8:cafe::17]").remotePort(4711) ), @@ -197,6 +249,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("192.0.2.43").remotePort(0) ), @@ -210,6 +263,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("192.0.2.43").remotePort(0) ), @@ -224,6 +278,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("192.0.2.43").remotePort(0) ), @@ -237,6 +292,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("192.0.2.43").remotePort(0) ), @@ -248,6 +304,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("192.0.2.43").remotePort(0) ), @@ -261,6 +318,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("example.com").serverPort(80) + .secure(false) .requestURL("http://example.com/") .remoteAddr("192.0.2.43").remotePort(0) ), @@ -274,9 +332,93 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("myhost").serverPort(443) + .secure(true) .requestURL("https://myhost/") ), + // ================================================================= + // ProxyPass usages + Arguments.of(new Request("ProxyPass (example.com:80 to localhost:8080)") + .headers( + "GET / HTTP/1.1", + "Host: localhost:8080", + "X-Forwarded-For: 10.20.30.40", + "X-Forwarded-Host: example.com" + ), + new Expectations() + .scheme("http").serverName("example.com").serverPort(80) + .secure(false) + .remoteAddr("10.20.30.40") + .requestURL("http://example.com/") + ), + Arguments.of(new Request("ProxyPass (example.com:81 to localhost:8080)") + .headers( + "GET / HTTP/1.1", + "Host: localhost:8080", + "X-Forwarded-For: 10.20.30.40", + "X-Forwarded-Host: example.com:81", + "X-Forwarded-Server: example.com", + "X-Forwarded-Proto: https" + ), + new Expectations() + .scheme("https").serverName("example.com").serverPort(81) + .secure(true) + .remoteAddr("10.20.30.40") + .requestURL("https://example.com:81/") + ), + Arguments.of(new Request("ProxyPass (example.com:443 to localhost:8443)") + .headers( + "GET / HTTP/1.1", + "Host: localhost:8443", + "X-Forwarded-Host: example.com", + "X-Forwarded-Proto: https" + ), + new Expectations() + .scheme("https").serverName("example.com").serverPort(443) + .secure(true) + .requestURL("https://example.com/") + ), + Arguments.of(new Request("ProxyPass (IPv6 from [::1]:80 to localhost:8080)") + .headers( + "GET / HTTP/1.1", + "Host: localhost:8080", + "X-Forwarded-For: 10.20.30.40", + "X-Forwarded-Host: [::1]" + ), + new Expectations() + .scheme("http").serverName("[::1]").serverPort(80) + .secure(false) + .remoteAddr("10.20.30.40") + .requestURL("http://[::1]/") + ), + Arguments.of(new Request("ProxyPass (IPv6 from [::1]:8888 to localhost:8080)") + .headers( + "GET / HTTP/1.1", + "Host: localhost:8080", + "X-Forwarded-For: 10.20.30.40", + "X-Forwarded-Host: [::1]:8888" + ), + new Expectations() + .scheme("http").serverName("[::1]").serverPort(8888) + .secure(false) + .remoteAddr("10.20.30.40") + .requestURL("http://[::1]:8888/") + ), + Arguments.of(new Request("Multiple ProxyPass (example.com:80 to rp.example.com:82 to localhost:8080)") + .headers( + "GET / HTTP/1.1", + "Host: localhost:8080", + "X-Forwarded-For: 10.20.30.40, 10.0.0.1", + "X-Forwarded-Host: example.com, rp.example.com:82", + "X-Forwarded-Server: example.com, rp.example.com", + "X-Forwarded-Proto: https, http" + ), + new Expectations() + .scheme("https").serverName("example.com").serverPort(443) + .secure(true) + .remoteAddr("10.20.30.40") + .requestURL("https://example.com/") + ), // ================================================================= // X-Forwarded-* usages Arguments.of(new Request("X-Forwarded-Proto (old syntax)") @@ -287,6 +429,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("myhost").serverPort(443) + .secure(true) .requestURL("https://myhost/") ), Arguments.of(new Request("X-Forwarded-For (multiple headers)") @@ -298,6 +441,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("10.9.8.7").remotePort(0) ), @@ -309,6 +453,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("10.9.8.7").remotePort(1111) ), @@ -320,6 +465,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("[2001:db8:cafe::17]").remotePort(1111) ), @@ -332,6 +478,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(2222) + .secure(false) .requestURL("http://myhost:2222/") .remoteAddr("[1:2:3:4:5:6:7:8]").remotePort(0) ), @@ -346,6 +493,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(2222) + .secure(false) .requestURL("http://myhost:2222/") .remoteAddr("[1:2:3:4:5:6:7:8]").remotePort(0) ), @@ -358,6 +506,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(2222) + .secure(false) .requestURL("http://myhost:2222/") .remoteAddr("[1:2:3:4:5:6:7:8]").remotePort(0) ), @@ -370,6 +519,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(4444) + .secure(false) .requestURL("http://myhost:4444/") .remoteAddr("192.168.1.200").remotePort(0) ), @@ -383,6 +533,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("192.168.1.200").remotePort(4444) ), @@ -395,6 +546,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(4444) + .secure(false) .requestURL("http://myhost:4444/") .remoteAddr("192.168.1.200").remotePort(0) ), @@ -409,6 +561,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("www.example.com").serverPort(4333) + .secure(true) .requestURL("https://www.example.com:4333/") .remoteAddr("8.5.4.3").remotePort(2222) ), @@ -423,6 +576,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("www.example.com").serverPort(4333) + .secure(true) .requestURL("https://www.example.com:4333/") .remoteAddr("8.5.4.3").remotePort(2222) ), @@ -438,6 +592,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("www.example.com").serverPort(4333) + .secure(true) .requestURL("https://www.example.com:4333/") .remoteAddr("8.5.4.3").remotePort(2222) ), @@ -453,6 +608,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("www.example.com").serverPort(4333) + .secure(true) .requestURL("https://www.example.com:4333/") .remoteAddr("8.5.4.3").remotePort(2222) ), @@ -468,6 +624,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("www.example.com").serverPort(4333) + .secure(true) .requestURL("https://www.example.com:4333/") .remoteAddr("8.5.4.3").remotePort(2222) ), @@ -481,6 +638,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("fw.example.com").serverPort(4333) + .secure(false) .requestURL("http://fw.example.com:4333/") .remoteAddr("8.5.4.3").remotePort(2222) ), @@ -494,6 +652,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("fw.example.com").serverPort(4333) + .secure(false) .requestURL("http://fw.example.com:4333/") .remoteAddr("8.5.4.3").remotePort(2222) ), @@ -509,6 +668,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("sub1.example.com").serverPort(10003) + .secure(true) .requestURL("https://sub1.example.com:10003/") .remoteAddr("127.0.0.1").remotePort(8888) ), @@ -524,6 +684,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("sub1.example.com").serverPort(10003) + .secure(true) .requestURL("https://sub1.example.com:10003/") .remoteAddr("127.0.0.1").remotePort(8888) ), @@ -540,6 +701,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("sub1.example.com").serverPort(10003) + .secure(true) .requestURL("https://sub1.example.com:10003/") .remoteAddr("127.0.0.1").remotePort(8888) ), @@ -555,6 +717,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("sub1.example.com").serverPort(10003) + .secure(true) .requestURL("https://sub1.example.com:10003/") .remoteAddr("127.0.0.1").remotePort(8888) ), @@ -571,10 +734,65 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("example.com").serverPort(80) + .secure(false) .requestURL("http://example.com/") .remoteAddr("192.0.2.43").remotePort(0) ), - + Arguments.of( + new Request("RFC7239 - mixed with HTTP/1.0 - No Host header") + .headers( + "GET /example HTTP/1.0", + "Forwarded: for=1.1.1.1:6060,proto=http;host=alt.example.net:7070" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(7070) + .secure(false) + .requestURL("http://alt.example.net:7070/example") + .remoteAddr("1.1.1.1").remotePort(6060) + ), + Arguments.of( + new Request("RFC7239 - mixed with HTTP/1.0 - Empty Host header") + .headers( + "GET /example HTTP/1.0", + "Host:", + "Forwarded: for=1.1.1.1:6060,proto=http;host=alt.example.net:7070" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(7070) + .secure(false) + .requestURL("http://alt.example.net:7070/example") + .remoteAddr("1.1.1.1").remotePort(6060) + ), + // ================================================================= + // Forced Behavior + Arguments.of(new Request("Forced Host (no port)") + .configureCustomizer((customizer) -> customizer.setForcedHost("always.example.com")) + .headers( + "GET / HTTP/1.1", + "Host: myhost", + "X-Forwarded-For: 11.9.8.7:1111", + "X-Forwarded-Host: example.com:2222" + ), + new Expectations() + .scheme("http").serverName("always.example.com").serverPort(80) + .secure(false) + .requestURL("http://always.example.com/") + .remoteAddr("11.9.8.7").remotePort(1111) + ), + Arguments.of(new Request("Forced Host with port") + .configureCustomizer((customizer) -> customizer.setForcedHost("always.example.com:9090")) + .headers( + "GET / HTTP/1.1", + "Host: myhost", + "X-Forwarded-For: 11.9.8.7:1111", + "X-Forwarded-Host: example.com:2222" + ), + new Expectations() + .scheme("http").serverName("always.example.com").serverPort(9090) + .secure(false) + .requestURL("http://always.example.com:9090/") + .remoteAddr("11.9.8.7").remotePort(1111) + ), // ================================================================= // Legacy Headers Arguments.of(new Request("X-Proxied-Https") @@ -585,6 +803,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("myhost").serverPort(443) + .secure(true) .requestURL("https://myhost/") .remoteAddr("0.0.0.0").remotePort(0) ), @@ -597,6 +816,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("0.0.0.0").remotePort(0) .sslSession("Wibble") @@ -610,6 +830,7 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("myhost").serverPort(443) + .secure(true) .requestURL("https://myhost/") .remoteAddr("0.0.0.0").remotePort(0) .sslSession("0123456789abcdef") @@ -623,6 +844,7 @@ public static Stream cases() ), new Expectations() .scheme("http").serverName("myhost").serverPort(80) + .secure(false) .requestURL("http://myhost/") .remoteAddr("0.0.0.0").remotePort(0) .sslCertificate("Wibble") @@ -636,9 +858,121 @@ public static Stream cases() ), new Expectations() .scheme("https").serverName("myhost").serverPort(443) + .secure(true) .requestURL("https://myhost/") .remoteAddr("0.0.0.0").remotePort(0) .sslCertificate("0123456789abcdef") + ), + // ================================================================= + // Complicated scenarios + Arguments.of(new Request("No initial authority, X-Forwarded-Proto on http, Proxy-Ssl-Id exists (setSslIsSecure==true)") + .configureCustomizer((customizer) -> customizer.setSslIsSecure(true)) + .headers( + "GET /foo HTTP/1.1", + "Host: myhost", + "X-Forwarded-Proto: http", + "Proxy-Ssl-Id: Wibble" + ), + new Expectations() + .scheme("http").serverName("myhost").serverPort(80) + .secure(true) + .requestURL("http://myhost/foo") + .remoteAddr("0.0.0.0").remotePort(0) + .sslSession("Wibble") + ), + Arguments.of(new Request("https initial authority, X-Forwarded-Proto on http, Proxy-Ssl-Id exists (setSslIsSecure==false)") + .configureCustomizer((customizer) -> customizer.setSslIsSecure(false)) + .headers( + "GET https://alt.example.net/foo HTTP/1.1", + "Host: myhost", + "X-Forwarded-Proto: http", + "Proxy-Ssl-Id: Wibble" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(80) + .secure(false) + .requestURL("http://alt.example.net/foo") + .remoteAddr("0.0.0.0").remotePort(0) + .sslSession("Wibble") + ), + Arguments.of(new Request("No initial authority, X-Proxied-Https off, Proxy-Ssl-Id exists (setSslIsSecure==true)") + .configureCustomizer((customizer) -> customizer.setSslIsSecure(true)) + .headers( + "GET /foo HTTP/1.1", + "Host: myhost", + "X-Proxied-Https: off", // this wins for scheme and secure + "Proxy-Ssl-Id: Wibble" + ), + new Expectations() + .scheme("http").serverName("myhost").serverPort(80) + .secure(false) + .requestURL("http://myhost/foo") + .remoteAddr("0.0.0.0").remotePort(0) + .sslSession("Wibble") + ), + Arguments.of(new Request("Https initial authority, X-Proxied-Https off, Proxy-Ssl-Id exists (setSslIsSecure==true)") + .configureCustomizer((customizer) -> customizer.setSslIsSecure(true)) + .headers( + "GET https://alt.example.net/foo HTTP/1.1", + "Host: myhost", + "X-Proxied-Https: off", // this wins for scheme and secure + "Proxy-Ssl-Id: Wibble" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(80) + .secure(false) + .requestURL("http://alt.example.net/foo") + .remoteAddr("0.0.0.0").remotePort(0) + .sslSession("Wibble") + ), + Arguments.of(new Request("Https initial authority, X-Proxied-Https off, Proxy-Ssl-Id exists (setSslIsSecure==true) (alt order)") + .configureCustomizer((customizer) -> customizer.setSslIsSecure(true)) + .headers( + "GET https://alt.example.net/foo HTTP/1.1", + "Host: myhost", + "Proxy-Ssl-Id: Wibble", + "X-Proxied-Https: off" // this wins for scheme and secure + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(80) + .secure(false) + .requestURL("http://alt.example.net/foo") + .remoteAddr("0.0.0.0").remotePort(0) + .sslSession("Wibble") + ), + Arguments.of(new Request("Http initial authority, X-Proxied-Https off, Proxy-Ssl-Id exists (setSslIsSecure==false)") + .configureCustomizer((customizer) -> customizer.setSslIsSecure(false)) + .headers( + "GET https://alt.example.net/foo HTTP/1.1", + "Host: myhost", + "X-Proxied-Https: off", + "Proxy-Ssl-Id: Wibble", + "Proxy-auth-cert: 0123456789abcdef" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(80) + .secure(false) + .requestURL("http://alt.example.net/foo") + .remoteAddr("0.0.0.0").remotePort(0) + .sslSession("Wibble") + .sslCertificate("0123456789abcdef") + ), + Arguments.of(new Request("Http initial authority, X-Proxied-Https off, Proxy-Ssl-Id exists (setSslIsSecure==false) (alt)") + .configureCustomizer((customizer) -> customizer.setSslIsSecure(false)) + .headers( + "GET https://alt.example.net/foo HTTP/1.1", + "Host: myhost", + "Proxy-Ssl-Id: Wibble", + "Proxy-auth-cert: 0123456789abcdef", + "X-Proxied-Https: off" + ), + new Expectations() + .scheme("http").serverName("alt.example.net").serverPort(80) + .secure(false) + .requestURL("http://alt.example.net/foo") + .remoteAddr("0.0.0.0").remotePort(0) + .sslSession("Wibble") + .sslCertificate("0123456789abcdef") ) ); } @@ -650,7 +984,7 @@ public void testDefaultBehavior(Request request, Expectations expectations) thro request.configure(customizer); String rawRequest = request.getRawRequest((header) -> header); - System.out.println(rawRequest); + // System.out.println(rawRequest); HttpTester.Response response = HttpTester.parseResponse(connector.getResponse(rawRequest)); assertThat("status", response.getStatus(), is(200)); @@ -670,7 +1004,7 @@ public void testConfiguredBehavior(Request request, Expectations expectations) t .replaceFirst("X-Proxied-Https:", "Jetty-Proxied-Https:") .replaceFirst("Proxy-Ssl-Id:", "Jetty-Proxy-Ssl-Id:") .replaceFirst("Proxy-auth-cert:", "Jetty-Proxy-Auth-Cert:")); - System.out.println(rawRequest); + // System.out.println(rawRequest); HttpTester.Response response = HttpTester.parseResponse(connectorConfigured.getResponse(rawRequest)); assertThat("status", response.getStatus(), is(200)); @@ -678,20 +1012,94 @@ public void testConfiguredBehavior(Request request, Expectations expectations) t expectations.accept(actual); } - @Test - public void testBadInput() throws Exception + public static Stream nonStandardPortCases() { - Request request = new Request("Bad port value") - .headers( - "GET / HTTP/1.1", - "Host: myhost", - "X-Forwarded-Port: " - ); + return Stream.of( + // RFC7239 Tests with https. + Arguments.of(new Request("RFC7239 with https and h2") + .headers( + "GET /test/forwarded.jsp HTTP/1.1", + "Host: web.example.net", + "Forwarded: for=192.168.2.6;host=web.example.net;proto=https;proto-version=h2" + ), + new Expectations() + .scheme("https").serverName("web.example.net").serverPort(443) + .requestURL("https://web.example.net/test/forwarded.jsp") + .remoteAddr("192.168.2.6").remotePort(0) + ), + // RFC7239 Tests with https and proxy provided port + Arguments.of(new Request("RFC7239 with proxy provided port on https and h2") + .headers( + "GET /test/forwarded.jsp HTTP/1.1", + "Host: web.example.net:9443", + "Forwarded: for=192.168.2.6;host=web.example.net:9443;proto=https;proto-version=h2" + ), + new Expectations() + .scheme("https").serverName("web.example.net").serverPort(9443) + .requestURL("https://web.example.net:9443/test/forwarded.jsp") + .remoteAddr("192.168.2.6").remotePort(0) + ), + // RFC7239 Tests with https, no port in Host, but proxy provided port + Arguments.of(new Request("RFC7239 with client provided host and different proxy provided port on https and h2") + .headers( + "GET /test/forwarded.jsp HTTP/1.1", + "Host: web.example.net", + "Forwarded: for=192.168.2.6;host=new.example.net:7443;proto=https;proto-version=h2" + // Client: https://web.example.net/test/forwarded.jsp + // Proxy Requests: https://new.example.net/test/forwarded.jsp + ), + new Expectations() + .scheme("https").serverName("new.example.net").serverPort(7443) + .requestURL("https://new.example.net:7443/test/forwarded.jsp") + .remoteAddr("192.168.2.6").remotePort(0) + ) + ); + } + + /** + * Tests against a Connector with a HttpConfiguration on non-standard ports. + * HttpConfiguration is set to securePort of 8443 + */ + @ParameterizedTest(name = "{0}") + @MethodSource("nonStandardPortCases") + public void testNonStandardPortBehavior(Request request, Expectations expectations) throws Exception + { + request.configure(customizerAlt); + + String rawRequest = request.getRawRequest((header) -> header); + // System.out.println(rawRequest); + + HttpTester.Response response = HttpTester.parseResponse(connectorAlt.getResponse(rawRequest)); + assertThat("status", response.getStatus(), is(200)); + + expectations.accept(actual); + } + + public static Stream badRequestCases() + { + return Stream.of( + new Request("Bad port value") + .headers( + "GET / HTTP/1.1", + "Host: myhost", + "X-Forwarded-Port: " + ), + new Request("Invalid X-Proxied-Https value") + .headers( + "GET / HTTP/1.1", + "Host: myhost", + "X-Proxied-Https: foo" + ) + ); + } + @ParameterizedTest + @MethodSource("badRequestCases") + public void testBadInput(Request request) throws Exception + { request.configure(customizer); String rawRequest = request.getRawRequest((header) -> header); - System.out.println(rawRequest); HttpTester.Response response = HttpTester.parseResponse(connector.getResponse(rawRequest)); assertThat("status", response.getStatus(), is(400)); @@ -756,12 +1164,13 @@ private static class Expectations implements Consumer int expectedRemotePort = 0; String expectedSslSession; String expectedSslCertificate; + Boolean secure; @Override public void accept(Actual actual) { assertThat("scheme", actual.scheme.get(), is(expectedScheme)); - if (actual.scheme.get().equals("https")) + if (secure != null && secure) { assertTrue(actual.wasSecure.get(), "wasSecure"); } @@ -783,6 +1192,12 @@ public void accept(Actual actual) } } + public Expectations secure(boolean flag) + { + this.secure = flag; + return this; + } + public Expectations scheme(String scheme) { this.expectedScheme = scheme; diff --git a/jetty-servlet/pom.xml b/jetty-servlet/pom.xml index b5194c6e51a3..3ba5fd2d4cc2 100644 --- a/jetty-servlet/pom.xml +++ b/jetty-servlet/pom.xml @@ -3,13 +3,12 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-servlet Jetty :: Servlet Handling Jetty Servlet Container - http://www.eclipse.org/jetty ${project.groupId}.servlet diff --git a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/FilterHolder.java b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/FilterHolder.java index ded28c8769f9..6f4af7368b78 100644 --- a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/FilterHolder.java +++ b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/FilterHolder.java @@ -35,6 +35,7 @@ import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; +import org.eclipse.jetty.server.Request; import org.eclipse.jetty.util.TypeUtil; import org.eclipse.jetty.util.component.Dumpable; import org.eclipse.jetty.util.component.DumpableCollection; @@ -186,11 +187,24 @@ public Filter getFilter() return _filter; } - public void doFilter(ServletRequest request, ServletResponse response, - FilterChain chain) - throws IOException, ServletException + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { - _filter.doFilter(request, response, chain); + if (isAsyncSupported() || !request.isAsyncSupported()) + getFilter().doFilter(request, response, chain); + else + { + Request baseRequest = Request.getBaseRequest(request); + Objects.requireNonNull(baseRequest); + try + { + baseRequest.setAsyncSupported(false, this); + getFilter().doFilter(request, response, chain); + } + finally + { + baseRequest.setAsyncSupported(true, null); + } + } } @Override diff --git a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ListenerHolder.java b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ListenerHolder.java index ef10588e5d3c..42d4c0549a82 100644 --- a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ListenerHolder.java +++ b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ListenerHolder.java @@ -19,7 +19,6 @@ package org.eclipse.jetty.servlet; import java.util.EventListener; -import javax.servlet.ServletContext; import javax.servlet.ServletException; import org.eclipse.jetty.server.handler.ContextHandler; @@ -78,33 +77,30 @@ public void doStart() throws Exception throw new IllegalStateException(msg); } - ContextHandler contextHandler = ContextHandler.getCurrentContext().getContextHandler(); - if (contextHandler != null) + ContextHandler contextHandler = null; + if (getServletHandler() != null) + contextHandler = getServletHandler().getServletContextHandler(); + if (contextHandler == null && ContextHandler.getCurrentContext() != null) + contextHandler = ContextHandler.getCurrentContext().getContextHandler(); + if (contextHandler == null) + throw new IllegalStateException("No Context"); + + _listener = getInstance(); + if (_listener == null) { - _listener = getInstance(); - if (_listener == null) + //create an instance of the listener and decorate it + try { - //create an instance of the listener and decorate it - try - { - ServletContext context = contextHandler.getServletContext(); - _listener = (context != null) - ? context.createListener(getHeldClass()) - : getHeldClass().getDeclaredConstructor().newInstance(); - } - catch (ServletException ex) - { - Throwable cause = ex.getRootCause(); - if (cause instanceof InstantiationException) - throw (InstantiationException)cause; - if (cause instanceof IllegalAccessException) - throw (IllegalAccessException)cause; - throw ex; - } + _listener = contextHandler.getServletContext().createListener(getHeldClass()); } + catch (ServletException ex) + { + throw ex; + } + _listener = wrap(_listener, WrapFunction.class, WrapFunction::wrapEventListener); - contextHandler.addEventListener(_listener); } + contextHandler.addEventListener(_listener); } @Override diff --git a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletContextHandler.java b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletContextHandler.java index 2793b5cc7712..5607ef044e3f 100644 --- a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletContextHandler.java +++ b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletContextHandler.java @@ -190,9 +190,20 @@ public void addEventListener(EventListener listener) @Override public void setHandler(Handler handler) { - if (handler != null) - LOG.warn("ServletContextHandler.setHandler should not be called directly. Use insertHandler or setSessionHandler etc."); - super.setHandler(handler); + if (handler instanceof SessionHandler) + setSessionHandler((SessionHandler)handler); + else if (handler instanceof SecurityHandler) + setSecurityHandler((SecurityHandler)handler); + else if (handler instanceof ServletHandler) + setServletHandler((ServletHandler)handler); + else if (handler instanceof GzipHandler) + setGzipHandler((GzipHandler)handler); + else + { + if (handler != null) + LOG.warn("ServletContextHandler.setHandler should not be called directly. Use insertHandler or setSessionHandler etc."); + super.setHandler(handler); + } } private void doSetHandler(HandlerWrapper wrapper, Handler handler) diff --git a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletHandler.java b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletHandler.java index 1979d285e6ab..ba41caf32858 100644 --- a/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletHandler.java +++ b/jetty-servlet/src/main/java/org/eclipse/jetty/servlet/ServletHandler.java @@ -28,10 +28,9 @@ import java.util.List; import java.util.ListIterator; import java.util.Map; -import java.util.Queue; +import java.util.Objects; import java.util.Set; import java.util.concurrent.ConcurrentHashMap; -import java.util.concurrent.ConcurrentLinkedQueue; import java.util.concurrent.ConcurrentMap; import java.util.function.Consumer; import java.util.stream.Stream; @@ -63,7 +62,6 @@ import org.eclipse.jetty.server.handler.ContextHandler; import org.eclipse.jetty.server.handler.ScopedHandler; import org.eclipse.jetty.util.ArrayUtil; -import org.eclipse.jetty.util.LazyList; import org.eclipse.jetty.util.MultiException; import org.eclipse.jetty.util.MultiMap; import org.eclipse.jetty.util.URIUtil; @@ -101,7 +99,7 @@ public class ServletHandler extends ScopedHandler private int _matchBeforeIndex = -1; //index of last programmatic FilterMapping with isMatchAfter=false private int _matchAfterIndex = -1; //index of 1st programmatic FilterMapping with isMatchAfter=true private boolean _filterChainsCached = true; - private int _maxFilterChainsCacheSize = 512; + private int _maxFilterChainsCacheSize = 1024; private boolean _startWithUnavailable = false; private boolean _ensureDefaultServlet = true; private IdentityService _identityService; @@ -112,9 +110,9 @@ public class ServletHandler extends ScopedHandler private final Map _filterNameMap = new HashMap<>(); private List _filterPathMappings; private MultiMap _filterNameMappings; + private List _wildFilterNameMappings; private final Map _servletNameMap = new HashMap<>(); - // private PathMap _servletPathMap; private PathMappings _servletPathMap; private ListenerHolder[] _listeners = new ListenerHolder[0]; @@ -123,9 +121,6 @@ public class ServletHandler extends ScopedHandler @SuppressWarnings("unchecked") protected final ConcurrentMap[] _chainCache = new ConcurrentMap[FilterMapping.ALL]; - @SuppressWarnings("unchecked") - protected final Queue[] _chainLRU = new Queue[FilterMapping.ALL]; - /** * Constructor. */ @@ -136,7 +131,7 @@ public ServletHandler() @Override public boolean isDumpable(Object o) { - return !(o instanceof Holder || o instanceof BaseHolder || o instanceof FilterMapping || o instanceof ServletMapping); + return !(o instanceof BaseHolder || o instanceof FilterMapping || o instanceof ServletMapping); } @Override @@ -184,12 +179,6 @@ protected synchronized void doStart() _chainCache[FilterMapping.INCLUDE] = new ConcurrentHashMap<>(); _chainCache[FilterMapping.ERROR] = new ConcurrentHashMap<>(); _chainCache[FilterMapping.ASYNC] = new ConcurrentHashMap<>(); - - _chainLRU[FilterMapping.REQUEST] = new ConcurrentLinkedQueue<>(); - _chainLRU[FilterMapping.FORWARD] = new ConcurrentLinkedQueue<>(); - _chainLRU[FilterMapping.INCLUDE] = new ConcurrentLinkedQueue<>(); - _chainLRU[FilterMapping.ERROR] = new ConcurrentLinkedQueue<>(); - _chainLRU[FilterMapping.ASYNC] = new ConcurrentLinkedQueue<>(); } if (_contextHandler == null) @@ -274,14 +263,14 @@ protected synchronized void doStop() } //Retain only filters and mappings that were added using jetty api (ie Source.EMBEDDED) - FilterHolder[] fhs = (FilterHolder[])LazyList.toArray(filterHolders, FilterHolder.class); + FilterHolder[] fhs = filterHolders.toArray(new FilterHolder[0]); updateBeans(_filters, fhs); _filters = fhs; - FilterMapping[] fms = (FilterMapping[])LazyList.toArray(filterMappings, FilterMapping.class); + FilterMapping[] fms = filterMappings.toArray(new FilterMapping[0]); updateBeans(_filterMappings, fms); _filterMappings = fms; - _matchAfterIndex = (_filterMappings == null || _filterMappings.length == 0 ? -1 : _filterMappings.length - 1); + _matchAfterIndex = (_filterMappings.length == 0 ? -1 : _filterMappings.length - 1); _matchBeforeIndex = -1; // Stop servlets @@ -319,10 +308,10 @@ protected synchronized void doStop() } //Retain only Servlets and mappings added via jetty apis (ie Source.EMBEDDED) - ServletHolder[] shs = (ServletHolder[])LazyList.toArray(servletHolders, ServletHolder.class); + ServletHolder[] shs = servletHolders.toArray(new ServletHolder[0]); updateBeans(_servlets, shs); _servlets = shs; - ServletMapping[] sms = (ServletMapping[])LazyList.toArray(servletMappings, ServletMapping.class); + ServletMapping[] sms = servletMappings.toArray(new ServletMapping[0]); updateBeans(_servletMappings, sms); _servletMappings = sms; @@ -347,7 +336,7 @@ protected synchronized void doStop() listenerHolders.add(_listeners[i]); } } - ListenerHolder[] listeners = (ListenerHolder[])LazyList.toArray(listenerHolders, ListenerHolder.class); + ListenerHolder[] listeners = listenerHolders.toArray(new ListenerHolder[0]); updateBeans(_listeners, listeners); _listeners = listeners; @@ -596,8 +585,6 @@ public MappedResource getMappedServlet(String target) return _servletPathMap.getMatch(target); } - if (_servletNameMap == null) - return null; ServletHolder holder = _servletNameMap.get(target); if (holder == null) return null; @@ -609,93 +596,73 @@ protected FilterChain getFilterChain(Request baseRequest, String pathInContext, String key = pathInContext == null ? servletHolder.getName() : pathInContext; int dispatch = FilterMapping.dispatch(baseRequest.getDispatcherType()); - if (_filterChainsCached && _chainCache != null) + if (_filterChainsCached) { FilterChain chain = _chainCache[dispatch].get(key); if (chain != null) return chain; } - // Build list of filters (list of FilterHolder objects) - List filters = new ArrayList<>(); - - // Path filters - if (pathInContext != null && _filterPathMappings != null) - { - for (FilterMapping filterPathMapping : _filterPathMappings) - { - if (filterPathMapping.appliesTo(pathInContext, dispatch)) - filters.add(filterPathMapping.getFilterHolder()); - } - } + // Build the filter chain from the inside out. + // ie first wrap the servlet with the last filter to be applied. + // The mappings lists have been reversed to make this simple and fast. + FilterChain chain = null; - // Servlet name filters if (servletHolder != null && _filterNameMappings != null && !_filterNameMappings.isEmpty()) { - Object o = _filterNameMappings.get(servletHolder.getName()); + if (_wildFilterNameMappings != null) + for (FilterMapping mapping : _wildFilterNameMappings) + chain = newFilterChain(mapping.getFilterHolder(), chain == null ? new ChainEnd(servletHolder) : chain); - for (int i = 0; i < LazyList.size(o); i++) + for (FilterMapping mapping : _filterNameMappings.get(servletHolder.getName())) { - FilterMapping mapping = LazyList.get(o, i); if (mapping.appliesTo(dispatch)) - filters.add(mapping.getFilterHolder()); + chain = newFilterChain(mapping.getFilterHolder(), chain == null ? new ChainEnd(servletHolder) : chain); } + } - o = _filterNameMappings.get("*"); - for (int i = 0; i < LazyList.size(o); i++) + if (pathInContext != null && _filterPathMappings != null) + { + for (FilterMapping mapping : _filterPathMappings) { - FilterMapping mapping = LazyList.get(o, i); - if (mapping.appliesTo(dispatch)) - filters.add(mapping.getFilterHolder()); + if (mapping.appliesTo(pathInContext, dispatch)) + chain = newFilterChain(mapping.getFilterHolder(), chain == null ? new ChainEnd(servletHolder) : chain); } } - if (filters.isEmpty()) - return null; - - FilterChain chain = null; if (_filterChainsCached) { - if (!filters.isEmpty()) - chain = newCachedChain(filters, servletHolder); - final Map cache = _chainCache[dispatch]; - final Queue lru = _chainLRU[dispatch]; - // Do we have too many cached chains? - while (_maxFilterChainsCacheSize > 0 && cache.size() >= _maxFilterChainsCacheSize) + if (_maxFilterChainsCacheSize > 0 && cache.size() >= _maxFilterChainsCacheSize) { - // The LRU list is not atomic with the cache map, so be prepared to invalidate if - // a key is not found to delete. - // Delete by LRU (where U==created) - String k = lru.poll(); - if (k == null) - { - cache.clear(); - break; - } - cache.remove(k); + // flush the cache + LOG.debug("{} flushed filter chain cache for {}", this, baseRequest.getDispatcherType()); + cache.clear(); } - + chain = chain == null ? new ChainEnd(servletHolder) : chain; + // flush the cache + LOG.debug("{} cached filter chain for {}: {}", this, baseRequest.getDispatcherType(), chain); cache.put(key, chain); - lru.add(key); } - else if (!filters.isEmpty()) - chain = new Chain(baseRequest, filters, servletHolder); - return chain; } + /** + * Create a FilterChain that calls the passed filter with the passed chain + * @param filterHolder The filter to invoke + * @param chain The chain to pass to the filter + * @return A FilterChain that invokes the filter with the chain + */ + protected FilterChain newFilterChain(FilterHolder filterHolder, FilterChain chain) + { + return new Chain(filterHolder, chain); + } + protected void invalidateChainsCache() { - if (_chainLRU[FilterMapping.REQUEST] != null) + if (_chainCache[FilterMapping.REQUEST] != null) { - _chainLRU[FilterMapping.REQUEST].clear(); - _chainLRU[FilterMapping.FORWARD].clear(); - _chainLRU[FilterMapping.INCLUDE].clear(); - _chainLRU[FilterMapping.ERROR].clear(); - _chainLRU[FilterMapping.ASYNC].clear(); - _chainCache[FilterMapping.REQUEST].clear(); _chainCache[FilterMapping.FORWARD].clear(); _chainCache[FilterMapping.INCLUDE].clear(); @@ -806,6 +773,29 @@ public boolean isInitialized() return _initialized; } + protected void initializeHolders(BaseHolder[] holders) + { + for (BaseHolder holder : holders) + { + holder.setServletHandler(this); + if (isInitialized()) + { + try + { + if (!holder.isStarted()) + { + holder.start(); + holder.initialize(); + } + } + catch (Exception e) + { + throw new RuntimeException(e); + } + } + } + } + /** * @return whether the filter chains are cached. */ @@ -833,10 +823,7 @@ public ListenerHolder[] getListeners() public void setListeners(ListenerHolder[] listeners) { if (listeners != null) - for (ListenerHolder holder : listeners) - { - holder.setServletHandler(this); - } + initializeHolders(listeners); updateBeans(_listeners,listeners); _listeners = listeners; } @@ -846,18 +833,6 @@ public ListenerHolder newListenerHolder(Source source) return new ListenerHolder(source); } - /** - * Create a new CachedChain - * - * @param filters the filter chain to be cached as a collection of {@link FilterHolder} - * @param servletHolder the servletHolder - * @return a new {@link CachedChain} instance - */ - public CachedChain newCachedChain(List filters, ServletHolder servletHolder) - { - return new CachedChain(filters, servletHolder); - } - /** * Add a new servlet holder * @@ -908,15 +883,13 @@ public ServletHolder addServletWithMapping(Class servlet, Str */ public void addServletWithMapping(ServletHolder servlet, String pathSpec) { + Objects.requireNonNull(servlet); ServletHolder[] holders = getServlets(); - if (holders != null) - holders = holders.clone(); - try { synchronized (this) { - if (servlet != null && !containsServletHolder(servlet)) + if (!containsServletHolder(servlet)) setServlets(ArrayUtil.addToArray(holders, servlet, ServletHolder.class)); } @@ -1021,15 +994,14 @@ public FilterHolder addFilterWithMapping(String className, String pathSpec, Enum */ public void addFilterWithMapping(FilterHolder holder, String pathSpec, EnumSet dispatches) { + Objects.requireNonNull(holder); FilterHolder[] holders = getFilters(); - if (holders != null) - holders = holders.clone(); try { synchronized (this) { - if (holder != null && !containsFilterHolder(holder)) + if (!containsFilterHolder(holder)) setFilters(ArrayUtil.addToArray(holders, holder, FilterHolder.class)); } @@ -1089,6 +1061,7 @@ public FilterHolder addFilterWithMapping(String className, String pathSpec, int */ public void addFilterWithMapping(FilterHolder holder, String pathSpec, int dispatches) { + Objects.requireNonNull(holder); FilterHolder[] holders = getFilters(); if (holders != null) holders = holders.clone(); @@ -1097,7 +1070,7 @@ public void addFilterWithMapping(FilterHolder holder, String pathSpec, int dispa { synchronized (this) { - if (holder != null && !containsFilterHolder(holder)) + if (!containsFilterHolder(holder)) setFilters(ArrayUtil.addToArray(holders, holder, FilterHolder.class)); } @@ -1180,7 +1153,7 @@ public void addFilterMapping(FilterMapping mapping) if (mappings == null || mappings.length == 0) { setFilterMappings(insertFilterMapping(mapping, 0, false)); - if (source != null && source == Source.JAVAX_API) + if (source == Source.JAVAX_API) _matchAfterIndex = 0; } else @@ -1188,7 +1161,7 @@ public void addFilterMapping(FilterMapping mapping) //there are existing entries. If this is a programmatic filtermapping, it is added at the end of the list. //If this is a normal filtermapping, it is inserted after all the other filtermappings (matchBefores and normals), //but before the first matchAfter filtermapping. - if (source != null && Source.JAVAX_API == source) + if (source == Source.JAVAX_API) { setFilterMappings(insertFilterMapping(mapping, mappings.length - 1, false)); if (_matchAfterIndex < 0) @@ -1224,12 +1197,12 @@ public void prependFilterMapping(FilterMapping mapping) if (mappings == null || mappings.length == 0) { setFilterMappings(insertFilterMapping(mapping, 0, false)); - if (source != null && Source.JAVAX_API == source) + if (source == Source.JAVAX_API) _matchBeforeIndex = 0; } else { - if (source != null && Source.JAVAX_API == source) + if (source == Source.JAVAX_API) { //programmatically defined filter mappings are prepended to mapping list in the order //in which they were defined. In other words, insert this mapping at the tail of the @@ -1341,6 +1314,7 @@ protected synchronized void updateMappings() { _filterPathMappings = null; _filterNameMappings = null; + _wildFilterNameMappings = Collections.emptyList(); } else { @@ -1365,17 +1339,24 @@ protected synchronized void updateMappings() } } } + + // Reverse filter mappings to apply as wrappers last filter wrapped first + for (Map.Entry> entry : _filterNameMappings.entrySet()) + Collections.reverse(entry.getValue()); + Collections.reverse(_filterPathMappings); + _wildFilterNameMappings = _filterNameMappings.get("*"); + if (_wildFilterNameMappings != null) + Collections.reverse(_wildFilterNameMappings); } // Map servlet paths to holders - if (_servletMappings == null || _servletNameMap == null) + if (_servletMappings == null) { _servletPathMap = null; } else { PathMappings pm = new PathMappings<>(); - Map servletPathMappings = new HashMap<>(); //create a map of paths to set of ServletMappings that define that mapping HashMap> sms = new HashMap<>(); @@ -1386,12 +1367,7 @@ protected synchronized void updateMappings() { for (String pathSpec : pathSpecs) { - List mappings = sms.get(pathSpec); - if (mappings == null) - { - mappings = new ArrayList<>(); - sms.put(pathSpec, mappings); - } + List mappings = sms.computeIfAbsent(pathSpec, k -> new ArrayList<>()); mappings.add(servletMapping); } } @@ -1453,7 +1429,6 @@ else if (isAllowDuplicateMappings()) finalMapping.getServletName(), _servletNameMap.get(finalMapping.getServletName()).getSource()); - servletPathMappings.put(pathSpec, finalMapping); pm.put(new ServletPathSpec(pathSpec), _servletNameMap.get(finalMapping.getServletName())); } @@ -1461,13 +1436,10 @@ else if (isAllowDuplicateMappings()) } // flush filter chain cache - if (_chainCache != null) + for (int i = _chainCache.length; i-- > 0; ) { - for (int i = _chainCache.length; i-- > 0; ) - { - if (_chainCache[i] != null) - _chainCache[i].clear(); - } + if (_chainCache[i] != null) + _chainCache[i].clear(); } if (LOG.isDebugEnabled()) @@ -1478,16 +1450,6 @@ else if (isAllowDuplicateMappings()) LOG.debug("servletPathMap=" + _servletPathMap); LOG.debug("servletNameMap=" + _servletNameMap); } - - try - { - if (_contextHandler != null && _contextHandler.isStarted() || _contextHandler == null && isStarted()) - initialize(); - } - catch (Exception e) - { - throw new RuntimeException(e); - } } protected void notFound(Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException @@ -1502,28 +1464,26 @@ protected synchronized boolean containsFilterHolder(FilterHolder holder) { if (_filters == null) return false; - boolean found = false; for (FilterHolder f : _filters) { if (f == holder) - found = true; + return true; } - return found; + return false; } protected synchronized boolean containsServletHolder(ServletHolder holder) { if (_servlets == null) return false; - boolean found = false; for (ServletHolder s : _servlets) { @SuppressWarnings("ReferenceEquality") boolean foundServletHolder = (s == holder); if (foundServletHolder) - found = true; + return true; } - return found; + return false; } /** @@ -1541,7 +1501,7 @@ public void setFilterMappings(FilterMapping[] filterMappings) { updateBeans(_filterMappings,filterMappings); _filterMappings = filterMappings; - if (isStarted()) + if (isRunning()) updateMappings(); invalidateChainsCache(); } @@ -1549,10 +1509,7 @@ public void setFilterMappings(FilterMapping[] filterMappings) public synchronized void setFilters(FilterHolder[] holders) { if (holders != null) - for (FilterHolder holder : holders) - { - holder.setServletHandler(this); - } + initializeHolders(holders); updateBeans(_filters,holders); _filters = holders; updateNameMappings(); @@ -1566,7 +1523,7 @@ public void setServletMappings(ServletMapping[] servletMappings) { updateBeans(_servletMappings,servletMappings); _servletMappings = servletMappings; - if (isStarted()) + if (isRunning()) updateMappings(); invalidateChainsCache(); } @@ -1579,169 +1536,13 @@ public void setServletMappings(ServletMapping[] servletMappings) public synchronized void setServlets(ServletHolder[] holders) { if (holders != null) - for (ServletHolder holder : holders) - { - holder.setServletHandler(this); - } + initializeHolders(holders); updateBeans(_servlets,holders); _servlets = holders; updateNameMappings(); invalidateChainsCache(); } - protected class CachedChain implements FilterChain - { - FilterHolder _filterHolder; - CachedChain _next; - ServletHolder _servletHolder; - - /** - * @param filters list of {@link FilterHolder} objects - * @param servletHolder the current {@link ServletHolder} - */ - protected CachedChain(List filters, ServletHolder servletHolder) - { - if (!filters.isEmpty()) - { - _filterHolder = filters.get(0); - filters.remove(0); - _next = new CachedChain(filters, servletHolder); - } - else - _servletHolder = servletHolder; - } - - @Override - public void doFilter(ServletRequest request, ServletResponse response) - throws IOException, ServletException - { - final Request baseRequest = Request.getBaseRequest(request); - - // pass to next filter - if (_filterHolder != null) - { - if (LOG.isDebugEnabled()) - LOG.debug("call filter {}", _filterHolder); - - //if the request already does not support async, then the setting for the filter - //is irrelevant. However if the request supports async but this filter does not - //temporarily turn it off for the execution of the filter - if (baseRequest.isAsyncSupported() && !_filterHolder.isAsyncSupported()) - { - try - { - baseRequest.setAsyncSupported(false, _filterHolder.toString()); - _filterHolder.doFilter(request, response, _next); - } - finally - { - baseRequest.setAsyncSupported(true, null); - } - } - else - _filterHolder.doFilter(request, response, _next); - - return; - } - - // Call servlet - HttpServletRequest srequest = (HttpServletRequest)request; - if (_servletHolder == null) - notFound(baseRequest, srequest, (HttpServletResponse)response); - else - { - if (LOG.isDebugEnabled()) - LOG.debug("call servlet " + _servletHolder); - _servletHolder.handle(baseRequest, request, response); - } - } - - @Override - public String toString() - { - if (_filterHolder != null) - return _filterHolder + "->" + _next.toString(); - if (_servletHolder != null) - return _servletHolder.toString(); - return "null"; - } - } - - private class Chain implements FilterChain - { - final Request _baseRequest; - final List _chain; - final ServletHolder _servletHolder; - int _filter = 0; - - private Chain(Request baseRequest, List filters, ServletHolder servletHolder) - { - _baseRequest = baseRequest; - _chain = filters; - _servletHolder = servletHolder; - } - - @Override - public void doFilter(ServletRequest request, ServletResponse response) - throws IOException, ServletException - { - if (LOG.isDebugEnabled()) - LOG.debug("doFilter " + _filter); - - // pass to next filter - if (_filter < _chain.size()) - { - FilterHolder holder = _chain.get(_filter++); - if (LOG.isDebugEnabled()) - LOG.debug("call filter " + holder); - - //if the request already does not support async, then the setting for the filter - //is irrelevant. However if the request supports async but this filter does not - //temporarily turn it off for the execution of the filter - if (!holder.isAsyncSupported() && _baseRequest.isAsyncSupported()) - { - try - { - _baseRequest.setAsyncSupported(false, holder.toString()); - holder.doFilter(request, response, this); - } - finally - { - _baseRequest.setAsyncSupported(true, null); - } - } - else - holder.doFilter(request, response, this); - - return; - } - - // Call servlet - HttpServletRequest srequest = (HttpServletRequest)request; - if (_servletHolder == null) - notFound(Request.getBaseRequest(request), srequest, (HttpServletResponse)response); - else - { - if (LOG.isDebugEnabled()) - LOG.debug("call servlet {}", _servletHolder); - _servletHolder.handle(_baseRequest, request, response); - } - } - - @Override - public String toString() - { - StringBuilder b = new StringBuilder(); - for (FilterHolder f : _chain) - { - b.append(f.toString()); - b.append("->"); - } - b.append(_servletHolder); - return b.toString(); - } - } - /** * @return The maximum entries in a filter chain cache. */ @@ -1790,4 +1591,52 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) resp.sendError(HttpServletResponse.SC_NOT_FOUND); } } + + static class Chain implements FilterChain + { + private final FilterHolder _filterHolder; + private final FilterChain _filterChain; + + Chain(FilterHolder filter, FilterChain chain) + { + _filterHolder = filter; + _filterChain = chain; + } + + @Override + public void doFilter(ServletRequest request, ServletResponse response) throws IOException, ServletException + { + _filterHolder.doFilter(request, response, _filterChain); + } + + @Override + public String toString() + { + return String.format("Chain@%x(%s)->%s", hashCode(), _filterHolder, _filterChain); + } + } + + static class ChainEnd implements FilterChain + { + private final ServletHolder _servletHolder; + + ChainEnd(ServletHolder holder) + { + _servletHolder = holder; + } + + @Override + public void doFilter(ServletRequest request, ServletResponse response) throws IOException, ServletException + { + Request baseRequest = Request.getBaseRequest(request); + Objects.requireNonNull(baseRequest); + _servletHolder.handle(baseRequest, request, response); + } + + @Override + public String toString() + { + return String.format("ChainEnd@%x(%s)", hashCode(), _servletHolder); + } + } } diff --git a/jetty-servlet/src/test/java/org/eclipse/jetty/servlet/ServletContextHandlerTest.java b/jetty-servlet/src/test/java/org/eclipse/jetty/servlet/ServletContextHandlerTest.java index 63070746fa89..3119dec21a9d 100644 --- a/jetty-servlet/src/test/java/org/eclipse/jetty/servlet/ServletContextHandlerTest.java +++ b/jetty-servlet/src/test/java/org/eclipse/jetty/servlet/ServletContextHandlerTest.java @@ -897,7 +897,7 @@ public void destroy() } @Test - public void testAddServletFromSCL() throws Exception + public void testAddFilterServletFromSCL() throws Exception { //A servlet can be added from a ServletContextListener ServletContextHandler context = new ServletContextHandler(); @@ -905,10 +905,11 @@ public void testAddServletFromSCL() throws Exception context.setContextPath("/"); context.addEventListener(new ServletContextListener() { - @Override public void contextInitialized(ServletContextEvent sce) { + sce.getServletContext().addFilter("filter", new MyFilter()) + .addMappingForUrlPatterns(EnumSet.of(DispatcherType.REQUEST), true, "/*"); ServletRegistration rego = sce.getServletContext().addServlet("hello", HelloServlet.class); rego.addMapping("/hello/*"); } @@ -927,11 +928,13 @@ public void contextDestroyed(ServletContextEvent sce) request.append("\n"); String response = _connector.getResponse(request.toString()); - assertThat("Response", response, containsString("Hello World")); + assertThat(response, containsString("200 OK")); + assertThat(response, containsString("filter: filter")); + assertThat(response, containsString("Hello World")); } @Test - public void testAddServletFromSCI() throws Exception + public void testAddFilterServletFromSCI() throws Exception { //A servlet can be added from a ServletContainerInitializer ContextHandlerCollection contexts = new ContextHandlerCollection(); @@ -943,6 +946,8 @@ class ServletAddingSCI implements ServletContainerInitializer @Override public void onStartup(Set> c, ServletContext ctx) { + ctx.addFilter("filter", new MyFilter()) + .addMappingForUrlPatterns(EnumSet.of(DispatcherType.REQUEST), true, "/*"); ServletRegistration rego = ctx.addServlet("hello", HelloServlet.class); rego.addMapping("/hello/*"); } @@ -957,7 +962,9 @@ public void onStartup(Set> c, ServletContext ctx) request.append("\n"); String response = _connector.getResponse(request.toString()); - assertThat("Response", response, containsString("Hello World")); + assertThat(response, containsString("200 OK")); + assertThat(response, containsString("filter: filter")); + assertThat(response, containsString("Hello World")); } @Test @@ -1430,7 +1437,6 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) public static class MyFilter implements Filter { - @Override public void init(FilterConfig filterConfig) throws ServletException { @@ -1440,6 +1446,7 @@ public void init(FilterConfig filterConfig) throws ServletException public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { + ((HttpServletResponse)response).addHeader("filter", "filter"); request.getServletContext().setAttribute("filter", "filter"); chain.doFilter(request, response); } @@ -1636,4 +1643,180 @@ else if ("delete".equalsIgnoreCase(action)) } } } -} + + public static class TestPListener implements ServletRequestListener + { + @Override + public void requestInitialized(ServletRequestEvent sre) + { + ServletRequest request = sre.getServletRequest(); + Integer count = (Integer)request.getAttribute("testRequestListener"); + request.setAttribute("testRequestListener", count == null ? 1 : count + 1); + } + + @Override + public void requestDestroyed(ServletRequestEvent sre) + { + } + } + + @Test + public void testProgrammaticListener() throws Exception + { + ServletContextHandler context = new ServletContextHandler(); + ServletHandler handler = new ServletHandler(); + _server.setHandler(context); + context.setHandler(handler); + + // Add a servlet to report number of listeners + handler.addServletWithMapping(new ServletHolder(new HttpServlet() + { + @Override + protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException + { + resp.getOutputStream().print("Listeners=" + req.getAttribute("testRequestListener")); + } + }), "/"); + + // Add a listener in STOPPED, STARTING and STARTED states + handler.addListener(new ListenerHolder(TestPListener.class)); + handler.addServlet(new ServletHolder(new HttpServlet() + { + @Override + public void init() throws ServletException + { + handler.addListener(new ListenerHolder(TestPListener.class)); + } + }) + { + { + setInitOrder(1); + } + }); + _server.start(); + handler.addListener(new ListenerHolder(TestPListener.class)); + + String request = + "GET /test HTTP/1.0\n" + + "Host: localhost\n" + + "\n"; + String response = _connector.getResponse(request); + assertThat(response, containsString("200 OK")); + assertThat(response, containsString("Listeners=3")); + } + + public static class TestPFilter implements Filter + { + @Override + public void init(FilterConfig filterConfig) throws ServletException + { + } + + @Override + public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException + { + Integer count = (Integer)request.getAttribute("testFilter"); + request.setAttribute("testFilter", count == null ? 1 : count + 1); + chain.doFilter(request, response); + } + + @Override + public void destroy() + { + } + } + + @Test + public void testProgrammaticFilters() throws Exception + { + ServletContextHandler context = new ServletContextHandler(); + ServletHandler handler = new ServletHandler(); + _server.setHandler(context); + context.setHandler(handler); + + // Add a servlet to report number of filters + handler.addServletWithMapping(new ServletHolder(new HttpServlet() + { + @Override + protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException + { + resp.getOutputStream().print("Filters=" + req.getAttribute("testFilter")); + } + }), "/"); + + // Add a filter in STOPPED, STARTING and STARTED states + handler.addFilterWithMapping(new FilterHolder(TestPFilter.class), "/*", EnumSet.of(DispatcherType.REQUEST)); + handler.addServlet(new ServletHolder(new HttpServlet() + { + @Override + public void init() throws ServletException + { + handler.addFilterWithMapping(new FilterHolder(TestPFilter.class), "/*", EnumSet.of(DispatcherType.REQUEST)); + } + }) + { + { + setInitOrder(1); + } + }); + _server.start(); + handler.addFilterWithMapping(new FilterHolder(TestPFilter.class), "/*", EnumSet.of(DispatcherType.REQUEST)); + + String request = + "GET /test HTTP/1.0\n" + + "Host: localhost\n" + + "\n"; + String response = _connector.getResponse(request); + assertThat(response, containsString("200 OK")); + assertThat(response, containsString("Filters=3")); + } + + public static class TestPServlet extends HttpServlet + { + @Override + protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException + { + resp.getOutputStream().println(req.getRequestURI()); + } + } + + @Test + public void testProgrammaticServlets() throws Exception + { + ServletContextHandler context = new ServletContextHandler(); + ServletHandler handler = new ServletHandler(); + _server.setHandler(context); + context.setHandler(handler); + + // Add a filter in STOPPED, STARTING and STARTED states + handler.addServletWithMapping(new ServletHolder(TestPServlet.class), "/one"); + handler.addServlet(new ServletHolder(new HttpServlet() + { + @Override + public void init() throws ServletException + { + handler.addServletWithMapping(new ServletHolder(TestPServlet.class), "/two"); + } + }) + { + { + setInitOrder(1); + } + }); + _server.start(); + handler.addServletWithMapping(new ServletHolder(TestPServlet.class), "/three"); + + String request = "GET /one HTTP/1.0\n" + "Host: localhost\n" + "\n"; + String response = _connector.getResponse(request); + assertThat(response, containsString("200 OK")); + assertThat(response, containsString("/one")); + request = "GET /two HTTP/1.0\n" + "Host: localhost\n" + "\n"; + response = _connector.getResponse(request); + assertThat(response, containsString("200 OK")); + assertThat(response, containsString("/two")); + request = "GET /three HTTP/1.0\n" + "Host: localhost\n" + "\n"; + response = _connector.getResponse(request); + assertThat(response, containsString("200 OK")); + assertThat(response, containsString("/three")); + } +} \ No newline at end of file diff --git a/jetty-servlets/pom.xml b/jetty-servlets/pom.xml index 402513cfeb42..f4895965801e 100644 --- a/jetty-servlets/pom.xml +++ b/jetty-servlets/pom.xml @@ -3,13 +3,12 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-servlets Jetty :: Utility Servlets and Filters Utility Servlets from Jetty - http://www.eclipse.org/jetty ${project.groupId}.servlets diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/GzipContentLengthTest.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/GzipContentLengthTest.java index e2efbdfa3c09..02e2ea743d5f 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/GzipContentLengthTest.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/GzipContentLengthTest.java @@ -43,7 +43,7 @@ /** * Test the GzipHandler support for Content-Length setting variations. * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @ExtendWith(WorkDirExtension.class) public class GzipContentLengthTest @@ -204,7 +204,7 @@ public void testAsyncScheduledDispatchWritePassed(Scenario scenario) throws Exce * 4) outputStream.write() * * @throws Exception on test failure - * @see Eclipse Bug 354014 + * @see Eclipse Bug 354014 */ @ParameterizedTest @MethodSource("scenarios") @@ -221,7 +221,7 @@ public void testServletLengthStreamTypeWrite(Scenario scenario) throws Exception * 4) outputStream.write() * * @throws Exception on test failure - * @see Eclipse Bug 354014 + * @see Eclipse Bug 354014 */ @ParameterizedTest @MethodSource("scenarios") @@ -238,7 +238,7 @@ public void testServletLengthTypeStreamWrite(Scenario scenario) throws Exception * 4) outputStream.write() * * @throws Exception on test failure - * @see Eclipse Bug 354014 + * @see Eclipse Bug 354014 */ @ParameterizedTest @MethodSource("scenarios") @@ -255,7 +255,7 @@ public void testServletStreamLengthTypeWrite(Scenario scenario) throws Exception * 4) outputStream.write() (with frequent response flush) * * @throws Exception on test failure - * @see Eclipse Bug 354014 + * @see Eclipse Bug 354014 */ @ParameterizedTest @MethodSource("scenarios") @@ -272,7 +272,7 @@ public void testServletStreamLengthTypeWriteWithFlush(Scenario scenario) throws * 4) outputStream.write() * * @throws Exception on test failure - * @see Eclipse Bug 354014 + * @see Eclipse Bug 354014 */ @ParameterizedTest @MethodSource("scenarios") @@ -289,7 +289,7 @@ public void testServletStreamTypeLengthWrite(Scenario scenario) throws Exception * 4) outputStream.write() * * @throws Exception on test failure - * @see Eclipse Bug 354014 + * @see Eclipse Bug 354014 */ @ParameterizedTest @MethodSource("scenarios") @@ -306,7 +306,7 @@ public void testServletTypeLengthStreamWrite(Scenario scenario) throws Exception * 4) outputStream.write() * * @throws Exception on test failure - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @ParameterizedTest @MethodSource("scenarios") @@ -326,7 +326,7 @@ public void testServletTypeStreamLengthWrite(Scenario scenario) throws Exception * while also using GzipFilter * * @throws Exception on test failure - * @see Eclipse Bug 450873 + * @see Eclipse Bug 450873 */ @ParameterizedTest @MethodSource("scenarios") diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/IncludedGzipMinSizeTest.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/IncludedGzipMinSizeTest.java index 3ae9fe081087..6c4e3453a162 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/IncludedGzipMinSizeTest.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/IncludedGzipMinSizeTest.java @@ -29,7 +29,7 @@ * Perform specific tests on the IncludableGzipHandler's ability to manage * minGzipSize initialization parameter. * - * @see http://bugs.eclipse.org/366106 + * @see https://bugs.eclipse.org/366106 */ @ExtendWith(WorkDirExtension.class) public class IncludedGzipMinSizeTest diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletBufferTypeLengthWrite.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletBufferTypeLengthWrite.java index afbd57d13f14..86b81993af90 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletBufferTypeLengthWrite.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletBufferTypeLengthWrite.java @@ -40,7 +40,7 @@ * 4) write * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletBufferTypeLengthWrite extends TestDirContentServlet diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthStreamTypeWrite.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthStreamTypeWrite.java index 4ec937636c00..358a68dec690 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthStreamTypeWrite.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthStreamTypeWrite.java @@ -37,7 +37,7 @@ * 4) write * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletLengthStreamTypeWrite extends TestDirContentServlet diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthTypeStreamWrite.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthTypeStreamWrite.java index 7b43a04fdc4a..2e6ccc45aa81 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthTypeStreamWrite.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletLengthTypeStreamWrite.java @@ -37,7 +37,7 @@ * 4) write * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletLengthTypeStreamWrite extends TestDirContentServlet diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWrite.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWrite.java index 1d86a2dfed1f..237d6f48b2d8 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWrite.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWrite.java @@ -37,7 +37,7 @@ * 4) write * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletStreamLengthTypeWrite extends TestDirContentServlet diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWriteWithFlush.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWriteWithFlush.java index 685d9f0f66b0..9d4a7cef74cf 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWriteWithFlush.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamLengthTypeWriteWithFlush.java @@ -37,7 +37,7 @@ * 4) write and flush * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletStreamLengthTypeWriteWithFlush extends TestDirContentServlet diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamTypeLengthWrite.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamTypeLengthWrite.java index e84ae9610d5e..ed2c96e6c07d 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamTypeLengthWrite.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletStreamTypeLengthWrite.java @@ -37,7 +37,7 @@ * 4) write * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletStreamTypeLengthWrite extends TestDirContentServlet diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeLengthStreamWrite.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeLengthStreamWrite.java index 94ad93ba9340..f206ca0bf28c 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeLengthStreamWrite.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeLengthStreamWrite.java @@ -37,7 +37,7 @@ * 4) write * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletTypeLengthStreamWrite extends TestDirContentServlet diff --git a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeStreamLengthWrite.java b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeStreamLengthWrite.java index 08313aa6d8ac..de414a22e2a2 100644 --- a/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeStreamLengthWrite.java +++ b/jetty-servlets/src/test/java/org/eclipse/jetty/server/handler/gzip/TestServletTypeStreamLengthWrite.java @@ -37,7 +37,7 @@ * 4) write * * - * @see http://bugs.eclipse.org/354014 + * @see https://bugs.eclipse.org/354014 */ @SuppressWarnings("serial") public class TestServletTypeStreamLengthWrite extends TestDirContentServlet diff --git a/jetty-spring/pom.xml b/jetty-spring/pom.xml index 39d8abc6d1ae..12e8517f3928 100644 --- a/jetty-spring/pom.xml +++ b/jetty-spring/pom.xml @@ -2,7 +2,7 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-spring diff --git a/jetty-spring/src/main/config/modules/spring.mod b/jetty-spring/src/main/config/modules/spring.mod index 17ea36269f54..d7168bc1444c 100644 --- a/jetty-spring/src/main/config/modules/spring.mod +++ b/jetty-spring/src/main/config/modules/spring.mod @@ -11,6 +11,6 @@ server lib/spring/*.jar [ini-template] -## See http://www.eclipse.org/jetty/documentation/current/frameworks.html#framework-jetty-spring +## See https://eclipse.org/jetty/documentation/current/frameworks.html#framework-jetty-spring ## for information on how to complete spring configuration diff --git a/jetty-start/pom.xml b/jetty-start/pom.xml index 962becc90d95..3a6a588f5464 100644 --- a/jetty-start/pom.xml +++ b/jetty-start/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-start Jetty :: Start The start utility - http://www.eclipse.org/jetty ${project.groupId}.start diff --git a/jetty-start/src/main/java/org/eclipse/jetty/start/ModuleGraphWriter.java b/jetty-start/src/main/java/org/eclipse/jetty/start/ModuleGraphWriter.java index 8fa823805002..2bcd74448232 100644 --- a/jetty-start/src/main/java/org/eclipse/jetty/start/ModuleGraphWriter.java +++ b/jetty-start/src/main/java/org/eclipse/jetty/start/ModuleGraphWriter.java @@ -120,7 +120,7 @@ private void writeHeaderMessage(PrintWriter out, Path outputFile) out.println("/*"); out.println(" * GraphViz Graph of Jetty Modules"); out.println(" * "); - out.println(" * Jetty: http://eclipse.org/jetty/"); + out.println(" * Jetty: https://eclipse.org/jetty/"); out.println(" * GraphViz: http://graphviz.org/"); out.println(" * "); out.println(" * To Generate Graph image using graphviz:"); diff --git a/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt b/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt index 4bd9fa87be52..530eecc55ea5 100644 --- a/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt +++ b/jetty-start/src/main/resources/org/eclipse/jetty/start/usage.txt @@ -74,7 +74,7 @@ Debug and Start Logging: --debug Enable debug output of the startup procedure. Note: this does not setup debug for Jetty itself. If you want debug for Jetty, configure your logging. - http://www.eclipse.org/jetty/documentation/ + https://www.eclipse.org/jetty/documentation/ --start-log-file= A filename, relative to ${jetty.base}, where all startup @@ -264,4 +264,4 @@ Defaults: 5) /start.d/*.ini For more information on startup, see the online documentation at - http://www.eclipse.org/jetty/documentation/ + https://www.eclipse.org/jetty/documentation/ diff --git a/jetty-start/src/test/java/org/eclipse/jetty/start/fileinits/MavenLocalRepoFileInitializerTest.java b/jetty-start/src/test/java/org/eclipse/jetty/start/fileinits/MavenLocalRepoFileInitializerTest.java index 06b59d38f0d6..19c420df315e 100644 --- a/jetty-start/src/test/java/org/eclipse/jetty/start/fileinits/MavenLocalRepoFileInitializerTest.java +++ b/jetty-start/src/test/java/org/eclipse/jetty/start/fileinits/MavenLocalRepoFileInitializerTest.java @@ -65,7 +65,7 @@ public void setupBaseHome() throws IOException public void testGetCoordinateNotMaven() { MavenLocalRepoFileInitializer repo = new MavenLocalRepoFileInitializer(baseHome); - String ref = "http://www.eclipse.org/jetty"; + String ref = "https://www.eclipse.org/jetty/"; Coordinates coords = repo.getCoordinates(URI.create(ref)); assertThat("Coords", coords, nullValue()); } diff --git a/jetty-unixsocket/pom.xml b/jetty-unixsocket/pom.xml index 3a0e838ab1fb..1ef374147335 100644 --- a/jetty-unixsocket/pom.xml +++ b/jetty-unixsocket/pom.xml @@ -2,27 +2,15 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-unixsocket Jetty :: UnixSocket Jetty UnixSocket - http://www.eclipse.org/jetty ${project.groupId}.unixsocket - - - - org.codehaus.mojo - findbugs-maven-plugin - - org.eclipse.jetty.unixsocket.* - - - - org.eclipse.jetty @@ -32,6 +20,12 @@ com.github.jnr jnr-unixsocket + + + com.github.jnr + jnr-a64asm + + org.eclipse.jetty @@ -45,4 +39,81 @@ test + + + + org.codehaus.mojo + findbugs-maven-plugin + + org.eclipse.jetty.unixsocket.* + + + + org.apache.maven.plugins + maven-dependency-plugin + + + build-deps-file + generate-resources + + list + + + false + ${project.build.directory}/deps.txt + true + org.eclipse.jetty,javax.servlet + true + runtime + + + + + + org.apache.maven.plugins + maven-antrun-plugin + + + process-deps + process-resources + + run + + + + + + + + + + + + + + + + + + + + + org.apache.maven.plugins + maven-assembly-plugin + + + package + + single + + + + src/main/assembly/config.xml + + + + + + + diff --git a/jetty-unixsocket/src/main/assembly/config.xml b/jetty-unixsocket/src/main/assembly/config.xml new file mode 100644 index 000000000000..3c97242ba281 --- /dev/null +++ b/jetty-unixsocket/src/main/assembly/config.xml @@ -0,0 +1,28 @@ + + + config + false + + jar + + + + src/main/config-template + + + ** + + + **/unixsocket-prefix.mod + **/unixsocket-suffix.mod + + + + target + modules + + unixsocket.mod + + + + diff --git a/jetty-unixsocket/src/main/config/etc/jetty-unixsocket-forwarded.xml b/jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-forwarded.xml similarity index 100% rename from jetty-unixsocket/src/main/config/etc/jetty-unixsocket-forwarded.xml rename to jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-forwarded.xml diff --git a/jetty-unixsocket/src/main/config/etc/jetty-unixsocket-http.xml b/jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-http.xml similarity index 100% rename from jetty-unixsocket/src/main/config/etc/jetty-unixsocket-http.xml rename to jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-http.xml diff --git a/jetty-unixsocket/src/main/config/etc/jetty-unixsocket-http2c.xml b/jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-http2c.xml similarity index 100% rename from jetty-unixsocket/src/main/config/etc/jetty-unixsocket-http2c.xml rename to jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-http2c.xml diff --git a/jetty-unixsocket/src/main/config/etc/jetty-unixsocket-proxy-protocol.xml b/jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-proxy-protocol.xml similarity index 100% rename from jetty-unixsocket/src/main/config/etc/jetty-unixsocket-proxy-protocol.xml rename to jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-proxy-protocol.xml diff --git a/jetty-unixsocket/src/main/config/etc/jetty-unixsocket-secure.xml b/jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-secure.xml similarity index 100% rename from jetty-unixsocket/src/main/config/etc/jetty-unixsocket-secure.xml rename to jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket-secure.xml diff --git a/jetty-unixsocket/src/main/config/etc/jetty-unixsocket.xml b/jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket.xml similarity index 100% rename from jetty-unixsocket/src/main/config/etc/jetty-unixsocket.xml rename to jetty-unixsocket/src/main/config-template/etc/jetty-unixsocket.xml diff --git a/jetty-unixsocket/src/main/config/modules/unixsocket-forwarded.mod b/jetty-unixsocket/src/main/config-template/modules/unixsocket-forwarded.mod similarity index 100% rename from jetty-unixsocket/src/main/config/modules/unixsocket-forwarded.mod rename to jetty-unixsocket/src/main/config-template/modules/unixsocket-forwarded.mod diff --git a/jetty-unixsocket/src/main/config/modules/unixsocket-http.mod b/jetty-unixsocket/src/main/config-template/modules/unixsocket-http.mod similarity index 100% rename from jetty-unixsocket/src/main/config/modules/unixsocket-http.mod rename to jetty-unixsocket/src/main/config-template/modules/unixsocket-http.mod diff --git a/jetty-unixsocket/src/main/config/modules/unixsocket-http2c.mod b/jetty-unixsocket/src/main/config-template/modules/unixsocket-http2c.mod similarity index 100% rename from jetty-unixsocket/src/main/config/modules/unixsocket-http2c.mod rename to jetty-unixsocket/src/main/config-template/modules/unixsocket-http2c.mod diff --git a/jetty-unixsocket/src/main/config-template/modules/unixsocket-prefix.mod b/jetty-unixsocket/src/main/config-template/modules/unixsocket-prefix.mod new file mode 100644 index 000000000000..9e7f49111333 --- /dev/null +++ b/jetty-unixsocket/src/main/config-template/modules/unixsocket-prefix.mod @@ -0,0 +1,24 @@ +# DO NOT EDIT - See: https://www.eclipse.org/jetty/documentation/current/startup-modules.html + +[description] +Enables a Unix Domain Socket Connector that can receive +requests from a local proxy and/or SSL offloader (eg haproxy) in either +HTTP or TCP mode. Unix Domain Sockets are more efficient than +localhost TCP/IP connections as they reduce data copies, avoid +needless fragmentation and have better dispatch behaviours. +When enabled with corresponding support modules, the connector can +accept HTTP, HTTPS or HTTP2C traffic. + +[tags] +connector + +[depend] +server + +[xml] +etc/jetty-unixsocket.xml + +[lib] +lib/jetty-unixsocket-${jetty.version}.jar +lib/jnr/*.jar + diff --git a/jetty-unixsocket/src/main/config/modules/unixsocket-proxy-protocol.mod b/jetty-unixsocket/src/main/config-template/modules/unixsocket-proxy-protocol.mod similarity index 100% rename from jetty-unixsocket/src/main/config/modules/unixsocket-proxy-protocol.mod rename to jetty-unixsocket/src/main/config-template/modules/unixsocket-proxy-protocol.mod diff --git a/jetty-unixsocket/src/main/config/modules/unixsocket-secure.mod b/jetty-unixsocket/src/main/config-template/modules/unixsocket-secure.mod similarity index 100% rename from jetty-unixsocket/src/main/config/modules/unixsocket-secure.mod rename to jetty-unixsocket/src/main/config-template/modules/unixsocket-secure.mod diff --git a/jetty-unixsocket/src/main/config-template/modules/unixsocket-suffix.mod b/jetty-unixsocket/src/main/config-template/modules/unixsocket-suffix.mod new file mode 100644 index 000000000000..dc5f02721436 --- /dev/null +++ b/jetty-unixsocket/src/main/config-template/modules/unixsocket-suffix.mod @@ -0,0 +1,20 @@ +[license] +Jetty UnixSockets is implemented using the Java Native Runtime, which is an +open source project hosted on Github and released under the Apache 2.0 license. +https://github.com/jnr/jnr-unixsocket +http://www.apache.org/licenses/LICENSE-2.0.html + +[ini-template] +### Unix SocketHTTP Connector Configuration + +## Unix socket path to bind to +# jetty.unixsocket.path=/tmp/jetty.sock + +## Connector idle timeout in milliseconds +# jetty.unixsocket.idleTimeout=30000 + +## Number of selectors (-1 picks default) +# jetty.unixsocket.selectors=-1 + +## ServerSocketChannel backlog (0 picks platform default) +# jetty.unixsocket.acceptQueueSize=0 diff --git a/jetty-unixsocket/src/main/config/modules/unixsocket.mod b/jetty-unixsocket/src/main/config/modules/unixsocket.mod deleted file mode 100644 index 5c573d624f03..000000000000 --- a/jetty-unixsocket/src/main/config/modules/unixsocket.mod +++ /dev/null @@ -1,59 +0,0 @@ -# DO NOT EDIT - See: https://www.eclipse.org/jetty/documentation/current/startup-modules.html - -[description] -Enables a Unix Domain Socket Connector that can receive -requests from a local proxy and/or SSL offloader (eg haproxy) in either -HTTP or TCP mode. Unix Domain Sockets are more efficient than -localhost TCP/IP connections as they reduce data copies, avoid -needless fragmentation and have better dispatch behaviours. -When enabled with corresponding support modules, the connector can -accept HTTP, HTTPS or HTTP2C traffic. - -[tags] -connector - -[depend] -server - -[xml] -etc/jetty-unixsocket.xml - -[files] -maven://com.github.jnr/jnr-unixsocket/0.22|lib/jnr/jnr-unixsocket-0.22.jar -maven://com.github.jnr/jnr-ffi/2.1.9|lib/jnr/jnr-ffi-2.1.9.jar -maven://com.github.jnr/jffi/1.2.17|lib/jnr/jffi-1.2.17.jar -maven://com.github.jnr/jffi/1.2.16/jar/native|lib/jnr/jffi-1.2.16-native.jar -maven://org.ow2.asm/asm/7.0|lib/jnr/asm-7.0.jar -maven://org.ow2.asm/asm-commons/7.0|lib/jnr/asm-commons-7.0.jar -maven://org.ow2.asm/asm-analysis/7.0|lib/jnr/asm-analysis-7.0.jar -maven://org.ow2.asm/asm-tree/7.0|lib/jnr/asm-tree-7.0.jar -maven://org.ow2.asm/asm-util/7.0|lib/jnr/asm-util-7.0.jar -maven://com.github.jnr/jnr-x86asm/1.0.2|lib/jnr/jnr-x86asm-1.0.2.jar -maven://com.github.jnr/jnr-constants/0.9.11|lib/jnr/jnr-constants-0.9.11.jar -maven://com.github.jnr/jnr-enxio/0.20|lib/jnr/jnr-enxio-0.20.jar -maven://com.github.jnr/jnr-posix/3.0.47|lib/jnr/jnr-posix-3.0.47.jar - -[lib] -lib/jetty-unixsocket-${jetty.version}.jar -lib/jnr/*.jar - -[license] -Jetty UnixSockets is implemented using the Java Native Runtime, which is an -open source project hosted on Github and released under the Apache 2.0 license. -https://github.com/jnr/jnr-unixsocket -http://www.apache.org/licenses/LICENSE-2.0.html - -[ini-template] -### Unix SocketHTTP Connector Configuration - -## Unix socket path to bind to -# jetty.unixsocket.path=/tmp/jetty.sock - -## Connector idle timeout in milliseconds -# jetty.unixsocket.idleTimeout=30000 - -## Number of selectors (-1 picks default) -# jetty.unixsocket.selectors=-1 - -## ServerSocketChannel backlog (0 picks platform default) -# jetty.unixsocket.acceptQueueSize=0 diff --git a/jetty-util-ajax/pom.xml b/jetty-util-ajax/pom.xml index f7417d8479eb..d7da4624dfb8 100644 --- a/jetty-util-ajax/pom.xml +++ b/jetty-util-ajax/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-util-ajax Jetty :: Utilities :: Ajax(JSON) JSON/Ajax Utility classes for Jetty - http://www.eclipse.org/jetty ${project.groupId}.util.ajax diff --git a/jetty-util/pom.xml b/jetty-util/pom.xml index 31a0b61d242f..a1ab21a3f2bc 100644 --- a/jetty-util/pom.xml +++ b/jetty-util/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-util Jetty :: Utilities Utility classes for Jetty - http://www.eclipse.org/jetty ${project.groupId}.util diff --git a/jetty-util/src/main/java/org/eclipse/jetty/util/Jetty.java b/jetty-util/src/main/java/org/eclipse/jetty/util/Jetty.java index d899cc371ca2..e15859f34159 100644 --- a/jetty-util/src/main/java/org/eclipse/jetty/util/Jetty.java +++ b/jetty-util/src/main/java/org/eclipse/jetty/util/Jetty.java @@ -72,7 +72,7 @@ public class Jetty else VERSION = System.getProperty("jetty.version", __buildProperties.getProperty("version", "9.4.z-SNAPSHOT")); - POWERED_BY = "Powered by Jetty:// " + VERSION + ""; + POWERED_BY = "Powered by Jetty:// " + VERSION + ""; // Show warning when RC# or M# is in version string STABLE = !VERSION.matches("^.*\\.(RC|M)[0-9]+$"); diff --git a/jetty-util/src/main/java/org/eclipse/jetty/util/compression/CompressionPool.java b/jetty-util/src/main/java/org/eclipse/jetty/util/compression/CompressionPool.java index cf35e73d79fd..e73ddd316db7 100644 --- a/jetty-util/src/main/java/org/eclipse/jetty/util/compression/CompressionPool.java +++ b/jetty-util/src/main/java/org/eclipse/jetty/util/compression/CompressionPool.java @@ -125,4 +125,17 @@ public void doStop() } _numObjects.set(0); } + + @Override + public String toString() + { + StringBuilder str = new StringBuilder(); + str.append(getClass().getSimpleName()); + str.append('@').append(Integer.toHexString(hashCode())); + str.append('{').append(getState()); + str.append(",size=").append(_pool == null ? -1 : _pool.size()); + str.append(",capacity=").append(_capacity <= 0 ? "UNLIMITED" : _capacity); + str.append('}'); + return str.toString(); + } } diff --git a/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java b/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java index 709d39b17e40..3bdc6979d6b1 100644 --- a/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java +++ b/jetty-util/src/main/java/org/eclipse/jetty/util/resource/FileResource.java @@ -226,7 +226,7 @@ private static URI checkFileAlias(final URI uri, final File file) LOG.debug(e); try { - return new URI("http://eclipse.org/bad/canonical/alias"); + return new URI("https://eclipse.org/bad/canonical/alias"); } catch (Exception ex2) { diff --git a/jetty-util/src/test/java/org/eclipse/jetty/util/LazyListTest.java b/jetty-util/src/test/java/org/eclipse/jetty/util/LazyListTest.java index 990227c28dd6..7a2ca5faa482 100644 --- a/jetty-util/src/test/java/org/eclipse/jetty/util/LazyListTest.java +++ b/jetty-util/src/test/java/org/eclipse/jetty/util/LazyListTest.java @@ -1501,12 +1501,12 @@ public void testGetGenericListInput() uris.add(URI.create("http://www.mortbay.org/")); uris.add(URI.create("http://jetty.codehaus.org/jetty/")); uris.add(URI.create("http://www.intalio.com/jetty/")); - uris.add(URI.create("http://www.eclipse.org/jetty/")); + uris.add(URI.create("https://www.eclipse.org/jetty/")); // Make sure that Generics pass through the 'get' routine safely. // We should be able to call this without casting the result to URI URI eclipseUri = LazyList.get(uris, 3); - assertEquals("http://www.eclipse.org/jetty/", eclipseUri.toASCIIString()); + assertEquals("https://www.eclipse.org/jetty/", eclipseUri.toASCIIString()); } /** diff --git a/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java b/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java index 05e86a686b92..f8d687847dfd 100644 --- a/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java +++ b/jetty-util/src/test/java/org/eclipse/jetty/util/resource/FileSystemResourceTest.java @@ -223,7 +223,7 @@ public void testNonAbsoluteURI(Class resourceClass) public void testNotFileURI(Class resourceClass) { assertThrows(IllegalArgumentException.class, - () -> newResource(resourceClass, new URI("http://www.eclipse.org/jetty/"))); + () -> newResource(resourceClass, new URI("https://www.eclipse.org/jetty/"))); } @ParameterizedTest diff --git a/jetty-webapp/pom.xml b/jetty-webapp/pom.xml index 10ccfdce33a3..f517af50adcf 100644 --- a/jetty-webapp/pom.xml +++ b/jetty-webapp/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-webapp Jetty :: Webapp Application Support Jetty web application support - http://www.eclipse.org/jetty ${project.groupId}.webapp @@ -69,6 +68,13 @@ ${project.version} test + + org.eclipse.jetty + jetty-http + ${project.version} + tests + test + org.eclipse.jetty.toolchain jetty-test-helper diff --git a/jetty-webapp/src/main/java/org/eclipse/jetty/webapp/WebAppContext.java b/jetty-webapp/src/main/java/org/eclipse/jetty/webapp/WebAppContext.java index 616958e636e5..97f388710ec3 100644 --- a/jetty-webapp/src/main/java/org/eclipse/jetty/webapp/WebAppContext.java +++ b/jetty-webapp/src/main/java/org/eclipse/jetty/webapp/WebAppContext.java @@ -689,7 +689,7 @@ public void addServerClass(String classOrPackageOrLocation) * * @param classOrPackage A pattern. * @see #setServerClasses(String[]) - * @see Jetty Documentation: Classloading + * @see Jetty Documentation: Classloading * @deprecated Use {@link #getServerClasspathPattern()}.{@link ClasspathPattern#add(String)} */ @Deprecated @@ -743,7 +743,7 @@ public void addSystemClass(String classOrPackage) * * @param classOrPackage A pattern. * @see #setSystemClasses(String[]) - * @see Jetty Documentation: Classloading + * @see Jetty Documentation: Classloading * @deprecated Use {@link #getSystemClasspathPattern()}.{@link ClasspathPattern#add(String)} */ @Deprecated diff --git a/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppClassLoaderTest.java b/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppClassLoaderTest.java index fe3d08b6f4bb..fd3031173c8b 100644 --- a/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppClassLoaderTest.java +++ b/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppClassLoaderTest.java @@ -342,7 +342,7 @@ public void testResources() throws Exception } @Test - public void ordering() throws Exception + public void testClashingResource() throws Exception { // The existence of a URLStreamHandler changes the behavior assumeTrue(URLStreamHandlerUtil.getFactory() == null, "URLStreamHandler changes behavior, skip test"); diff --git a/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppContextExtraClasspathTest.java b/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppContextExtraClasspathTest.java deleted file mode 100644 index 93167f07a870..000000000000 --- a/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppContextExtraClasspathTest.java +++ /dev/null @@ -1,216 +0,0 @@ -// -// ======================================================================== -// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others. -// ------------------------------------------------------------------------ -// All rights reserved. This program and the accompanying materials -// are made available under the terms of the Eclipse Public License v1.0 -// and Apache License v2.0 which accompanies this distribution. -// -// The Eclipse Public License is available at -// http://www.eclipse.org/legal/epl-v10.html -// -// The Apache License v2.0 is available at -// http://www.opensource.org/licenses/apache2.0.php -// -// You may elect to redistribute this code under either of these licenses. -// ======================================================================== -// - -package org.eclipse.jetty.webapp; - -import java.io.File; -import java.net.URL; -import java.nio.file.Files; -import java.nio.file.Path; -import java.nio.file.Paths; -import java.util.ArrayList; -import java.util.List; -import java.util.stream.Collectors; -import java.util.stream.Stream; - -import org.eclipse.jetty.server.Server; -import org.eclipse.jetty.server.ServerConnector; -import org.eclipse.jetty.toolchain.test.MavenTestingUtils; -import org.eclipse.jetty.util.component.LifeCycle; -import org.eclipse.jetty.util.resource.PathResource; -import org.junit.jupiter.api.AfterEach; -import org.junit.jupiter.api.Test; -import org.junit.jupiter.params.ParameterizedTest; -import org.junit.jupiter.params.provider.Arguments; -import org.junit.jupiter.params.provider.MethodSource; - -import static org.hamcrest.MatcherAssert.assertThat; -import static org.hamcrest.Matchers.instanceOf; -import static org.hamcrest.Matchers.is; -import static org.junit.jupiter.api.Assertions.assertTrue; - -public class WebAppContextExtraClasspathTest -{ - private Server server; - - private Server newServer() - { - server = new Server(); - ServerConnector connector = new ServerConnector(server); - connector.setPort(0); - server.addConnector(connector); - return server; - } - - @AfterEach - public void tearDown() - { - LifeCycle.stop(server); - } - - @Test - public void testBaseResourceAbsolutePath() throws Exception - { - Server server = newServer(); - - WebAppContext context = new WebAppContext(); - context.setContextPath("/"); - - Path warPath = MavenTestingUtils.getTestResourcePathFile("wars/dump.war"); - warPath = warPath.toAbsolutePath(); - assertTrue(warPath.isAbsolute(), "Path should be absolute: " + warPath); - // Use String reference to war - // On Unix / Linux this should have no issue. - // On Windows with fully qualified paths such as "E:\mybase\webapps\dump.war" the - // resolution of the Resource can trigger various URI issues with the "E:" portion of the provided String. - context.setResourceBase(warPath.toString()); - - server.setHandler(context); - server.start(); - - assertTrue(context.isAvailable(), "WebAppContext should be available"); - } - - public static Stream extraClasspathGlob() - { - List references = new ArrayList<>(); - - Path extLibs = MavenTestingUtils.getTestResourcePathDir("ext"); - extLibs = extLibs.toAbsolutePath(); - - // Absolute reference with trailing slash and glob - references.add(Arguments.of(extLibs.toString() + File.separator + "*")); - - // Establish a relative extraClassPath reference - String relativeExtLibsDir = MavenTestingUtils.getBasePath().relativize(extLibs).toString(); - - // This will be in the String form similar to "src/test/resources/ext/*" (with trailing slash and glob) - references.add(Arguments.of(relativeExtLibsDir + File.separator + "*")); - - return references.stream(); - } - - /** - * Test using WebAppContext.setExtraClassPath(String) with a reference to a glob - */ - @ParameterizedTest - @MethodSource("extraClasspathGlob") - public void testExtraClasspathGlob(String extraClasspathGlobReference) throws Exception - { - Server server = newServer(); - - WebAppContext context = new WebAppContext(); - context.setContextPath("/"); - Path warPath = MavenTestingUtils.getTestResourcePathFile("wars/dump.war"); - context.setBaseResource(new PathResource(warPath)); - context.setExtraClasspath(extraClasspathGlobReference); - - server.setHandler(context); - server.start(); - - // Should not have failed the start of the WebAppContext - assertTrue(context.isAvailable(), "WebAppContext should be available"); - - // Test WebAppClassLoader contents for expected jars - ClassLoader contextClassLoader = context.getClassLoader(); - assertThat(contextClassLoader, instanceOf(WebAppClassLoader.class)); - WebAppClassLoader webAppClassLoader = (WebAppClassLoader)contextClassLoader; - Path extLibsDir = MavenTestingUtils.getTestResourcePathDir("ext"); - extLibsDir = extLibsDir.toAbsolutePath(); - List expectedPaths = Files.list(extLibsDir) - .filter(Files::isRegularFile) - .filter((path) -> path.toString().endsWith(".jar")) - .collect(Collectors.toList()); - List actualPaths = new ArrayList<>(); - for (URL url : webAppClassLoader.getURLs()) - { - actualPaths.add(Paths.get(url.toURI())); - } - assertThat("WebAppClassLoader.urls.length", actualPaths.size(), is(expectedPaths.size())); - for (Path expectedPath : expectedPaths) - { - boolean found = false; - for (Path actualPath : actualPaths) - { - if (Files.isSameFile(actualPath, expectedPath)) - { - found = true; - } - } - assertTrue(found, "Not able to find expected jar in WebAppClassLoader: " + expectedPath); - } - } - - public static Stream extraClasspathDir() - { - List references = new ArrayList<>(); - - Path extLibs = MavenTestingUtils.getTestResourcePathDir("ext"); - extLibs = extLibs.toAbsolutePath(); - - // Absolute reference with trailing slash - references.add(Arguments.of(extLibs.toString() + File.separator)); - - // Absolute reference without trailing slash - references.add(Arguments.of(extLibs.toString())); - - // Establish a relative extraClassPath reference - String relativeExtLibsDir = MavenTestingUtils.getBasePath().relativize(extLibs).toString(); - - // This will be in the String form similar to "src/test/resources/ext/" (with trailing slash) - references.add(Arguments.of(relativeExtLibsDir + File.separator)); - - // This will be in the String form similar to "src/test/resources/ext/" (without trailing slash) - references.add(Arguments.of(relativeExtLibsDir)); - - return references.stream(); - } - - /** - * Test using WebAppContext.setExtraClassPath(String) with a reference to a directory - */ - @ParameterizedTest - @MethodSource("extraClasspathDir") - public void testExtraClasspathDir(String extraClassPathReference) throws Exception - { - Server server = newServer(); - - WebAppContext context = new WebAppContext(); - context.setContextPath("/"); - Path warPath = MavenTestingUtils.getTestResourcePathFile("wars/dump.war"); - context.setBaseResource(new PathResource(warPath)); - - context.setExtraClasspath(extraClassPathReference); - - server.setHandler(context); - server.start(); - - // Should not have failed the start of the WebAppContext - assertTrue(context.isAvailable(), "WebAppContext should be available"); - - // Test WebAppClassLoader contents for expected directory reference - ClassLoader contextClassLoader = context.getClassLoader(); - assertThat(contextClassLoader, instanceOf(WebAppClassLoader.class)); - WebAppClassLoader webAppClassLoader = (WebAppClassLoader)contextClassLoader; - URL[] urls = webAppClassLoader.getURLs(); - assertThat("URLs", urls.length, is(1)); - Path extLibs = MavenTestingUtils.getTestResourcePathDir("ext"); - extLibs = extLibs.toAbsolutePath(); - assertThat("URL[0]", urls[0].toURI(), is(extLibs.toUri())); - } -} diff --git a/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppContextTest.java b/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppContextTest.java index 5b205ecc21a4..b6b0447e1eed 100644 --- a/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppContextTest.java +++ b/jetty-webapp/src/test/java/org/eclipse/jetty/webapp/WebAppContextTest.java @@ -19,94 +19,89 @@ package org.eclipse.jetty.webapp; import java.io.File; -import java.io.IOException; +import java.net.URL; +import java.nio.file.Files; import java.nio.file.Path; +import java.nio.file.Paths; import java.util.ArrayList; import java.util.Arrays; -import java.util.Collection; import java.util.List; import java.util.stream.Collectors; +import java.util.stream.Stream; import javax.servlet.GenericServlet; import javax.servlet.ServletContext; -import javax.servlet.ServletContextEvent; -import javax.servlet.ServletContextListener; -import javax.servlet.ServletException; import javax.servlet.ServletRequest; import javax.servlet.ServletResponse; -import javax.servlet.http.HttpSessionEvent; -import javax.servlet.http.HttpSessionListener; +import org.eclipse.jetty.http.HttpStatus; +import org.eclipse.jetty.http.HttpTester; import org.eclipse.jetty.server.LocalConnector; import org.eclipse.jetty.server.Server; +import org.eclipse.jetty.server.ServerConnector; import org.eclipse.jetty.server.handler.ContextHandlerCollection; import org.eclipse.jetty.server.handler.HandlerList; -import org.eclipse.jetty.server.handler.HotSwapHandler; import org.eclipse.jetty.servlet.ErrorPageErrorHandler; import org.eclipse.jetty.servlet.ServletContextHandler; +import org.eclipse.jetty.servlet.ServletHolder; +import org.eclipse.jetty.toolchain.test.FS; import org.eclipse.jetty.toolchain.test.MavenTestingUtils; +import org.eclipse.jetty.toolchain.test.jupiter.WorkDir; +import org.eclipse.jetty.toolchain.test.jupiter.WorkDirExtension; +import org.eclipse.jetty.util.component.LifeCycle; import org.eclipse.jetty.util.log.Log; +import org.eclipse.jetty.util.log.Logger; import org.eclipse.jetty.util.resource.PathResource; import org.eclipse.jetty.util.resource.Resource; -import org.eclipse.jetty.util.resource.ResourceCollection; +import org.junit.jupiter.api.AfterEach; import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.extension.ExtendWith; +import org.junit.jupiter.params.ParameterizedTest; +import org.junit.jupiter.params.provider.Arguments; +import org.junit.jupiter.params.provider.MethodSource; import static org.hamcrest.MatcherAssert.assertThat; -import static org.hamcrest.Matchers.contains; -import static org.hamcrest.Matchers.containsString; +import static org.hamcrest.Matchers.instanceOf; +import static org.hamcrest.Matchers.is; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.junit.jupiter.api.Assertions.assertFalse; import static org.junit.jupiter.api.Assertions.assertNotNull; import static org.junit.jupiter.api.Assertions.assertNull; import static org.junit.jupiter.api.Assertions.assertTrue; +@ExtendWith(WorkDirExtension.class) public class WebAppContextTest { - public class MySessionListener implements HttpSessionListener - { - - @Override - public void sessionCreated(HttpSessionEvent se) - { - // TODO Auto-generated method stub - - } - - @Override - public void sessionDestroyed(HttpSessionEvent se) - { - // TODO Auto-generated method stub + public static final Logger LOG = Log.getLogger(WebAppContextTest.class); + public WorkDir workDir; + private final List lifeCycles = new ArrayList<>(); - } + @AfterEach + public void tearDown() + { + lifeCycles.forEach(LifeCycle::stop); } - @Test - public void testSessionListeners() - throws Exception + private Server newServer() { Server server = new Server(); - - WebAppContext wac = new WebAppContext(); - - wac.setServer(server); - server.setHandler(wac); - wac.addEventListener(new MySessionListener()); - - Collection listeners = wac.getSessionHandler().getBeans(org.eclipse.jetty.webapp.WebAppContextTest.MySessionListener.class); - assertNotNull(listeners); - assertEquals(1, listeners.size()); + ServerConnector connector = new ServerConnector(server); + connector.setPort(0); + server.addConnector(connector); + lifeCycles.add(server); + return server; } @Test public void testConfigurationClassesFromDefault() { - Server server = new Server(); - //test if no classnames set, its the defaults + Server server = newServer(); + // test if no classnames set, its the defaults WebAppContext wac = new WebAppContext(); assertEquals(0, wac.getConfigurations().length); String[] classNames = wac.getConfigurationClasses(); assertNotNull(classNames); - //test if no classname set, and none from server its the defaults + // test if no classname set, and none from server its the defaults wac.setServer(server); assertTrue(Arrays.equals(classNames, wac.getConfigurationClasses())); } @@ -116,7 +111,7 @@ public void testConfigurationClassesExplicit() { String[] classNames = {"x.y.z"}; - Server server = new Server(); + Server server = newServer(); server.setAttribute(Configuration.ATTR, classNames); //test an explicitly set classnames list overrides that from the server @@ -136,7 +131,7 @@ public void testConfigurationClassesExplicit() } catch (Exception e) { - Log.getRootLogger().ignore(e); + LOG.ignore(e); } assertTrue(Arrays.equals(classNames, wac2.getConfigurationClasses())); } @@ -151,7 +146,7 @@ public void testConfigurationInstances() //test that explicit config instances override any from server String[] classNames = {"x.y.z"}; - Server server = new Server(); + Server server = newServer(); server.setAttribute(Configuration.ATTR, classNames); wac.setServer(server); assertTrue(Arrays.equals(configs, wac.getConfigurations())); @@ -160,7 +155,7 @@ public void testConfigurationInstances() @Test public void testRealPathDoesNotExist() throws Exception { - Server server = new Server(0); + Server server = newServer(); WebAppContext context = new WebAppContext(".", "/"); server.setHandler(context); server.start(); @@ -178,15 +173,31 @@ public void testRealPathDoesNotExist() throws Exception @Test public void testContextWhiteList() throws Exception { - Server server = new Server(0); + Server server = newServer(); HandlerList handlers = new HandlerList(); WebAppContext contextA = new WebAppContext(".", "/A"); - contextA.addServlet(ServletA.class, "/s"); + ServletHolder servletAHolder = new ServletHolder(new GenericServlet() + { + @Override + public void service(ServletRequest req, ServletResponse res) + { + this.getServletContext().getContext("/A/s"); + } + }); + contextA.addServlet(servletAHolder, "/s"); handlers.addHandler(contextA); WebAppContext contextB = new WebAppContext(".", "/B"); - contextB.addServlet(ServletB.class, "/s"); + ServletHolder servletBHolder = new ServletHolder(new GenericServlet() + { + @Override + public void service(ServletRequest req, ServletResponse res) + { + this.getServletContext().getContext("/B/s"); + } + }); + contextB.addServlet(servletBHolder, "/s"); contextB.setContextWhiteList(new String[]{"/doesnotexist", "/B/s"}); handlers.addHandler(contextB); @@ -205,22 +216,20 @@ public void testContextWhiteList() throws Exception @Test public void testAlias() throws Exception { - File dir = File.createTempFile("dir", null); - dir.delete(); - dir.mkdir(); - dir.deleteOnExit(); + Path tempDir = workDir.getEmptyPathDir().resolve("dir"); + FS.ensureEmpty(tempDir); - File webinf = new File(dir, "WEB-INF"); - webinf.mkdir(); + Path webinf = tempDir.resolve("WEB-INF"); + FS.ensureEmpty(webinf); - File classes = new File(dir, "classes"); - classes.mkdir(); + Path classes = tempDir.resolve("classes"); + FS.ensureEmpty(classes); - File someclass = new File(classes, "SomeClass.class"); - someclass.createNewFile(); + Path someClass = classes.resolve("SomeClass.class"); + FS.touch(someClass); WebAppContext context = new WebAppContext(); - context.setBaseResource(new ResourceCollection(dir.getAbsolutePath())); + context.setBaseResource(new PathResource(tempDir)); context.setResourceAlias("/WEB-INF/classes/", "/classes/"); @@ -229,9 +238,10 @@ public void testAlias() throws Exception } @Test - public void testIsProtected() throws Exception + public void testIsProtected() { WebAppContext context = new WebAppContext(); + assertTrue(context.isProtectedTarget("/web-inf/lib/foo.jar")); assertTrue(context.isProtectedTarget("/meta-inf/readme.txt")); assertFalse(context.isProtectedTarget("/something-else/web-inf")); @@ -240,11 +250,13 @@ public void testIsProtected() throws Exception @Test public void testNullPath() throws Exception { - Server server = new Server(0); + Server server = newServer(); + HandlerList handlers = new HandlerList(); ContextHandlerCollection contexts = new ContextHandlerCollection(); WebAppContext context = new WebAppContext(); - context.setBaseResource(Resource.newResource("./src/test/webapp")); + Path testWebapp = MavenTestingUtils.getProjectDirPath("src/test/webapp"); + context.setBaseResource(new PathResource(testWebapp)); context.setContextPath("/"); server.setHandler(handlers); handlers.addHandler(contexts); @@ -254,27 +266,25 @@ public void testNullPath() throws Exception server.addConnector(connector); server.start(); - try - { - String response = connector.getResponse("GET http://localhost:8080 HTTP/1.1\r\nHost: localhost:8080\r\nConnection: close\r\n\r\n"); - assertThat("Response OK", response, containsString("200 OK")); - } - finally - { - server.stop(); - } + + String rawResponse = connector.getResponse("GET http://localhost:8080 HTTP/1.1\r\nHost: localhost:8080\r\nConnection: close\r\n\r\n"); + HttpTester.Response response = HttpTester.parseResponse(rawResponse); + assertThat("Response OK", response.getStatus(), is(HttpStatus.OK_200)); } @Test public void testNullSessionAndSecurityHandler() throws Exception { - Server server = new Server(0); + Server server = newServer(); + HandlerList handlers = new HandlerList(); ContextHandlerCollection contexts = new ContextHandlerCollection(); WebAppContext context = new WebAppContext(null, null, null, null, null, new ErrorPageErrorHandler(), ServletContextHandler.NO_SESSIONS | ServletContextHandler.NO_SECURITY); context.setContextPath("/"); - context.setBaseResource(Resource.newResource("./src/test/webapp")); + + Path testWebapp = MavenTestingUtils.getProjectDirPath("src/test/webapp"); + context.setBaseResource(new PathResource(testWebapp)); server.setHandler(handlers); handlers.addHandler(contexts); contexts.addHandler(context); @@ -282,149 +292,158 @@ public void testNullSessionAndSecurityHandler() throws Exception LocalConnector connector = new LocalConnector(server); server.addConnector(connector); - try - { - server.start(); - assertTrue(context.isAvailable()); - } - finally - { - server.stop(); - } + server.start(); + assertTrue(context.isAvailable()); } - class ServletA extends GenericServlet + @Test + public void testBaseResourceAbsolutePath() throws Exception { - @Override - public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException - { - this.getServletContext().getContext("/A/s"); - } - } + Server server = newServer(); - class ServletB extends GenericServlet - { - @Override - public void service(ServletRequest req, ServletResponse res) throws ServletException, IOException - { - this.getServletContext().getContext("/B/s"); - } + WebAppContext context = new WebAppContext(); + context.setContextPath("/"); + + Path warPath = MavenTestingUtils.getTestResourcePathFile("wars/dump.war"); + warPath = warPath.toAbsolutePath(); + assertTrue(warPath.isAbsolute(), "Path should be absolute: " + warPath); + // Use String reference to war + // On Unix / Linux this should have no issue. + // On Windows with fully qualified paths such as "E:\mybase\webapps\dump.war" the + // resolution of the Resource can trigger various URI issues with the "E:" portion of the provided String. + context.setResourceBase(warPath.toString()); + + server.setHandler(context); + server.start(); + + assertTrue(context.isAvailable(), "WebAppContext should be available"); } - @Test - public void testServletContextListener() throws Exception + public static Stream extraClasspathGlob() { - Server server = new Server(); - HotSwapHandler swap = new HotSwapHandler(); - server.setHandler(swap); - server.start(); + List references = new ArrayList<>(); - ServletContextHandler context = new ServletContextHandler( - ServletContextHandler.SESSIONS); - context.setContextPath("/"); - context.setResourceBase(System.getProperty("java.io.tmpdir")); + Path extLibs = MavenTestingUtils.getTestResourcePathDir("ext"); + extLibs = extLibs.toAbsolutePath(); - final List history = new ArrayList<>(); + // Absolute reference with trailing slash and glob + references.add(Arguments.of(extLibs.toString() + File.separator + "*")); - context.addEventListener(new ServletContextListener() - { - @Override - public void contextInitialized(ServletContextEvent servletContextEvent) - { - history.add("I0"); - } + // Establish a relative extraClassPath reference + String relativeExtLibsDir = MavenTestingUtils.getBasePath().relativize(extLibs).toString(); - @Override - public void contextDestroyed(ServletContextEvent servletContextEvent) - { - history.add("D0"); - } - }); - context.addEventListener(new ServletContextListener() - { - @Override - public void contextInitialized(ServletContextEvent servletContextEvent) - { - history.add("I1"); - } + // This will be in the String form similar to "src/test/resources/ext/*" (with trailing slash and glob) + references.add(Arguments.of(relativeExtLibsDir + File.separator + "*")); - @Override - public void contextDestroyed(ServletContextEvent servletContextEvent) - { - history.add("D1"); - throw new RuntimeException("Listener1 destroy broken"); - } - }); - context.addEventListener(new ServletContextListener() - { - @Override - public void contextInitialized(ServletContextEvent servletContextEvent) - { - history.add("I2"); - throw new RuntimeException("Listener2 init broken"); - } + return references.stream(); + } - @Override - public void contextDestroyed(ServletContextEvent servletContextEvent) - { - history.add("D2"); - } - }); - context.addEventListener(new ServletContextListener() - { - @Override - public void contextInitialized(ServletContextEvent servletContextEvent) - { - history.add("I3"); - } + /** + * Test using WebAppContext.setExtraClassPath(String) with a reference to a glob + */ + @ParameterizedTest + @MethodSource("extraClasspathGlob") + public void testExtraClasspathGlob(String extraClasspathGlobReference) throws Exception + { + Server server = newServer(); - @Override - public void contextDestroyed(ServletContextEvent servletContextEvent) - { - history.add("D3"); - } - }); + WebAppContext context = new WebAppContext(); + context.setContextPath("/"); + Path warPath = MavenTestingUtils.getTestResourcePathFile("wars/dump.war"); + context.setBaseResource(new PathResource(warPath)); + context.setExtraClasspath(extraClasspathGlobReference); - try - { - swap.setHandler(context); - context.start(); - } - catch (Exception e) + server.setHandler(context); + server.start(); + + // Should not have failed the start of the WebAppContext + assertTrue(context.isAvailable(), "WebAppContext should be available"); + + // Test WebAppClassLoader contents for expected jars + ClassLoader contextClassLoader = context.getClassLoader(); + assertThat(contextClassLoader, instanceOf(WebAppClassLoader.class)); + WebAppClassLoader webAppClassLoader = (WebAppClassLoader)contextClassLoader; + Path extLibsDir = MavenTestingUtils.getTestResourcePathDir("ext"); + extLibsDir = extLibsDir.toAbsolutePath(); + List expectedPaths = Files.list(extLibsDir) + .filter(Files::isRegularFile) + .filter((path) -> path.toString().endsWith(".jar")) + .collect(Collectors.toList()); + List actualPaths = new ArrayList<>(); + for (URL url : webAppClassLoader.getURLs()) { - history.add(e.getMessage()); + actualPaths.add(Paths.get(url.toURI())); } - finally + assertThat("WebAppClassLoader.urls.length", actualPaths.size(), is(expectedPaths.size())); + for (Path expectedPath : expectedPaths) { - try + boolean found = false; + for (Path actualPath : actualPaths) { - swap.setHandler(null); - } - catch (Exception e) - { - while (e.getCause() instanceof Exception) + if (Files.isSameFile(actualPath, expectedPath)) { - e = (Exception)e.getCause(); + found = true; } - history.add(e.getMessage()); } + assertTrue(found, "Not able to find expected jar in WebAppClassLoader: " + expectedPath); } + } + + public static Stream extraClasspathDir() + { + List references = new ArrayList<>(); + + Path extLibs = MavenTestingUtils.getTestResourcePathDir("ext"); + extLibs = extLibs.toAbsolutePath(); + + // Absolute reference with trailing slash + references.add(Arguments.of(extLibs.toString() + File.separator)); + + // Absolute reference without trailing slash + references.add(Arguments.of(extLibs.toString())); - assertThat(history, contains("I0", "I1", "I2", "Listener2 init broken", "D1", "D0", "Listener1 destroy broken")); + // Establish a relative extraClassPath reference + String relativeExtLibsDir = MavenTestingUtils.getBasePath().relativize(extLibs).toString(); - server.stop(); + // This will be in the String form similar to "src/test/resources/ext/" (with trailing slash) + references.add(Arguments.of(relativeExtLibsDir + File.separator)); + + // This will be in the String form similar to "src/test/resources/ext/" (without trailing slash) + references.add(Arguments.of(relativeExtLibsDir)); + + return references.stream(); } - @Test - public void ordering() throws Exception + /** + * Test using WebAppContext.setExtraClassPath(String) with a reference to a directory + */ + @ParameterizedTest + @MethodSource("extraClasspathDir") + public void testExtraClasspathDir(String extraClassPathReference) throws Exception { - Path testWebappDir = MavenTestingUtils.getProjectDirPath("src/test/webapp"); - Resource webapp = new PathResource(testWebappDir); + Server server = newServer(); + WebAppContext context = new WebAppContext(); - context.setBaseResource(webapp); - context.setContextPath("/test"); - new WebInfConfiguration().preConfigure(context); - assertEquals(Arrays.asList("acme.jar", "alpha.jar", "omega.jar"), - context.getMetaData().getWebInfJars().stream().map(r -> r.getURI().toString().replaceFirst(".+/", "")).collect(Collectors.toList())); + context.setContextPath("/"); + Path warPath = MavenTestingUtils.getTestResourcePathFile("wars/dump.war"); + context.setBaseResource(new PathResource(warPath)); + + context.setExtraClasspath(extraClassPathReference); + + server.setHandler(context); + server.start(); + + // Should not have failed the start of the WebAppContext + assertTrue(context.isAvailable(), "WebAppContext should be available"); + + // Test WebAppClassLoader contents for expected directory reference + ClassLoader contextClassLoader = context.getClassLoader(); + assertThat(contextClassLoader, instanceOf(WebAppClassLoader.class)); + WebAppClassLoader webAppClassLoader = (WebAppClassLoader)contextClassLoader; + URL[] urls = webAppClassLoader.getURLs(); + assertThat("URLs", urls.length, is(1)); + Path extLibs = MavenTestingUtils.getTestResourcePathDir("ext"); + extLibs = extLibs.toAbsolutePath(); + assertThat("URL[0]", urls[0].toURI(), is(extLibs.toUri())); } } diff --git a/jetty-websocket/javax-websocket-client-impl/pom.xml b/jetty-websocket/javax-websocket-client-impl/pom.xml index 06642eb87400..689b9fe8a0fc 100644 --- a/jetty-websocket/javax-websocket-client-impl/pom.xml +++ b/jetty-websocket/javax-websocket-client-impl/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-websocket/javax-websocket-server-impl/pom.xml b/jetty-websocket/javax-websocket-server-impl/pom.xml index 18d588fafa1a..f3a788a04cc5 100644 --- a/jetty-websocket/javax-websocket-server-impl/pom.xml +++ b/jetty-websocket/javax-websocket-server-impl/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-websocket/jetty-websocket-tests/pom.xml b/jetty-websocket/jetty-websocket-tests/pom.xml index d9fbabf13a61..c8553660bda1 100644 --- a/jetty-websocket/jetty-websocket-tests/pom.xml +++ b/jetty-websocket/jetty-websocket-tests/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-websocket/jetty-websocket-tests/src/test/java/org/eclipse/jetty/websocket/tests/UpgradeWithLeftOverHttpBytesTest.java b/jetty-websocket/jetty-websocket-tests/src/test/java/org/eclipse/jetty/websocket/tests/UpgradeWithLeftOverHttpBytesTest.java new file mode 100644 index 000000000000..db18d6ae19c6 --- /dev/null +++ b/jetty-websocket/jetty-websocket-tests/src/test/java/org/eclipse/jetty/websocket/tests/UpgradeWithLeftOverHttpBytesTest.java @@ -0,0 +1,353 @@ +// +// ======================================================================== +// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others. +// ------------------------------------------------------------------------ +// All rights reserved. This program and the accompanying materials +// are made available under the terms of the Eclipse Public License v1.0 +// and Apache License v2.0 which accompanies this distribution. +// +// The Eclipse Public License is available at +// http://www.eclipse.org/legal/epl-v10.html +// +// The Apache License v2.0 is available at +// http://www.opensource.org/licenses/apache2.0.php +// +// You may elect to redistribute this code under either of these licenses. +// ======================================================================== +// + +package org.eclipse.jetty.websocket.tests; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.net.ServerSocket; +import java.net.Socket; +import java.net.URI; +import java.nio.ByteBuffer; +import java.nio.charset.StandardCharsets; +import java.util.Scanner; +import java.util.concurrent.CountDownLatch; +import java.util.concurrent.TimeUnit; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import org.eclipse.jetty.client.api.Request; +import org.eclipse.jetty.io.MappedByteBufferPool; +import org.eclipse.jetty.util.BufferUtil; +import org.eclipse.jetty.util.StringUtil; +import org.eclipse.jetty.websocket.api.Session; +import org.eclipse.jetty.websocket.api.StatusCode; +import org.eclipse.jetty.websocket.api.WebSocketPolicy; +import org.eclipse.jetty.websocket.api.annotations.WebSocket; +import org.eclipse.jetty.websocket.api.extensions.Frame; +import org.eclipse.jetty.websocket.client.WebSocketClient; +import org.eclipse.jetty.websocket.common.AcceptHash; +import org.eclipse.jetty.websocket.common.CloseInfo; +import org.eclipse.jetty.websocket.common.Generator; +import org.eclipse.jetty.websocket.common.frames.TextFrame; +import org.junit.jupiter.api.AfterEach; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import static org.hamcrest.MatcherAssert.assertThat; +import static org.hamcrest.Matchers.containsString; +import static org.hamcrest.Matchers.is; +import static org.junit.jupiter.api.Assertions.assertDoesNotThrow; +import static org.junit.jupiter.api.Assertions.assertFalse; +import static org.junit.jupiter.api.Assertions.assertTrue; + +public class UpgradeWithLeftOverHttpBytesTest +{ + private ServerSocket server; + private URI serverUri; + private WebSocketClient client; + private final Generator generator = new Generator(WebSocketPolicy.newServerPolicy(), new MappedByteBufferPool()); + + @BeforeEach + public void start() throws Exception + { + client = new WebSocketClient(); + client.start(); + server = new ServerSocket(0); + serverUri = URI.create("ws://localhost:" + server.getLocalPort()); + } + + @AfterEach + public void stop() throws Exception + { + client.stop(); + server.close(); + } + + @WebSocket + public static class OnOpenSocket extends EventSocket + { + CountDownLatch onOpenBlocked = new CountDownLatch(1); + + @Override + public void onOpen(Session session) + { + super.onOpen(session); + assertDoesNotThrow(() -> assertTrue(onOpenBlocked.await(1, TimeUnit.MINUTES))); + } + } + + @Test + public void testRequestCompletesFirstNoWebSocketBytesInResponse() throws Exception + { + // Initiate connection. + OnOpenSocket clientEndpoint = new OnOpenSocket(); + client.connect(clientEndpoint, serverUri); + Socket serverSocket = server.accept(); + + // Upgrade to WebSocket. + String upgradeRequest = getRequestHeaders(serverSocket.getInputStream()); + assertThat(upgradeRequest, containsString("HTTP/1.1")); + assertThat(upgradeRequest, containsString("Upgrade: websocket")); + String upgradeResponse = "HTTP/1.1 101 Switching Protocols\n" + + "Upgrade: WebSocket\n" + + "Connection: Upgrade\n" + + "Sec-WebSocket-Accept: " + getAcceptKey(upgradeRequest) + "\n" + + "\n"; + serverSocket.getOutputStream().write(upgradeResponse.getBytes(StandardCharsets.ISO_8859_1)); + + // Wait for WebSocket to be opened, wait 1 sec before allowing it to continue. + assertTrue(clientEndpoint.openLatch.await(5, TimeUnit.SECONDS)); + Thread.sleep(1000); + clientEndpoint.onOpenBlocked.countDown(); + + // Send some websocket data. + int numFrames = 1000; + for (int i = 0; i < numFrames; i++) + { + Frame frame = new TextFrame().setPayload(BufferUtil.toBuffer(Integer.toString(i))); + serverSocket.getOutputStream().write(toByteArray(frame)); + } + Frame closeFrame = new CloseInfo(StatusCode.NORMAL, "closed by test").asFrame(); + serverSocket.getOutputStream().write(toByteArray(closeFrame)); + + // We receive the data correctly. + for (int i = 0; i < numFrames; i++) + { + String msg = clientEndpoint.textMessages.poll(5, TimeUnit.SECONDS); + assertThat(msg, is(Integer.toString(i))); + } + + // Closed successfully with correct status. + assertTrue(clientEndpoint.closeLatch.await(5, TimeUnit.SECONDS)); + assertThat(clientEndpoint.closeCode, is(StatusCode.NORMAL)); + assertThat(clientEndpoint.closeReason, is("closed by test")); + } + + @Test + public void testRequestCompletesFirstWithWebSocketBytesInResponse() throws Exception + { + // Initiate connection. + OnOpenSocket clientEndpoint = new OnOpenSocket(); + client.connect(clientEndpoint, serverUri); + Socket serverSocket = server.accept(); + + // Upgrade to WebSocket, sending first websocket frame with the upgrade response. + String upgradeRequest = getRequestHeaders(serverSocket.getInputStream()); + assertThat(upgradeRequest, containsString("HTTP/1.1")); + assertThat(upgradeRequest, containsString("Upgrade: websocket")); + String upgradeResponse = "HTTP/1.1 101 Switching Protocols\n" + + "Upgrade: WebSocket\n" + + "Connection: Upgrade\n" + + "Sec-WebSocket-Accept: " + getAcceptKey(upgradeRequest) + "\n" + + "\n"; + Frame firstFrame = new TextFrame().setPayload("first message payload"); + byte[] bytes = combineToByteArray(BufferUtil.toBuffer(upgradeResponse), generateFrame(firstFrame)); + serverSocket.getOutputStream().write(bytes); + + // Now we send the rest of the data. + int numFrames = 1000; + for (int i = 0; i < numFrames; i++) + { + Frame frame = new TextFrame().setPayload(BufferUtil.toBuffer(Integer.toString(i))); + serverSocket.getOutputStream().write(toByteArray(frame)); + } + Frame closeFrame = new CloseInfo(StatusCode.NORMAL, "closed by test").asFrame(); + serverSocket.getOutputStream().write(toByteArray(closeFrame)); + + // Wait for WebSocket to be opened, wait 1 sec before allowing it to continue. + // We delay to ensure HttpConnection is not still reading from network. + assertTrue(clientEndpoint.openLatch.await(5, TimeUnit.SECONDS)); + Thread.sleep(1000); + clientEndpoint.onOpenBlocked.countDown(); + + // We receive the data correctly. + assertThat(clientEndpoint.textMessages.poll(5, TimeUnit.SECONDS), is("first message payload")); + for (int i = 0; i < numFrames; i++) + { + String msg = clientEndpoint.textMessages.poll(5, TimeUnit.SECONDS); + assertThat(msg, is(Integer.toString(i))); + } + + // Closed successfully with correct status. + assertTrue(clientEndpoint.closeLatch.await(5, TimeUnit.SECONDS)); + assertThat(clientEndpoint.closeCode, is(StatusCode.NORMAL)); + assertThat(clientEndpoint.closeReason, is("closed by test")); + } + + @Test + public void testResponseCompletesFirstNoWebSocketBytesInResponse() throws Exception + { + // We delay the request to finish until after the response is complete. + client.addBean(new Request.Listener() + { + @Override + public void onCommit(Request request) + { + assertDoesNotThrow(() -> Thread.sleep(1000)); + } + }); + + // Initiate connection. + OnOpenSocket clientEndpoint = new OnOpenSocket(); + client.connect(clientEndpoint, serverUri); + Socket serverSocket = server.accept(); + + // Upgrade to WebSocket. + String upgradeRequest = getRequestHeaders(serverSocket.getInputStream()); + assertThat(upgradeRequest, containsString("HTTP/1.1")); + assertThat(upgradeRequest, containsString("Upgrade: websocket")); + String upgradeResponse = "HTTP/1.1 101 Switching Protocols\n" + + "Upgrade: WebSocket\n" + + "Connection: Upgrade\n" + + "Sec-WebSocket-Accept: " + getAcceptKey(upgradeRequest) + "\n" + + "\n"; + serverSocket.getOutputStream().write(upgradeResponse.getBytes(StandardCharsets.ISO_8859_1)); + + // Wait for WebSocket to be opened, wait 1 sec before allowing it to continue. + assertTrue(clientEndpoint.openLatch.await(5, TimeUnit.SECONDS)); + Thread.sleep(1000); + clientEndpoint.onOpenBlocked.countDown(); + + // Send some websocket data. + int numFrames = 1000; + for (int i = 0; i < numFrames; i++) + { + Frame frame = new TextFrame().setPayload(BufferUtil.toBuffer(Integer.toString(i))); + serverSocket.getOutputStream().write(toByteArray(frame)); + } + Frame closeFrame = new CloseInfo(StatusCode.NORMAL, "closed by test").asFrame(); + serverSocket.getOutputStream().write(toByteArray(closeFrame)); + + // We receive the data correctly. + for (int i = 0; i < numFrames; i++) + { + String msg = clientEndpoint.textMessages.poll(5, TimeUnit.SECONDS); + assertThat(msg, is(Integer.toString(i))); + } + + // Closed successfully with correct status. + assertTrue(clientEndpoint.closeLatch.await(5, TimeUnit.SECONDS)); + assertThat(clientEndpoint.closeCode, is(StatusCode.NORMAL)); + assertThat(clientEndpoint.closeReason, is("closed by test")); + } + + @Test + public void testResponseCompletesFirstWithWebSocketBytesInResponse() throws Exception + { + // We delay the request to finish until after the response is complete. + client.addBean(new Request.Listener() + { + @Override + public void onCommit(Request request) + { + assertDoesNotThrow(() -> Thread.sleep(1000)); + } + }); + + // Initiate connection. + OnOpenSocket clientEndpoint = new OnOpenSocket(); + client.connect(clientEndpoint, serverUri); + Socket serverSocket = server.accept(); + + // Upgrade to WebSocket, sending first websocket frame with the upgrade response. + String upgradeRequest = getRequestHeaders(serverSocket.getInputStream()); + assertThat(upgradeRequest, containsString("HTTP/1.1")); + assertThat(upgradeRequest, containsString("Upgrade: websocket")); + String upgradeResponse = "HTTP/1.1 101 Switching Protocols\n" + + "Upgrade: WebSocket\n" + + "Connection: Upgrade\n" + + "Sec-WebSocket-Accept: " + getAcceptKey(upgradeRequest) + "\n" + + "\n"; + Frame firstFrame = new TextFrame().setPayload("first message payload"); + byte[] bytes = combineToByteArray(BufferUtil.toBuffer(upgradeResponse), generateFrame(firstFrame)); + serverSocket.getOutputStream().write(bytes); + + // Now we send the rest of the data. + int numFrames = 1000; + for (int i = 0; i < numFrames; i++) + { + Frame frame = new TextFrame().setPayload(BufferUtil.toBuffer(Integer.toString(i))); + serverSocket.getOutputStream().write(toByteArray(frame)); + } + Frame closeFrame = new CloseInfo(StatusCode.NORMAL, "closed by test").asFrame(); + serverSocket.getOutputStream().write(toByteArray(closeFrame)); + + // Wait for WebSocket to be opened, wait 1 sec before allowing it to continue. + // We delay to ensure HttpConnection is not still reading from network. + assertTrue(clientEndpoint.openLatch.await(5, TimeUnit.SECONDS)); + Thread.sleep(1000); + clientEndpoint.onOpenBlocked.countDown(); + + // We receive the data correctly. + assertThat(clientEndpoint.textMessages.poll(5, TimeUnit.SECONDS), is("first message payload")); + for (int i = 0; i < numFrames; i++) + { + String msg = clientEndpoint.textMessages.poll(5, TimeUnit.SECONDS); + assertThat(msg, is(Integer.toString(i))); + } + + // Closed successfully with correct status. + assertTrue(clientEndpoint.closeLatch.await(5, TimeUnit.SECONDS)); + assertThat(clientEndpoint.closeCode, is(StatusCode.NORMAL)); + assertThat(clientEndpoint.closeReason, is("closed by test")); + } + + public ByteBuffer generateFrame(Frame frame) + { + int size = Generator.MAX_HEADER_LENGTH + frame.getPayloadLength(); + ByteBuffer buffer = BufferUtil.allocate(size); + int pos = BufferUtil.flipToFill(buffer); + generator.generateWholeFrame(frame, buffer); + BufferUtil.flipToFlush(buffer, pos); + return buffer; + } + + String getAcceptKey(String upgradeRequest) + { + Matcher matcher = Pattern.compile(".*Sec-WebSocket-Key: ([^\n\r]+)\r?\n.*", Pattern.DOTALL | Pattern.MULTILINE) + .matcher(upgradeRequest); + assertTrue(matcher.matches()); + String key = matcher.group(1); + assertFalse(StringUtil.isEmpty(key)); + return AcceptHash.hashKey(key); + } + + static String getRequestHeaders(InputStream is) + { + Scanner s = new Scanner(is).useDelimiter("\r\n\r\n"); + return s.hasNext() ? s.next() : ""; + } + + byte[] combineToByteArray(ByteBuffer... buffers) throws IOException + { + ByteArrayOutputStream baos = new ByteArrayOutputStream(); + for (ByteBuffer bb : buffers) + { + BufferUtil.writeTo(bb, baos); + } + + return baos.toByteArray(); + } + + byte[] toByteArray(Frame frame) + { + return BufferUtil.toArray(generateFrame(frame)); + } +} diff --git a/jetty-websocket/pom.xml b/jetty-websocket/pom.xml index caf0061d6943..c8014f9f112f 100644 --- a/jetty-websocket/pom.xml +++ b/jetty-websocket/pom.xml @@ -3,7 +3,7 @@ jetty-project org.eclipse.jetty - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 @@ -11,8 +11,6 @@ websocket-parent Jetty :: Websocket :: Parent pom - http://www.eclipse.org/jetty - websocket-common websocket-api @@ -23,7 +21,6 @@ javax-websocket-client-impl javax-websocket-server-impl - diff --git a/jetty-websocket/websocket-api/pom.xml b/jetty-websocket/websocket-api/pom.xml index c5a6a553fa19..695327c2305f 100644 --- a/jetty-websocket/websocket-api/pom.xml +++ b/jetty-websocket/websocket-api/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-websocket/websocket-client/pom.xml b/jetty-websocket/websocket-client/pom.xml index 8f2802f48486..9e4608bd5226 100644 --- a/jetty-websocket/websocket-client/pom.xml +++ b/jetty-websocket/websocket-client/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-websocket/websocket-client/src/main/java/org/eclipse/jetty/websocket/client/WebSocketClient.java b/jetty-websocket/websocket-client/src/main/java/org/eclipse/jetty/websocket/client/WebSocketClient.java index f118b865c405..9043a676d557 100644 --- a/jetty-websocket/websocket-client/src/main/java/org/eclipse/jetty/websocket/client/WebSocketClient.java +++ b/jetty-websocket/websocket-client/src/main/java/org/eclipse/jetty/websocket/client/WebSocketClient.java @@ -34,6 +34,7 @@ import java.util.function.Supplier; import org.eclipse.jetty.client.HttpClient; +import org.eclipse.jetty.client.api.Request; import org.eclipse.jetty.io.ByteBufferPool; import org.eclipse.jetty.util.DecoratedObjectFactory; import org.eclipse.jetty.util.StringUtil; @@ -377,6 +378,11 @@ public Future connect(Object websocket, URI toUri, ClientUpgradeRequest WebSocketUpgradeRequest wsReq = new WebSocketUpgradeRequest(this, httpClient, request); wsReq.timeout(request.getTimeout(), TimeUnit.MILLISECONDS); wsReq.setUpgradeListener(upgradeListener); + for (Request.Listener l : getBeans(Request.Listener.class)) + { + wsReq.listener(l); + } + return wsReq.sendAsync(); } diff --git a/jetty-websocket/websocket-common/pom.xml b/jetty-websocket/websocket-common/pom.xml index 400fb8eeff74..4ea9e253448f 100644 --- a/jetty-websocket/websocket-common/pom.xml +++ b/jetty-websocket/websocket-common/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-websocket/websocket-server/pom.xml b/jetty-websocket/websocket-server/pom.xml index 1df06067bb73..1d48a63f8dff 100644 --- a/jetty-websocket/websocket-server/pom.xml +++ b/jetty-websocket/websocket-server/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-websocket/websocket-servlet/pom.xml b/jetty-websocket/websocket-servlet/pom.xml index 9861c943fe91..2f213848023f 100644 --- a/jetty-websocket/websocket-servlet/pom.xml +++ b/jetty-websocket/websocket-servlet/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.websocket websocket-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/jetty-xml/pom.xml b/jetty-xml/pom.xml index c92ade935e2c..a6518dd6aa45 100644 --- a/jetty-xml/pom.xml +++ b/jetty-xml/pom.xml @@ -2,13 +2,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jetty-xml Jetty :: XML utilities The jetty xml utilities. - http://www.eclipse.org/jetty ${project.groupId}.xml diff --git a/jetty-xml/src/main/java/org/eclipse/jetty/xml/XmlConfiguration.java b/jetty-xml/src/main/java/org/eclipse/jetty/xml/XmlConfiguration.java index 24541c2eff43..62191d99cf78 100644 --- a/jetty-xml/src/main/java/org/eclipse/jetty/xml/XmlConfiguration.java +++ b/jetty-xml/src/main/java/org/eclipse/jetty/xml/XmlConfiguration.java @@ -1942,7 +1942,9 @@ private ConfigurationParser(Pool.Entry entry) redirectEntity("configure_9_3.dtd", config93); redirectEntity("http://jetty.mortbay.org/configure.dtd", config93); redirectEntity("http://jetty.eclipse.org/configure.dtd", config93); + redirectEntity("https://jetty.eclipse.org/configure.dtd", config93); redirectEntity("http://www.eclipse.org/jetty/configure.dtd", config93); + redirectEntity("https://www.eclipse.org/jetty/configure.dtd", config93); redirectEntity("-//Mort Bay Consulting//DTD Configure//EN", config93); redirectEntity("-//Jetty//Configure//EN", config93); } diff --git a/pom.xml b/pom.xml index 4ef4e2b6cdfe..3463d9943022 100644 --- a/pom.xml +++ b/pom.xml @@ -4,7 +4,7 @@ 4.0.0 org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT Jetty :: Project The Eclipse Jetty Project pom @@ -14,10 +14,10 @@ 1.8 1.8 - http://www.eclipse.org/jetty + https://eclipse.org/jetty UTF-8 1.4 - 8.29 + 8.36.2 1.7.30 2.11.2 3.4.2 @@ -27,17 +27,18 @@ 8.5.54 9.4.8.Final 2.0.10 - 2.4.0 - 7.3.1 + 2.5.1 + 9.0 1.21 benchmarks 1.4.0 - 5.6.2 - 3.6.0 + 5.7.0 + 3.6.3 1.3.1 3.1.0 - 3.1.3.Final - 1.0.5 + 3.1.5.Final + 3.4.1.Final + 1.0.6 1.10.8 @@ -57,14 +58,14 @@ false - 5.4 + 5.5 2.1.1.RELEASE 1.0 - 1.3 + 1.3.2 ${project.build.directory}/local-repo src/it/settings.xml 0 - 1.14.3 + 1.15.0-rc2 @@ -74,7 +75,7 @@ Eclipse Public License - Version 1.0 - http://www.eclipse.org/org/documents/epl-v10.php + https://www.eclipse.org/org/documents/epl-v10.php @@ -421,7 +422,7 @@ org.apache.maven.plugins maven-checkstyle-plugin - 3.1.0 + 3.1.1 jetty-checkstyle.xml true @@ -467,7 +468,7 @@ org.apache.maven.plugins maven-assembly-plugin - 3.1.1 + 3.3.0 org.eclipse.jetty.toolchain @@ -626,19 +627,12 @@ org.apache.maven.plugins maven-shade-plugin - 3.2.2 + 3.2.4 org.apache.maven.plugins maven-site-plugin 3.7.1 - - - org.apache.maven.wagon - wagon-ssh - 3.0.0 - - org.apache.maven.plugins @@ -689,7 +683,7 @@ org.jacoco jacoco-maven-plugin - 0.8.5 + 0.8.6 com.agilejava.docbkx @@ -742,7 +736,7 @@ org.codehaus.mojo build-helper-maven-plugin - 3.0.0 + 3.2.0 org.codehaus.mojo @@ -1049,6 +1043,16 @@ provided + + org.codehaus.plexus + plexus-component-annotations + 2.1.0 + + + org.codehaus.plexus + plexus-utils + 3.3.0 + org.apache.maven maven-plugin-api @@ -1090,6 +1094,11 @@ junit-jupiter ${testcontainers.version} + + net.java.dev.jna + jna + 5.5.0 + org.eclipse.jetty.toolchain @@ -1124,12 +1133,12 @@ org.jboss.logging jboss-logging - 3.3.2.Final + ${jboss.logging.version} com.github.jnr jnr-unixsocket - 0.24 + 0.38.3 org.apache.derby diff --git a/tests/pom.xml b/tests/pom.xml index a67d78b496a1..33231f8bdba5 100644 --- a/tests/pom.xml +++ b/tests/pom.xml @@ -4,13 +4,12 @@ org.eclipse.jetty jetty-project - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml org.eclipse.jetty.tests tests-parent Jetty Tests :: Parent - http://www.eclipse.org/jetty pom diff --git a/tests/test-continuation/pom.xml b/tests/test-continuation/pom.xml index 3276b9f88a1c..91f13c47d74b 100644 --- a/tests/test-continuation/pom.xml +++ b/tests/test-continuation/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 diff --git a/tests/test-distribution/pom.xml b/tests/test-distribution/pom.xml index d247df726295..a712360d539f 100644 --- a/tests/test-distribution/pom.xml +++ b/tests/test-distribution/pom.xml @@ -2,7 +2,7 @@ tests-parent org.eclipse.jetty.tests - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/CDITests.java b/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/CDITests.java index ebdac3c9d836..2cccee6d256e 100644 --- a/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/CDITests.java +++ b/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/CDITests.java @@ -58,12 +58,14 @@ public static Stream tests() return Stream.of( // -- Weld -- + // Uses test-weld-cdi-webapp Arguments.of("weld", "cdi2", null), Arguments.of("weld", "cdi-spi", null), // Weld >= 3.1.2 Arguments.of("weld", "decorate", null), // Weld >= 3.1.2 Arguments.of("weld", "cdi-decorate", null), // Weld >= 3.1.3 // -- Apache OpenWebBeans -- + // Uses test-owb-cdi-webapp Arguments.of("owb", "cdi-spi", null), Arguments.of("owb", "jsp", renameJettyWebOwbXml) // Arguments.of("owb", "decorate", null), // Not supported diff --git a/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/DemoBaseTests.java b/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/DemoBaseTests.java index 7c01b5cf713c..b5fb2eaf69f0 100644 --- a/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/DemoBaseTests.java +++ b/tests/test-distribution/src/test/java/org/eclipse/jetty/tests/distribution/DemoBaseTests.java @@ -150,6 +150,34 @@ public void testSpec() throws Exception } } + @Test + public void testJavadocProxy() throws Exception + { + String jettyVersion = System.getProperty("jettyVersion"); + DistributionTester distribution = DistributionTester.Builder.newInstance() + .jettyVersion(jettyVersion) + .jettyBase(Paths.get("demo-base")) + .mavenLocalRepository(System.getProperty("mavenRepoPath")) + .build(); + + int httpPort = distribution.freePort(); + int httpsPort = distribution.freePort(); + String[] args = { + "jetty.http.port=" + httpPort, + "jetty.httpConfig.port=" + httpsPort, + "jetty.ssl.port=" + httpsPort + }; + try (DistributionTester.Run run = distribution.start(args)) + { + assertTrue(run.awaitConsoleLogsFor("Started @", 10, TimeUnit.SECONDS)); + + startHttpClient(); + ContentResponse response = client.GET("http://localhost:" + httpPort + "/proxy/current/"); + assertEquals(HttpStatus.OK_200, response.getStatus()); + assertThat("Expecting APIdoc contents", response.getContentAsString(), containsString("All Classes")); + } + } + @Test @DisabledOnJre(JRE.JAVA_8) public void testJPMS() throws Exception diff --git a/tests/test-http-client-transport/pom.xml b/tests/test-http-client-transport/pom.xml index e71653cea8b7..1cfe95ba683f 100644 --- a/tests/test-http-client-transport/pom.xml +++ b/tests/test-http-client-transport/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/tests/test-integration/pom.xml b/tests/test-integration/pom.xml index 232e74755a02..bdfdb2e45e61 100644 --- a/tests/test-integration/pom.xml +++ b/tests/test-integration/pom.xml @@ -3,19 +3,17 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 test-integration jar Jetty Tests :: Integrations - http://www.eclipse.org/jetty ${project.build.directory}/test-wars ${project.build.directory}/test-libs ${project.build.directory}/test-dist ${project.groupId}.integrations - diff --git a/tests/test-jmx/jmx-webapp-it/pom.xml b/tests/test-jmx/jmx-webapp-it/pom.xml index d7ee49fcdaef..fc968385c8d3 100644 --- a/tests/test-jmx/jmx-webapp-it/pom.xml +++ b/tests/test-jmx/jmx-webapp-it/pom.xml @@ -3,13 +3,12 @@ org.eclipse.jetty.tests test-jmx-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 jmx-webapp-it jar Jetty Tests :: JMX :: WebApp Integration Tests - http://www.eclipse.org/jetty UTF-8 UTF-8 diff --git a/tests/test-jmx/jmx-webapp/pom.xml b/tests/test-jmx/jmx-webapp/pom.xml index e92e66e8ca4f..29c858de35b6 100644 --- a/tests/test-jmx/jmx-webapp/pom.xml +++ b/tests/test-jmx/jmx-webapp/pom.xml @@ -4,12 +4,11 @@ org.eclipse.jetty.tests test-jmx-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT jmx-webapp war Jetty Tests :: JMX :: WebApp - http://www.eclipse.org/jetty UTF-8 ${project.groupId}.jmx.webapp diff --git a/tests/test-jmx/pom.xml b/tests/test-jmx/pom.xml index 167063c6d56b..1a7ff0dc7c8c 100644 --- a/tests/test-jmx/pom.xml +++ b/tests/test-jmx/pom.xml @@ -3,13 +3,12 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 test-jmx-parent pom Jetty Tests :: JMX Parent - http://www.eclipse.org/jetty jmx-webapp jmx-webapp-it diff --git a/tests/test-loginservice/pom.xml b/tests/test-loginservice/pom.xml index 54cea5ede1fd..cf3c20898c24 100644 --- a/tests/test-loginservice/pom.xml +++ b/tests/test-loginservice/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-loginservice Jetty Tests :: Login Service - http://www.eclipse.org/jetty ${project.groupId}.loginservice diff --git a/tests/test-quickstart/pom.xml b/tests/test-quickstart/pom.xml index 2fda6792da1c..2adcedb1e2cb 100644 --- a/tests/test-quickstart/pom.xml +++ b/tests/test-quickstart/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 @@ -11,7 +11,6 @@ test-quickstart Test :: Jetty Quick Start Jetty Quick Start Test - http://www.eclipse.org/jetty ${project.groupId}.tests.quickstart diff --git a/tests/test-sessions/pom.xml b/tests/test-sessions/pom.xml index ce36c4828e6c..8ca469936bd2 100644 --- a/tests/test-sessions/pom.xml +++ b/tests/test-sessions/pom.xml @@ -4,13 +4,27 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-sessions-parent Jetty Tests :: Sessions :: Parent - http://www.eclipse.org/jetty pom - + + + + org.junit.jupiter + junit-jupiter + ${junit.version} + test + + + org.junit.jupiter + junit-jupiter-api + ${junit.version} + test + + + test-sessions-common test-file-sessions diff --git a/tests/test-sessions/test-file-sessions/pom.xml b/tests/test-sessions/test-file-sessions/pom.xml index 13a36d0cd3b8..79c154b532af 100644 --- a/tests/test-sessions/test-file-sessions/pom.xml +++ b/tests/test-sessions/test-file-sessions/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-file-sessions Jetty Tests :: Sessions :: File - http://www.eclipse.org/jetty ${project.groupId}.sessions.file diff --git a/tests/test-sessions/test-gcloud-sessions/pom.xml b/tests/test-sessions/test-gcloud-sessions/pom.xml index 40014e16ff66..909e3e45e2dd 100644 --- a/tests/test-sessions/test-gcloud-sessions/pom.xml +++ b/tests/test-sessions/test-gcloud-sessions/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-gcloud-sessions Jetty Tests :: Sessions :: GCloud - http://www.eclipse.org/jetty ${project.groupId}.sessions.gcloud @@ -57,12 +56,6 @@ jetty-gcloud-session-manager ${project.version} - - - io.grpc - grpc-core - compile - org.eclipse.jetty.toolchain jetty-test-helper diff --git a/tests/test-sessions/test-hazelcast-sessions/pom.xml b/tests/test-sessions/test-hazelcast-sessions/pom.xml index a597854e601a..e411a9eaffe0 100644 --- a/tests/test-sessions/test-hazelcast-sessions/pom.xml +++ b/tests/test-sessions/test-hazelcast-sessions/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-hazelcast-sessions Jetty Tests :: Sessions :: Hazelcast - http://www.eclipse.org/jetty ${project.groupId}.sessions.hazelcast diff --git a/tests/test-sessions/test-infinispan-sessions/pom.xml b/tests/test-sessions/test-infinispan-sessions/pom.xml index cbf3c9300627..da451a888a13 100644 --- a/tests/test-sessions/test-infinispan-sessions/pom.xml +++ b/tests/test-sessions/test-infinispan-sessions/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-infinispan-sessions Jetty Tests :: Sessions :: Infinispan - http://www.eclipse.org/jetty ${project.groupId}.sessions.infinispan diff --git a/tests/test-sessions/test-jdbc-sessions/pom.xml b/tests/test-sessions/test-jdbc-sessions/pom.xml index 69c63d9d201c..dcd659ff49ff 100644 --- a/tests/test-sessions/test-jdbc-sessions/pom.xml +++ b/tests/test-sessions/test-jdbc-sessions/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-jdbc-sessions Jetty Tests :: Sessions :: JDBC diff --git a/tests/test-sessions/test-memcached-sessions/pom.xml b/tests/test-sessions/test-memcached-sessions/pom.xml index 4f77ae438d65..e706240afc3c 100644 --- a/tests/test-sessions/test-memcached-sessions/pom.xml +++ b/tests/test-sessions/test-memcached-sessions/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-memcached-sessions Jetty Tests :: Sessions :: Memcached - http://www.eclipse.org/jetty ${project.groupId}.sessions.memcached diff --git a/tests/test-sessions/test-mongodb-sessions/pom.xml b/tests/test-sessions/test-mongodb-sessions/pom.xml index e93f4e1f6391..c28db381ad01 100644 --- a/tests/test-sessions/test-mongodb-sessions/pom.xml +++ b/tests/test-sessions/test-mongodb-sessions/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-mongodb-sessions Jetty Tests :: Sessions :: Mongo - http://www.eclipse.org/jetty ${project.groupId}.sessions.mongo localhost diff --git a/tests/test-sessions/test-sessions-common/pom.xml b/tests/test-sessions/test-sessions-common/pom.xml index 827e9e244fba..047fa957ca11 100644 --- a/tests/test-sessions/test-sessions-common/pom.xml +++ b/tests/test-sessions/test-sessions-common/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-sessions-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-sessions-common Jetty Tests :: Sessions :: Common - http://www.eclipse.org/jetty ${project.groupId}.sessions.common @@ -39,5 +38,10 @@ junit-jupiter compile + + org.junit.jupiter + junit-jupiter-api + compile + diff --git a/tests/test-sessions/test-sessions-common/src/test/java/org/eclipse/jetty/server/session/SessionListenerTest.java b/tests/test-sessions/test-sessions-common/src/test/java/org/eclipse/jetty/server/session/SessionListenerTest.java index 8ec42555884a..6e45e322d6da 100644 --- a/tests/test-sessions/test-sessions-common/src/test/java/org/eclipse/jetty/server/session/SessionListenerTest.java +++ b/tests/test-sessions/test-sessions-common/src/test/java/org/eclipse/jetty/server/session/SessionListenerTest.java @@ -18,14 +18,16 @@ package org.eclipse.jetty.server.session; -import java.io.File; -import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; +import java.io.OutputStream; import java.io.Serializable; import java.net.HttpCookie; import java.net.URL; import java.net.URLClassLoader; +import java.nio.file.Files; +import java.nio.file.Path; +import java.util.Collection; import java.util.concurrent.TimeUnit; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; @@ -34,17 +36,25 @@ import javax.servlet.http.HttpSession; import javax.servlet.http.HttpSessionBindingEvent; import javax.servlet.http.HttpSessionBindingListener; +import javax.servlet.http.HttpSessionEvent; +import javax.servlet.http.HttpSessionListener; import org.eclipse.jetty.client.HttpClient; import org.eclipse.jetty.client.api.ContentResponse; import org.eclipse.jetty.client.api.Request; +import org.eclipse.jetty.server.Server; import org.eclipse.jetty.servlet.ServletContextHandler; import org.eclipse.jetty.servlet.ServletHolder; import org.eclipse.jetty.toolchain.test.IO; -import org.eclipse.jetty.toolchain.test.MavenTestingUtils; +import org.eclipse.jetty.toolchain.test.jupiter.WorkDir; +import org.eclipse.jetty.toolchain.test.jupiter.WorkDirExtension; +import org.eclipse.jetty.util.component.LifeCycle; +import org.eclipse.jetty.webapp.WebAppContext; import org.junit.jupiter.api.Test; +import org.junit.jupiter.api.extension.ExtendWith; import static org.hamcrest.MatcherAssert.assertThat; +import static org.hamcrest.Matchers.greaterThan; import static org.hamcrest.Matchers.in; import static org.hamcrest.Matchers.is; import static org.junit.jupiter.api.Assertions.assertEquals; @@ -58,8 +68,11 @@ * * Test that session listeners are called. */ +@ExtendWith(WorkDirExtension.class) public class SessionListenerTest { + public WorkDir workDir; + /** * Test that listeners are called when a session is deliberately invalidated. */ @@ -73,8 +86,8 @@ public void testListenerWithInvalidation() throws Exception DefaultSessionCacheFactory cacheFactory = new DefaultSessionCacheFactory(); cacheFactory.setEvictionPolicy(SessionCache.NEVER_EVICT); - SessionDataStoreFactory storeFactory = new TestSessionDataStoreFactory(); - ((AbstractSessionDataStoreFactory)storeFactory).setGracePeriodSec(scavengePeriod); + TestSessionDataStoreFactory storeFactory = new TestSessionDataStoreFactory(); + storeFactory.setGracePeriodSec(scavengePeriod); TestServer server = new TestServer(0, inactivePeriod, scavengePeriod, cacheFactory, storeFactory); @@ -99,7 +112,7 @@ public void testListenerWithInvalidation() throws Exception ContentResponse response1 = client.GET(url + "?action=init"); assertEquals(HttpServletResponse.SC_OK, response1.getStatus()); String sessionCookie = response1.getHeaders().get("Set-Cookie"); - assertTrue(sessionCookie != null); + assertNotNull(sessionCookie); assertTrue(TestServlet.bindingListener.bound); String sessionId = TestServer.extractSessionId(sessionCookie); @@ -115,12 +128,12 @@ public void testListenerWithInvalidation() throws Exception } finally { - client.stop(); + LifeCycle.stop(client); } } finally { - server.stop(); + LifeCycle.stop(server); } } @@ -131,17 +144,20 @@ public void testListenerWithInvalidation() throws Exception @Test public void testSessionExpiresWithListener() throws Exception { + Path foodir = workDir.getEmptyPathDir(); + Path fooClass = foodir.resolve("Foo.class"); + //Use a class that would only be known to the webapp classloader - InputStream foostream = Thread.currentThread().getContextClassLoader().getResourceAsStream("Foo.clazz"); - File foodir = new File(MavenTestingUtils.getTargetDir(), "foo"); - foodir.mkdirs(); - File fooclass = new File(foodir, "Foo.class"); - IO.copy(foostream, new FileOutputStream(fooclass)); + try (InputStream foostream = Thread.currentThread().getContextClassLoader().getResourceAsStream("Foo.clazz"); + OutputStream out = Files.newOutputStream(fooClass)) + { + IO.copy(foostream, out); + } - assertTrue(fooclass.exists()); - assertTrue(fooclass.length() != 0); + assertTrue(Files.exists(fooClass)); + assertThat(Files.size(fooClass), greaterThan(0L)); - URL[] foodirUrls = new URL[]{foodir.toURI().toURL()}; + URL[] foodirUrls = new URL[]{foodir.toUri().toURL()}; URLClassLoader contextClassLoader = new URLClassLoader(foodirUrls, Thread.currentThread().getContextClassLoader()); String contextPath = "/"; @@ -151,8 +167,8 @@ public void testSessionExpiresWithListener() throws Exception DefaultSessionCacheFactory cacheFactory = new DefaultSessionCacheFactory(); cacheFactory.setEvictionPolicy(SessionCache.NEVER_EVICT); - SessionDataStoreFactory storeFactory = new TestSessionDataStoreFactory(); - ((AbstractSessionDataStoreFactory)storeFactory).setGracePeriodSec(scavengePeriod); + TestSessionDataStoreFactory storeFactory = new TestSessionDataStoreFactory(); + storeFactory.setGracePeriodSec(scavengePeriod); TestServer server1 = new TestServer(0, inactivePeriod, scavengePeriod, cacheFactory, storeFactory); @@ -164,31 +180,38 @@ public void testSessionExpiresWithListener() throws Exception TestHttpSessionListener listener = new TestHttpSessionListenerWithWebappClasses(true); context.getSessionHandler().addEventListener(listener); - server1.start(); - int port1 = server1.getPort(); - try { + server1.start(); + int port1 = server1.getPort(); + HttpClient client = new HttpClient(); - client.start(); - String url = "http://localhost:" + port1 + contextPath + servletMapping.substring(1); + try + { + client.start(); + String url = "http://localhost:" + port1 + contextPath + servletMapping.substring(1); - //make a request to set up a session on the server - ContentResponse response1 = client.GET(url + "?action=init"); - assertEquals(HttpServletResponse.SC_OK, response1.getStatus()); - String sessionCookie = response1.getHeaders().get("Set-Cookie"); - assertTrue(sessionCookie != null); + //make a request to set up a session on the server + ContentResponse response1 = client.GET(url + "?action=init"); + assertEquals(HttpServletResponse.SC_OK, response1.getStatus()); + String sessionCookie = response1.getHeaders().get("Set-Cookie"); + assertNotNull(sessionCookie); - String sessionId = TestServer.extractSessionId(sessionCookie); + String sessionId = TestServer.extractSessionId(sessionCookie); - assertThat(sessionId, is(in(listener.createdSessions))); + assertThat(sessionId, is(in(listener.createdSessions))); - //and wait until the session should have expired - Thread.currentThread().sleep(TimeUnit.SECONDS.toMillis(inactivePeriod + (2 * scavengePeriod))); + //and wait until the session should have expired + Thread.sleep(TimeUnit.SECONDS.toMillis(inactivePeriod + (2 * scavengePeriod))); - assertThat(sessionId, is(in(listener.destroyedSessions))); + assertThat(sessionId, is(in(listener.destroyedSessions))); - assertNull(listener.ex); + assertNull(listener.ex); + } + finally + { + LifeCycle.stop(client); + } } finally { @@ -209,8 +232,8 @@ public void testExpiredSession() throws Exception DefaultSessionCacheFactory cacheFactory = new DefaultSessionCacheFactory(); cacheFactory.setEvictionPolicy(SessionCache.NEVER_EVICT); - SessionDataStoreFactory storeFactory = new TestSessionDataStoreFactory(); - ((AbstractSessionDataStoreFactory)storeFactory).setGracePeriodSec(scavengePeriod); + TestSessionDataStoreFactory storeFactory = new TestSessionDataStoreFactory(); + storeFactory.setGracePeriodSec(scavengePeriod); TestServer server1 = new TestServer(0, inactivePeriod, scavengePeriod, cacheFactory, storeFactory); @@ -222,11 +245,11 @@ public void testExpiredSession() throws Exception context.getSessionHandler().addEventListener(listener); - server1.start(); - int port1 = server1.getPort(); - try { + server1.start(); + int port1 = server1.getPort(); + //save a session that has already expired long now = System.currentTimeMillis(); SessionData data = context.getSessionHandler().getSessionCache().getSessionDataStore().newSessionData("1234", now - 10, now - 5, now - 10, 30000); @@ -234,24 +257,31 @@ public void testExpiredSession() throws Exception context.getSessionHandler().getSessionCache().getSessionDataStore().store("1234", data); HttpClient client = new HttpClient(); - client.start(); + try + { + client.start(); - port1 = server1.getPort(); - String url = "http://localhost:" + port1 + contextPath + servletMapping.substring(1); + port1 = server1.getPort(); + String url = "http://localhost:" + port1 + contextPath + servletMapping.substring(1); - //make another request using the id of the expired session - Request request = client.newRequest(url + "?action=test"); - request.cookie(new HttpCookie("JSESSIONID", "1234")); - ContentResponse response = request.send(); - assertEquals(HttpServletResponse.SC_OK, response.getStatus()); + //make another request using the id of the expired session + Request request = client.newRequest(url + "?action=test"); + request.cookie(new HttpCookie("JSESSIONID", "1234")); + ContentResponse response = request.send(); + assertEquals(HttpServletResponse.SC_OK, response.getStatus()); - //should be a new session id - String cookie2 = response.getHeaders().get("Set-Cookie"); - assertNotEquals("1234", TestServer.extractSessionId(cookie2)); + //should be a new session id + String cookie2 = response.getHeaders().get("Set-Cookie"); + assertNotEquals("1234", TestServer.extractSessionId(cookie2)); - assertTrue(listener.destroyedSessions.contains("1234")); + assertTrue(listener.destroyedSessions.contains("1234")); - assertNull(listener.ex); + assertNull(listener.ex); + } + finally + { + LifeCycle.stop(client); + } } finally { @@ -259,6 +289,42 @@ public void testExpiredSession() throws Exception } } + public static class MyHttpSessionListener implements HttpSessionListener + { + @Override + public void sessionCreated(HttpSessionEvent se) + { + } + + @Override + public void sessionDestroyed(HttpSessionEvent se) + { + } + } + + @Test + public void testSessionListeners() + { + Server server = new Server(); + try + { + WebAppContext wac = new WebAppContext(); + + wac.setServer(server); + server.setHandler(wac); + wac.addEventListener(new MyHttpSessionListener()); + + Collection listeners = wac.getSessionHandler().getBeans(MyHttpSessionListener.class); + assertNotNull(listeners); + + assertEquals(1, listeners.size()); + } + finally + { + LifeCycle.stop(server); + } + } + public static class MySessionBindingListener implements HttpSessionBindingListener, Serializable { private static final long serialVersionUID = 1L; @@ -314,7 +380,7 @@ protected void doGet(HttpServletRequest request, HttpServletResponse httpServlet if ("test".equals(action)) { HttpSession session = request.getSession(true); - assertTrue(session != null); + assertNotNull(session); } } } diff --git a/tests/test-webapps/pom.xml b/tests/test-webapps/pom.xml index e57b053ca111..a515d4e121a2 100644 --- a/tests/test-webapps/pom.xml +++ b/tests/test-webapps/pom.xml @@ -4,12 +4,11 @@ org.eclipse.jetty.tests tests-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml test-webapps-parent Jetty Tests :: WebApps :: Parent - http://www.eclipse.org/jetty pom diff --git a/tests/test-webapps/test-cdi-common-webapp/pom.xml b/tests/test-webapps/test-cdi-common-webapp/pom.xml index f72f6a6ded3a..cc927e640a52 100644 --- a/tests/test-webapps/test-cdi-common-webapp/pom.xml +++ b/tests/test-webapps/test-cdi-common-webapp/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/tests/test-webapps/test-felix-webapp/pom.xml b/tests/test-webapps/test-felix-webapp/pom.xml index 5fb3230e66b4..1495f4741663 100644 --- a/tests/test-webapps/test-felix-webapp/pom.xml +++ b/tests/test-webapps/test-felix-webapp/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/tests/test-webapps/test-http2-webapp/pom.xml b/tests/test-webapps/test-http2-webapp/pom.xml index bd11f63d7dfa..542ba1905ced 100644 --- a/tests/test-webapps/test-http2-webapp/pom.xml +++ b/tests/test-webapps/test-http2-webapp/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/tests/test-webapps/test-jaas-webapp/pom.xml b/tests/test-webapps/test-jaas-webapp/pom.xml index 4c40b0106567..1f592e09e9b7 100644 --- a/tests/test-webapps/test-jaas-webapp/pom.xml +++ b/tests/test-webapps/test-jaas-webapp/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-jaas-webapp Jetty Tests :: WebApp :: JAAS diff --git a/tests/test-webapps/test-jaas-webapp/src/main/webapp/index.html b/tests/test-webapps/test-jaas-webapp/src/main/webapp/index.html index 148e11d86015..23ba3a117d86 100644 --- a/tests/test-webapps/test-jaas-webapp/src/main/webapp/index.html +++ b/tests/test-webapps/test-jaas-webapp/src/main/webapp/index.html @@ -6,7 +6,7 @@ - +
Demo Home
@@ -24,7 +24,7 @@

Preparation

$JETTY_BASE/start.ini file. The Jetty demo-base already has JAAS enabled in its start.ini file.

The full source of this demonstration is available here.

+href="https://github.com/eclipse/jetty.project/tree/jetty-9.4.x/tests/test-webapps/test-jaas-webapp">here.

Using the Demo

@@ -32,11 +32,13 @@

Using the Demo

LOGIN

- This demo uses a simple login module that stores its configuration in a properties file. There are other types of login module provided with the jetty distro. For full information, please refer to the Jetty 9 documentation. + This demo uses a simple login module that stores its configuration in a properties file. There are other types of login + module provided with the jetty distro. For full information, please refer to the + Jetty 9 documentation.


-
+
diff --git a/tests/test-webapps/test-jetty-webapp/pom.xml b/tests/test-webapps/test-jetty-webapp/pom.xml index ed9baaf97115..6ef29243a278 100644 --- a/tests/test-webapps/test-jetty-webapp/pom.xml +++ b/tests/test-webapps/test-jetty-webapp/pom.xml @@ -3,14 +3,13 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 org.eclipse.jetty test-jetty-webapp Test :: Jetty Test Webapp - http://www.eclipse.org/jetty war ${project.groupId}.tests.webapp diff --git a/tests/test-webapps/test-jetty-webapp/src/main/webapp/index.html b/tests/test-webapps/test-jetty-webapp/src/main/webapp/index.html index d7d2a3a54f23..14336ced0a97 100644 --- a/tests/test-webapps/test-jetty-webapp/src/main/webapp/index.html +++ b/tests/test-webapps/test-jetty-webapp/src/main/webapp/index.html @@ -10,7 +10,7 @@ - +
Demo Home
@@ -56,17 +56,17 @@

Jetty Tests:

Useful links:

- +


-
+
diff --git a/tests/test-webapps/test-jetty-webapp/src/main/webapp/remote.html b/tests/test-webapps/test-jetty-webapp/src/main/webapp/remote.html index d892bedb57f1..511ed7247c4f 100644 --- a/tests/test-webapps/test-jetty-webapp/src/main/webapp/remote.html +++ b/tests/test-webapps/test-jetty-webapp/src/main/webapp/remote.html @@ -5,14 +5,14 @@ - +

Welcome to Jetty 9 - REMOTE ACCESS!!

-This is the Test webapp for the Jetty 9 HTTP Server and Servlet Container. -For more information about Jetty, please visit our -website -or documentation. -Commercial support for Jetty is available via webtide. + This is the Test webapp for the Jetty 9 HTTP Server and Servlet Container. + For more information about Jetty, please visit our + website + or documentation. + Commercial support for Jetty is available via webtide.

This test context serves several demo filters and servlets diff --git a/tests/test-webapps/test-jndi-webapp/pom.xml b/tests/test-webapps/test-jndi-webapp/pom.xml index 839b49c166e7..a72acb269ba1 100644 --- a/tests/test-webapps/test-jndi-webapp/pom.xml +++ b/tests/test-webapps/test-jndi-webapp/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-jndi-webapp Jetty Tests :: WebApp :: JNDI diff --git a/tests/test-webapps/test-jndi-webapp/src/main/webapp/index.html b/tests/test-webapps/test-jndi-webapp/src/main/webapp/index.html index 7ae0c6d7682d..bd3526175af1 100644 --- a/tests/test-webapps/test-jndi-webapp/src/main/webapp/index.html +++ b/tests/test-webapps/test-jndi-webapp/src/main/webapp/index.html @@ -6,7 +6,7 @@ - +
Demo Home


@@ -27,7 +27,7 @@

Preparation

This will create a $JETTY_BASE/start.d/jndi.ini file to enable and parameterise JNDI. If the --add-to-start option instead, then the same initialisation will be appended to the $JETTY_BASE/start.ini file instead. The jetty demo-base already has JNDI enabled in the start.ini file and some mock resources included.

-

The full source of this demonstration is available here.

+

The full source of this demonstration is available here.

Execution

@@ -40,7 +40,7 @@

Execution


-
+
diff --git a/tests/test-webapps/test-mock-resources/pom.xml b/tests/test-webapps/test-mock-resources/pom.xml index d34ae4988c66..222ad4e4cbfe 100644 --- a/tests/test-webapps/test-mock-resources/pom.xml +++ b/tests/test-webapps/test-mock-resources/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT Jetty Tests :: WebApp :: Mock Resources test-mock-resources diff --git a/tests/test-webapps/test-owb-cdi-webapp/pom.xml b/tests/test-webapps/test-owb-cdi-webapp/pom.xml index 159858456464..fe3c036cab32 100644 --- a/tests/test-webapps/test-owb-cdi-webapp/pom.xml +++ b/tests/test-webapps/test-owb-cdi-webapp/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 @@ -13,6 +13,7 @@ ${project.groupId}.cdi.owb + 2.0.18 @@ -59,13 +60,12 @@ org.apache.openwebbeans openwebbeans-web - - 2.0.11 + ${openwebbeans.version} org.apache.openwebbeans openwebbeans-jetty9 - 2.0.11 + ${openwebbeans.version} diff --git a/tests/test-webapps/test-owb-cdi-webapp/src/main/java/org/eclipse/jetty/cdi/owb/OwbServletContainerInitializer.java b/tests/test-webapps/test-owb-cdi-webapp/src/main/java/org/eclipse/jetty/cdi/owb/OwbServletContainerInitializer.java deleted file mode 100644 index f5492fee0cbd..000000000000 --- a/tests/test-webapps/test-owb-cdi-webapp/src/main/java/org/eclipse/jetty/cdi/owb/OwbServletContainerInitializer.java +++ /dev/null @@ -1,55 +0,0 @@ -// -// ======================================================================== -// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others. -// ------------------------------------------------------------------------ -// All rights reserved. This program and the accompanying materials -// are made available under the terms of the Eclipse Public License v1.0 -// and Apache License v2.0 which accompanies this distribution. -// -// The Eclipse Public License is available at -// http://www.eclipse.org/legal/epl-v10.html -// -// The Apache License v2.0 is available at -// http://www.opensource.org/licenses/apache2.0.php -// -// You may elect to redistribute this code under either of these licenses. -// ======================================================================== -// - -package org.eclipse.jetty.cdi.owb; - -import java.util.Set; -import javax.servlet.ServletContainerInitializer; -import javax.servlet.ServletContext; -import javax.servlet.ServletContextEvent; -import javax.servlet.ServletException; - -import org.apache.webbeans.servlet.WebBeansConfigurationListener; - -/** - * @deprecated This class will not be required once https://issues.apache.org/jira/browse/OWB-1296 is available - */ -@Deprecated -public class OwbServletContainerInitializer implements ServletContainerInitializer -{ - @Override - public void onStartup(Set> c, ServletContext ctx) throws ServletException - { - Listener listener = new Listener(); - listener.preInitialize(new ServletContextEvent(ctx)); - ctx.addListener(listener); - } - - public static class Listener extends WebBeansConfigurationListener - { - void preInitialize(ServletContextEvent event) - { - super.contextInitialized(event); - } - - @Override - public void contextInitialized(ServletContextEvent event) - { - } - } -} diff --git a/tests/test-webapps/test-owb-cdi-webapp/src/main/resources/META-INF/services/javax.servlet.ServletContainerInitializer b/tests/test-webapps/test-owb-cdi-webapp/src/main/resources/META-INF/services/javax.servlet.ServletContainerInitializer deleted file mode 100644 index f164a18c5a82..000000000000 --- a/tests/test-webapps/test-owb-cdi-webapp/src/main/resources/META-INF/services/javax.servlet.ServletContainerInitializer +++ /dev/null @@ -1 +0,0 @@ -org.eclipse.jetty.cdi.owb.OwbServletContainerInitializer \ No newline at end of file diff --git a/tests/test-webapps/test-owb-cdi-webapp/src/main/webapp/WEB-INF/web.xml b/tests/test-webapps/test-owb-cdi-webapp/src/main/webapp/WEB-INF/web.xml index 79a39c5b9d41..3d42ea1c24ca 100644 --- a/tests/test-webapps/test-owb-cdi-webapp/src/main/webapp/WEB-INF/web.xml +++ b/tests/test-webapps/test-owb-cdi-webapp/src/main/webapp/WEB-INF/web.xml @@ -1,11 +1,15 @@ - + OWB CDI Integration Test WebApp - + + + openwebbeans.web.sci.active + true + Object factory for the CDI Bean Manager diff --git a/tests/test-webapps/test-proxy-webapp/pom.xml b/tests/test-webapps/test-proxy-webapp/pom.xml index bf82f7a15235..df6488efc501 100644 --- a/tests/test-webapps/test-proxy-webapp/pom.xml +++ b/tests/test-webapps/test-proxy-webapp/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT ../pom.xml 4.0.0 @@ -45,14 +45,6 @@ javax.servlet-api provided - - org.eclipse.jetty jetty-webapp @@ -61,13 +53,13 @@ org.eclipse.jetty - jetty-jmx + jetty-client ${project.version} - test - org.eclipse.jetty.toolchain - jetty-test-helper + org.eclipse.jetty + jetty-jmx + ${project.version} test diff --git a/tests/test-webapps/test-proxy-webapp/src/main/webapp/WEB-INF/web.xml b/tests/test-webapps/test-proxy-webapp/src/main/webapp/WEB-INF/web.xml index 342181c61c92..ac033c1d1d1f 100644 --- a/tests/test-webapps/test-proxy-webapp/src/main/webapp/WEB-INF/web.xml +++ b/tests/test-webapps/test-proxy-webapp/src/main/webapp/WEB-INF/web.xml @@ -7,10 +7,12 @@ JavadocTransparentProxy org.eclipse.jetty.proxy.ProxyServlet$Transparent - proxyTohttp://www.eclipse.org/jetty/javadoc/ + proxyTo + https://www.eclipse.org/jetty/javadoc/ - hostHeadereclipse.org + hostHeader + www.eclipse.org 1 true diff --git a/tests/test-webapps/test-proxy-webapp/src/test/java/org/eclipse/jetty/ProxyWebAppTest.java b/tests/test-webapps/test-proxy-webapp/src/test/java/org/eclipse/jetty/ProxyWebAppTest.java new file mode 100644 index 000000000000..0e4206e53d6f --- /dev/null +++ b/tests/test-webapps/test-proxy-webapp/src/test/java/org/eclipse/jetty/ProxyWebAppTest.java @@ -0,0 +1,96 @@ +// +// ======================================================================== +// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others. +// ------------------------------------------------------------------------ +// All rights reserved. This program and the accompanying materials +// are made available under the terms of the Eclipse Public License v1.0 +// and Apache License v2.0 which accompanies this distribution. +// +// The Eclipse Public License is available at +// http://www.eclipse.org/legal/epl-v10.html +// +// The Apache License v2.0 is available at +// http://www.opensource.org/licenses/apache2.0.php +// +// You may elect to redistribute this code under either of these licenses. +// ======================================================================== +// + +package org.eclipse.jetty; + +import java.util.concurrent.ExecutionException; +import java.util.concurrent.TimeoutException; + +import org.eclipse.jetty.client.HttpClient; +import org.eclipse.jetty.client.api.ContentResponse; +import org.eclipse.jetty.http.HttpStatus; +import org.eclipse.jetty.server.Server; +import org.eclipse.jetty.server.ServerConnector; +import org.eclipse.jetty.toolchain.test.MavenTestingUtils; +import org.eclipse.jetty.util.component.LifeCycle; +import org.eclipse.jetty.webapp.WebAppContext; +import org.junit.jupiter.api.AfterEach; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Tag; +import org.junit.jupiter.api.Test; + +import static org.hamcrest.MatcherAssert.assertThat; +import static org.hamcrest.Matchers.containsString; +import static org.hamcrest.Matchers.is; + +/** + * Test the configuration found in WEB-INF/web.xml for purposes of the demo-base + */ +public class ProxyWebAppTest +{ + private Server server; + private HttpClient client; + + @BeforeEach + public void setup() throws Exception + { + server = new Server(); + + ServerConnector connector = new ServerConnector(server); + connector.setPort(0); + server.addConnector(connector); + + WebAppContext webapp = new WebAppContext(); + // This is a pieced together WebApp. + // We don't have a valid WEB-INF/lib to rely on at this point. + // So, open up server classes here, for purposes of this testcase. + webapp.getServerClasspathPattern().add("-org.eclipse.jetty.proxy."); + webapp.setWar(MavenTestingUtils.getProjectDirPath("src/main/webapp").toString()); + webapp.setExtraClasspath(MavenTestingUtils.getTargetPath().resolve("classes").toString()); + server.setHandler(webapp); + + server.start(); + + client = new HttpClient(); + client.start(); + } + + @AfterEach + public void teardown() + { + LifeCycle.stop(client); + LifeCycle.stop(server); + } + + @Test + @Tag("external") + public void testProxyRequest() throws InterruptedException, ExecutionException, TimeoutException + { + ContentResponse response = client.newRequest(server.getURI().resolve("/proxy/current/")) + .followRedirects(false) + .send(); + + // Expecting a 200 OK (not a 302 redirect or other error) + // If we got an error here, that means our configuration in web.xml is bad / out of date. + // Such as the redirect from the eclipse website, we want all of the requests to go through + // this proxy configuration, not redirected to the actual website. + assertThat("response status", response.getStatus(), is(HttpStatus.OK_200)); + // Expecting a Javadoc / APIDoc response - look for something unique for APIdoc. + assertThat("response", response.getContentAsString(), containsString("All Classes")); + } +} diff --git a/tests/test-webapps/test-proxy-webapp/src/test/java/org/eclipse/jetty/TestTransparentProxyServer.java b/tests/test-webapps/test-proxy-webapp/src/test/java/org/eclipse/jetty/TestTransparentProxyServer.java deleted file mode 100644 index 8d1839c21b12..000000000000 --- a/tests/test-webapps/test-proxy-webapp/src/test/java/org/eclipse/jetty/TestTransparentProxyServer.java +++ /dev/null @@ -1,135 +0,0 @@ -// -// ======================================================================== -// Copyright (c) 1995-2020 Mort Bay Consulting Pty Ltd and others. -// ------------------------------------------------------------------------ -// All rights reserved. This program and the accompanying materials -// are made available under the terms of the Eclipse Public License v1.0 -// and Apache License v2.0 which accompanies this distribution. -// -// The Eclipse Public License is available at -// http://www.eclipse.org/legal/epl-v10.html -// -// The Apache License v2.0 is available at -// http://www.opensource.org/licenses/apache2.0.php -// -// You may elect to redistribute this code under either of these licenses. -// ======================================================================== -// - -package org.eclipse.jetty; - -import java.lang.management.ManagementFactory; - -import org.eclipse.jetty.alpn.server.ALPNServerConnectionFactory; -import org.eclipse.jetty.http2.HTTP2Cipher; -import org.eclipse.jetty.http2.server.HTTP2ServerConnectionFactory; -import org.eclipse.jetty.jmx.MBeanContainer; -import org.eclipse.jetty.server.ForwardedRequestCustomizer; -import org.eclipse.jetty.server.Handler; -import org.eclipse.jetty.server.HttpConfiguration; -import org.eclipse.jetty.server.HttpConnectionFactory; -import org.eclipse.jetty.server.SecureRequestCustomizer; -import org.eclipse.jetty.server.Server; -import org.eclipse.jetty.server.ServerConnector; -import org.eclipse.jetty.server.SslConnectionFactory; -import org.eclipse.jetty.server.handler.ContextHandlerCollection; -import org.eclipse.jetty.server.handler.DefaultHandler; -import org.eclipse.jetty.server.handler.HandlerCollection; -import org.eclipse.jetty.util.log.Log; -import org.eclipse.jetty.util.log.StdErrLog; -import org.eclipse.jetty.util.ssl.SslContextFactory; -import org.eclipse.jetty.util.thread.QueuedThreadPool; -import org.eclipse.jetty.webapp.WebAppContext; -import org.junit.jupiter.api.Disabled; - -@Disabled("Not a test case") -public class TestTransparentProxyServer -{ - public static void main(String[] args) throws Exception - { - ((StdErrLog)Log.getLog()).setSource(false); - - String jettyRoot = "../../.."; - - // Setup Threadpool - QueuedThreadPool threadPool = new QueuedThreadPool(); - threadPool.setMaxThreads(100); - - // Setup server - Server server = new Server(threadPool); - server.manage(threadPool); - - // Setup JMX - MBeanContainer mbContainer = new MBeanContainer(ManagementFactory.getPlatformMBeanServer()); - server.addBean(mbContainer); - server.addBean(Log.getLog()); - - // Common HTTP configuration - HttpConfiguration config = new HttpConfiguration(); - config.setSecurePort(8443); - config.addCustomizer(new ForwardedRequestCustomizer()); - config.setSendDateHeader(true); - config.setSendServerVersion(true); - - // Http Connector - HttpConnectionFactory http = new HttpConnectionFactory(config); - ServerConnector httpConnector = new ServerConnector(server, http); - httpConnector.setPort(8080); - httpConnector.setIdleTimeout(30000); - server.addConnector(httpConnector); - - // SSL configurations - SslContextFactory sslContextFactory = new SslContextFactory.Server(); - sslContextFactory.setKeyStorePath(jettyRoot + "/jetty-server/src/main/config/etc/keystore"); - sslContextFactory.setKeyStorePassword("OBF:1vny1zlo1x8e1vnw1vn61x8g1zlu1vn4"); - sslContextFactory.setKeyManagerPassword("OBF:1u2u1wml1z7s1z7a1wnl1u2g"); - sslContextFactory.setTrustStorePath(jettyRoot + "/jetty-server/src/main/config/etc/keystore"); - sslContextFactory.setTrustStorePassword("OBF:1vny1zlo1x8e1vnw1vn61x8g1zlu1vn4"); - sslContextFactory.setExcludeCipherSuites( - "SSL_RSA_WITH_DES_CBC_SHA", - "SSL_DHE_RSA_WITH_DES_CBC_SHA", - "SSL_DHE_DSS_WITH_DES_CBC_SHA", - "SSL_RSA_EXPORT_WITH_RC4_40_MD5", - "SSL_RSA_EXPORT_WITH_DES40_CBC_SHA", - "SSL_DHE_RSA_EXPORT_WITH_DES40_CBC_SHA", - "SSL_DHE_DSS_EXPORT_WITH_DES40_CBC_SHA"); - sslContextFactory.setCipherComparator(new HTTP2Cipher.CipherComparator()); - - // HTTPS Configuration - HttpConfiguration httpsConfig = new HttpConfiguration(config); - httpsConfig.addCustomizer(new SecureRequestCustomizer()); - - // HTTP2 factory - HTTP2ServerConnectionFactory h2 = new HTTP2ServerConnectionFactory(httpsConfig); - ALPNServerConnectionFactory alpn = new ALPNServerConnectionFactory(); - alpn.setDefaultProtocol(h2.getProtocol()); - - // SSL Factory - SslConnectionFactory ssl = new SslConnectionFactory(sslContextFactory, alpn.getProtocol()); - - // HTTP2 Connector - ServerConnector http2Connector = - new ServerConnector(server, ssl, alpn, h2, new HttpConnectionFactory(httpsConfig)); - http2Connector.setPort(8443); - http2Connector.setIdleTimeout(15000); - server.addConnector(http2Connector); - - // Handlers - HandlerCollection handlers = new HandlerCollection(); - ContextHandlerCollection contexts = new ContextHandlerCollection(); - handlers.setHandlers(new Handler[] - {contexts, new DefaultHandler()}); - - server.setHandler(handlers); - - // Setup proxy webapp - WebAppContext webapp = new WebAppContext(); - webapp.setResourceBase("src/main/webapp"); - contexts.addHandler(webapp); - - // start server - server.setStopAtShutdown(true); - server.start(); - server.join(); - } -} diff --git a/tests/test-webapps/test-proxy-webapp/src/test/resources/jetty-logging.properties b/tests/test-webapps/test-proxy-webapp/src/test/resources/jetty-logging.properties new file mode 100644 index 000000000000..bf725104bbd2 --- /dev/null +++ b/tests/test-webapps/test-proxy-webapp/src/test/resources/jetty-logging.properties @@ -0,0 +1,5 @@ +org.eclipse.jetty.util.log.class=org.eclipse.jetty.util.log.StdErrLog +#org.eclipse.jetty.LEVEL=WARN +#org.eclipse.jetty.client.LEVEL=DEBUG +#org.eclipse.jetty.http.LEVEL=DEBUG +#org.eclipse.jetty.proxy.LEVEL=DEBUG diff --git a/tests/test-webapps/test-servlet-spec/pom.xml b/tests/test-webapps/test-servlet-spec/pom.xml index 522b904f6d12..35c878cc3f86 100644 --- a/tests/test-webapps/test-servlet-spec/pom.xml +++ b/tests/test-webapps/test-servlet-spec/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-servlet-spec-parent Jetty Tests :: Spec Test WebApp :: Parent diff --git a/tests/test-webapps/test-servlet-spec/test-container-initializer/pom.xml b/tests/test-webapps/test-servlet-spec/test-container-initializer/pom.xml index 8f9b9ca92e06..6f56ce2af129 100644 --- a/tests/test-webapps/test-servlet-spec/test-container-initializer/pom.xml +++ b/tests/test-webapps/test-servlet-spec/test-container-initializer/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-servlet-spec-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-container-initializer jar diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/pom.xml b/tests/test-webapps/test-servlet-spec/test-spec-webapp/pom.xml index 27e67935ba40..25e437752fab 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/pom.xml +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty.tests test-servlet-spec-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT Jetty Tests :: Webapps :: Spec Webapp test-spec-webapp diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AnnotatedListener.java b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AnnotatedListener.java index 3ca3fb7862ae..a1d314b266ad 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AnnotatedListener.java +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AnnotatedListener.java @@ -18,6 +18,7 @@ package com.acme.test; +import java.util.logging.Logger; import javax.annotation.Resource; import javax.servlet.ServletContextAttributeEvent; import javax.servlet.ServletContextAttributeListener; @@ -37,6 +38,7 @@ @WebListener public class AnnotatedListener implements HttpSessionListener, HttpSessionAttributeListener, HttpSessionActivationListener, ServletContextListener, ServletContextAttributeListener, ServletRequestListener, ServletRequestAttributeListener { + private static final Logger LOG = Logger.getLogger(AnnotatedListener.class.getName()); @Resource(mappedName = "maxAmount") private Double maxAmount; @@ -44,31 +46,31 @@ public class AnnotatedListener implements HttpSessionListener, HttpSessionAttrib @Override public void attributeAdded(HttpSessionBindingEvent se) { - // System.err.println("attributedAdded "+se); + LOG.fine("attributedAdded " + se); } @Override public void attributeRemoved(HttpSessionBindingEvent se) { - // System.err.println("attributeRemoved "+se); + LOG.fine("attributeRemoved " + se); } @Override public void attributeReplaced(HttpSessionBindingEvent se) { - // System.err.println("attributeReplaced "+se); + LOG.fine("attributeReplaced " + se); } @Override public void sessionWillPassivate(HttpSessionEvent se) { - // System.err.println("sessionWillPassivate "+se); + LOG.fine("sessionWillPassivate " + se); } @Override public void sessionDidActivate(HttpSessionEvent se) { - // System.err.println("sessionDidActivate "+se); + LOG.fine("sessionDidActivate " + se); } @Override @@ -83,84 +85,66 @@ public void contextInitialized(ServletContextEvent sce) @Override public void contextDestroyed(ServletContextEvent sce) { - // System.err.println("contextDestroyed "+sce); + LOG.fine("contextDestroyed " + sce); } @Override public void attributeAdded(ServletContextAttributeEvent scab) { - // System.err.println("attributeAdded "+scab); + LOG.fine("attributeAdded " + scab); } @Override public void attributeRemoved(ServletContextAttributeEvent scab) { - // System.err.println("attributeRemoved "+scab); + LOG.fine("attributeRemoved " + scab); } @Override public void attributeReplaced(ServletContextAttributeEvent scab) { - // System.err.println("attributeReplaced "+scab); + LOG.fine("attributeReplaced " + scab); } @Override public void requestDestroyed(ServletRequestEvent sre) { - // System.err.println("requestDestroyed "+sre); + LOG.fine("requestDestroyed " + sre); } @Override public void requestInitialized(ServletRequestEvent sre) { - // System.err.println("requestInitialized "+sre); + LOG.fine("requestInitialized " + sre); } @Override public void attributeAdded(ServletRequestAttributeEvent srae) { - // System.err.println("attributeAdded "+srae); + LOG.fine("attributeAdded " + srae); } @Override public void attributeRemoved(ServletRequestAttributeEvent srae) { - // System.err.println("attributeRemoved "+srae); + LOG.fine("attributeRemoved " + srae); } @Override public void attributeReplaced(ServletRequestAttributeEvent srae) { - // System.err.println("attributeReplaced "+srae); + LOG.fine("attributeReplaced " + srae); } @Override public void sessionCreated(HttpSessionEvent se) { - // System.err.println("sessionCreated "+se); + LOG.fine("sessionCreated " + se); } @Override public void sessionDestroyed(HttpSessionEvent se) { - // System.err.println("sessionDestroyed "+se); - } - - public void requestCompleted(ServletRequestEvent rre) - { - // TODO Auto-generated method stub - - } - - public void requestResumed(ServletRequestEvent rre) - { - // TODO Auto-generated method stub - - } - - public void requestSuspended(ServletRequestEvent rre) - { - // TODO Auto-generated method stub - + LOG.fine("sessionDestroyed " + se); } } diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AsyncListenerServlet.java b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AsyncListenerServlet.java index 00744b292544..95814c29eda8 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AsyncListenerServlet.java +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/AsyncListenerServlet.java @@ -62,29 +62,21 @@ public boolean isResourceInjected() @Override public void onComplete(AsyncEvent event) throws IOException { - // TODO Auto-generated method stub - } @Override public void onTimeout(AsyncEvent event) throws IOException { - // TODO Auto-generated method stub - } @Override public void onError(AsyncEvent event) throws IOException { - // TODO Auto-generated method stub - } @Override public void onStartAsync(AsyncEvent event) throws IOException { - // TODO Auto-generated method stub - } } diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/Bar.java b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/Bar.java index 3f556b96b1db..779039783945 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/Bar.java +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/Bar.java @@ -20,7 +20,6 @@ public class Bar { - @com.acme.initializer.Foo(2) public void someMethod() { diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/ClassLoaderServlet.java b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/ClassLoaderServlet.java index f13f3afd3321..7af05a97285a 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/ClassLoaderServlet.java +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/ClassLoaderServlet.java @@ -40,7 +40,6 @@ protected void doGet(HttpServletRequest req, HttpServletResponse resp) { try { - PrintWriter writer = resp.getWriter(); writer.println(""); writer.println(""); diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/RoleAnnotationTest.java b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/RoleAnnotationTest.java index 2d0fa4b45063..bc734a6822bd 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/RoleAnnotationTest.java +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/RoleAnnotationTest.java @@ -32,7 +32,6 @@ * * Use DeclareRolesAnnotations from within Jetty. */ - @DeclareRoles({"server-administrator", "user"}) public class RoleAnnotationTest extends HttpServlet { diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/SecuredServlet.java b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/SecuredServlet.java index 08dfa47f0d1a..33620211aa5b 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/SecuredServlet.java +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/SecuredServlet.java @@ -20,7 +20,6 @@ import java.io.IOException; import java.io.PrintWriter; -import javax.servlet.ServletException; import javax.servlet.annotation.HttpConstraint; import javax.servlet.annotation.ServletSecurity; import javax.servlet.annotation.WebServlet; @@ -32,10 +31,9 @@ @ServletSecurity(@HttpConstraint(rolesAllowed = "admin")) public class SecuredServlet extends HttpServlet { - @Override protected void doPost(HttpServletRequest req, HttpServletResponse resp) - throws ServletException, IOException + throws IOException { PrintWriter writer = resp.getWriter(); writer.println(""); diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/TestListener.java b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/TestListener.java index 21c458679fad..19f0d38932b6 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/TestListener.java +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/java/com/acme/test/TestListener.java @@ -19,6 +19,7 @@ package com.acme.test; import java.util.EventListener; +import java.util.logging.Logger; import javax.annotation.Resource; import javax.servlet.ServletContextAttributeEvent; import javax.servlet.ServletContextAttributeListener; @@ -40,6 +41,8 @@ @WebListener public class TestListener implements HttpSessionListener, HttpSessionAttributeListener, HttpSessionActivationListener, ServletContextListener, ServletContextAttributeListener, ServletRequestListener, ServletRequestAttributeListener { + private static final Logger LOG = Logger.getLogger(TestListener.class.getName()); + public static class NaughtyServletContextListener implements ServletContextListener { @@ -85,31 +88,31 @@ public void sessionIdChanged(HttpSessionEvent event, String oldSessionId) @Override public void attributeAdded(HttpSessionBindingEvent se) { - // System.err.println("attributedAdded "+se); + LOG.fine("attributeAdded " + se); } @Override public void attributeRemoved(HttpSessionBindingEvent se) { - // System.err.println("attributeRemoved "+se); + LOG.fine("attributeRemoved " + se); } @Override public void attributeReplaced(HttpSessionBindingEvent se) { - // System.err.println("attributeReplaced "+se); + LOG.fine("attributeReplaced " + se); } @Override public void sessionWillPassivate(HttpSessionEvent se) { - // System.err.println("sessionWillPassivate "+se); + LOG.fine("sessionWillPassivate " + se); } @Override public void sessionDidActivate(HttpSessionEvent se) { - // System.err.println("sessionDidActivate "+se); + LOG.fine("sessionDidActivate " + se); } @Override @@ -165,84 +168,66 @@ public void contextInitialized(ServletContextEvent sce) @Override public void contextDestroyed(ServletContextEvent sce) { - // System.err.println("contextDestroyed "+sce); + LOG.fine("contextDestroyed " + sce); } @Override public void attributeAdded(ServletContextAttributeEvent scab) { - // System.err.println("attributeAdded "+scab); + LOG.fine("attributeAdded " + scab); } @Override public void attributeRemoved(ServletContextAttributeEvent scab) { - // System.err.println("attributeRemoved "+scab); + LOG.fine("attributeRemoved " + scab); } @Override public void attributeReplaced(ServletContextAttributeEvent scab) { - // System.err.println("attributeReplaced "+scab); + LOG.fine("attributeReplaced " + scab); } @Override public void requestDestroyed(ServletRequestEvent sre) { - // System.err.println("requestDestroyed "+sre); + LOG.fine("requestDestroyed " + sre); } @Override public void requestInitialized(ServletRequestEvent sre) { - // System.err.println("requestInitialized "+sre); + LOG.fine("requestInitialized " + sre); } @Override public void attributeAdded(ServletRequestAttributeEvent srae) { - // System.err.println("attributeAdded "+srae); + LOG.fine("attributeAdded " + srae); } @Override public void attributeRemoved(ServletRequestAttributeEvent srae) { - // System.err.println("attributeRemoved "+srae); + LOG.fine("attributeRemoved " + srae); } @Override public void attributeReplaced(ServletRequestAttributeEvent srae) { - // System.err.println("attributeReplaced "+srae); + LOG.fine("attributeReplaced " + srae); } @Override public void sessionCreated(HttpSessionEvent se) { - // System.err.println("sessionCreated "+se); + LOG.fine("sessionCreated " + se); } @Override public void sessionDestroyed(HttpSessionEvent se) { - // System.err.println("sessionDestroyed "+se); - } - - public void requestCompleted(ServletRequestEvent rre) - { - // TODO Auto-generated method stub - - } - - public void requestResumed(ServletRequestEvent rre) - { - // TODO Auto-generated method stub - - } - - public void requestSuspended(ServletRequestEvent rre) - { - // TODO Auto-generated method stub - + LOG.fine("sessionDestroyed " + se); } } diff --git a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/webapp/index.html b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/webapp/index.html index 0919b4bc2c13..950830f9f4dc 100644 --- a/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/webapp/index.html +++ b/tests/test-webapps/test-servlet-spec/test-spec-webapp/src/main/webapp/index.html @@ -6,7 +6,7 @@ - +
Demo Home
@@ -21,7 +21,7 @@

Servlet 3.1 Test WebApp

  • servlet container initializers.
  • multi-part upload support. -The source repository for this test is available here. +The source repository for this test is available here.

    Test Servlet 2.5/3.0 Annotations, Fragments and Initializers

    @@ -71,7 +71,7 @@

    Test ClassPath Isolation


    - +
    diff --git a/tests/test-webapps/test-servlet-spec/test-web-fragment/pom.xml b/tests/test-webapps/test-servlet-spec/test-web-fragment/pom.xml index c69489d37b20..80509eb3bdeb 100644 --- a/tests/test-webapps/test-servlet-spec/test-web-fragment/pom.xml +++ b/tests/test-webapps/test-servlet-spec/test-web-fragment/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-servlet-spec-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT Jetty Tests :: WebApp :: Servlet Spec :: Fragment Jar diff --git a/tests/test-webapps/test-simple-webapp/pom.xml b/tests/test-webapps/test-simple-webapp/pom.xml index 382406685f3c..05a480152501 100644 --- a/tests/test-webapps/test-simple-webapp/pom.xml +++ b/tests/test-webapps/test-simple-webapp/pom.xml @@ -4,7 +4,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-simple-webapp diff --git a/tests/test-webapps/test-webapp-rfc2616/pom.xml b/tests/test-webapps/test-webapp-rfc2616/pom.xml index 5acbe622cb79..76336c615f7a 100644 --- a/tests/test-webapps/test-webapp-rfc2616/pom.xml +++ b/tests/test-webapps/test-webapp-rfc2616/pom.xml @@ -4,11 +4,10 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT test-webapp-rfc2616 Jetty Tests :: WebApp :: RFC2616 - http://www.eclipse.org/jetty war ${project.groupId}.rfc2616 diff --git a/tests/test-webapps/test-websocket-client-webapp/pom.xml b/tests/test-webapps/test-websocket-client-webapp/pom.xml index 6bd4a5cb9e32..aedca8799288 100644 --- a/tests/test-webapps/test-websocket-client-webapp/pom.xml +++ b/tests/test-webapps/test-websocket-client-webapp/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0 diff --git a/tests/test-webapps/test-weld-cdi-webapp/pom.xml b/tests/test-webapps/test-weld-cdi-webapp/pom.xml index 00f6f2ab45df..6e3388e71872 100644 --- a/tests/test-webapps/test-weld-cdi-webapp/pom.xml +++ b/tests/test-webapps/test-weld-cdi-webapp/pom.xml @@ -3,7 +3,7 @@ org.eclipse.jetty.tests test-webapps-parent - 9.4.32-SNAPSHOT + 9.4.33-SNAPSHOT 4.0.0