Hi,
I'm currently on vacation so I can't give a fully considered response,
however I'll quickly make two points:
with regards to request trailers, the key decision is when they are
available, specially with async. Does the application have to read content
to -1 or onAllDataRead before the trailers are available? I think yes.
Then it does not make much sense to make them available via the normal
header API and I think they need their own API.
For responses, a simple addTrailer API is also not sufficient again because
of the timing of when it may be called. It may be too late to call
addTrailer after some content has been written because if the response has
been committed the container may have choosen to not use HTTP/1.1 chunking
for the respone (because content-length was known or because
Connection:close had been specified), so it may be impossible to add the
trailers. Thus I think we need an API that allows the application to
signal it's intent to maybe set trailers, so the container can choose a
transport framing that does support trailers. That is why an API that
uses Supplier or Future or similar makes sense, as it can be called early
to indicate that trailers may be supplied and then the trailers can be set
later (during and/or after content generation).
I'll respond more early next week.
cheers
On 7 Apr. 2017 4:28 am, "Shing Wai Chan" <shing.wai.chan_at_oracle.com> wrote:
In section 5.2 of servlet spec, we have:
"To be successfully transmitted back to the client, headers must be set
before the response is committed. Headers set after the response is
committed will be ignored by the servlet container"
So servlet does not support trailer headers, as specified in RFC7230
[1]. This is an attempt to provide better HTTP support for protocols built
on
top of it that rely on this trailer feature (such as gRPC).
In the following we will investigate the various options of supporting
trailer headers in servlet.
A. Reading the request trailer headers.
a) StandardHeader:
Request trailer headers are standard http request headers.
This can be accessed by using standard header APIs in HttpServletRequest.
No new API is added in this case.
b) HttpServletRequest:
Add the following API to HttpServletRequest:
public String getTrailer(String name);
public Collection<String> getTrailers(String name);
public Collection<String> getTrailerNames();
Note: existing methods in HttpServletRequest interface use Enumeration
here.
c) RequestTrailerMap (from Simone Bordet):
Add the following API to HttpServletRequest:
public Map<String, String> getTrailers();
d) RequestTrailerField (from Simone Bordet):
Add the following API to HttpServletRequest:
public TrailerFields getTrailers();
TrailerFields is a class representing a list of trailer fields
Note: For (b)-(d) above, then the trailer headers will "not" be
available to HttpServletRequest#getHeader, #getHeaders, #getHeaderNames.
B. Writing the response trailer headers.
a) HttpServletResponse:
public void addTrailer(String name, String value)
public void getTrailer(String name)
public Collection<String> getTrailers(String name)
public Collection<String> getTrailerNames()
b) Supplier (from Simone Bordet):
public void setTrailers(Supplier<TrailerFields>);
where TrailerFields is defined in A.d above.
c) SupplierMap (cf. A.c, above)
public void setTrailers(Supplier<Map<String, String>>);
ACTION: Please reply by April 11, 2017, COB. In the absence of responses,
I am inclined
to select A.a HttpServletRequest and B.a HttpServletResponse.
Shing Wai Chan
ps.
[1]
https://tools.ietf.org/rfc/rfc7230.txt