Class JavaHttpTransport
- All Implemented Interfaces:
Closeable,AutoCloseable,HttpTransport
HttpTransport implementation backed by the JDK's built-in HttpClient.
This is the default transport used by RestClient. It is built into the
juneau-rest-client artifact, requires no external dependencies, and is always available on Java 11+.
It is auto-discovered via ServiceLoader and can also be instantiated explicitly:
When a pooled keep-alive connection is torn down by the server before any response bytes are received (an
immediate EOF surfaced by the JDK client as an IOException whose message is
"HTTP/1.1 header parser received no bytes"), this transport replays the request exactly once on a fresh
connection — but only when TransportRequest.isSafeToReplay() proves it is safe (an idempotent method
with an absent or repeatable body). The JDK client already retries body-less GET requests itself, but not
other idempotent methods (e.g. PUT/DELETE); this backstop closes that gap while never replaying a
POST or any other non-idempotent request.
For SSRF-guard-active (@Remote) requests (see TransportRequest.isSsrfGuardActive()), this
transport pin-on-connects: it resolves the request host, selects an address that passes
RemoteUrlPolicy, and rewrites the request URI to that literal address
(preserving the original host via an explicit Host header) so the socket connects only to the
validated address — and re-runs the same check on every Location hop via
PolicyEnforcedRedirects. The JDK HttpClient has no connect-time/DNS SPI, so an IP-literal
rewrite cannot preserve TLS SNI/hostname verification for the original hostname; per the locked design, policy
-covered HTTPS requests are therefore refused (fail closed) on this transport — use a transport
that supports connect-time pinning (e.g. Apache HttpClient 4.5/5), or set allowPrivateUrls(true) if the
target is an intentional local-dev/intranet endpoint. A policy-covered request is also refused if the
underlying HttpClient was built with automatic redirect-following enabled (HttpClient.Redirect.NORMAL or
HttpClient.Redirect.ALWAYS), since this transport cannot re-validate hops that client follows on its own; build it
with the default HttpClient.Redirect.NEVER (the JDK default) to let this transport's own redirect loop apply.
See Also:
- Since:
- 9.2.1
-
Method Summary
Modifier and TypeMethodDescriptionstatic JavaHttpTransportBuilderbuilder()Returns a new builder for this transport.static JavaHttpTransportcreate()Returns a new instance backed by a defaultHttpClient.execute(TransportRequest request) Executes the given request and returns the response.booleanReturnstrueif this transport can honor the SSRF guardrail's connect-time contract for a policy-covered request (TransportRequest.isSsrfGuardActive()): pin-on-connect to a resolved address that has passed the deny-private policy, and Juneau-controlled redirect revalidation (no fallback to the transport's own auto-follow).Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, waitMethods inherited from interface org.apache.juneau.rest.client.HttpTransport
close
-
Method Details
-
builder
Returns a new builder for this transport.- Returns:
- A new builder. Never
null .
-
create
Returns a new instance backed by a defaultHttpClient.- Returns:
- A new instance. Never
null .
-
execute
Description copied from interface:HttpTransportExecutes the given request and returns the response.The caller is responsible for closing the returned
TransportResponseafter consuming the body.- Specified by:
executein interfaceHttpTransport- Parameters:
request- The fully-resolved request. Must not benull .- Returns:
- The response. Never
null . - Throws:
TransportException- If a network-level error occurs.
-
supportsUrlPolicy
Description copied from interface:HttpTransportReturnstrueif this transport can honor the SSRF guardrail's connect-time contract for a policy-covered request (TransportRequest.isSsrfGuardActive()): pin-on-connect to a resolved address that has passed the deny-private policy, and Juneau-controlled redirect revalidation (no fallback to the transport's own auto-follow).The default implementation returns
false(fail closed): an unknown/caller-supplied transport that has not affirmatively opted in is presumed unable to honor the contract, soRestRequest#run()rejects policy-covered requests against it rather than silently connecting without the guardrail. First-party transports that construct and fully control their own underlying HTTP client override this to returntrue.- Specified by:
supportsUrlPolicyin interfaceHttpTransport- Returns:
trueif this transport supports pin-on-connect + redirect revalidation for policy-covered requests.
-