jsr339-experts@jax-rs-spec.java.net

[jsr339-experts] Re: [jax-rs-spec users] Re: _at_Consumes matching when Content-Type is null

From: Bill Burke <bburke_at_redhat.com>
Date: Thu, 23 May 2013 16:11:25 -0400

On 5/23/2013 3:58 PM, Sergey Beryozkin wrote:
> On 23/05/13 19:18, Bill Burke wrote:
>>
>>
>> On 5/23/2013 1:47 PM, Marek Potociar wrote:
>>>
>>> On May 23, 2013, at 7:34 PM, Bill Burke <bburke_at_redhat.com> wrote:
>>>
>>>>
>>>>
>>>> On 5/23/2013 11:00 AM, Marek Potociar wrote:
>>>>>
>>>>> On May 22, 2013, at 9:56 PM, Bill Burke <bburke_at_redhat.com> wrote:
>>>>>
>>>>>>
>>>>>> @Consumes("text/plain")
>>>>>> @POST
>>>>>> @Path("plain")
>>>>>> public void tckPOST();
>>>>>>
>>>>>> @Path("start")
>>>>>> @POST
>>>>>> public void start()
>>>>>>
>>>>>> @Path("start")
>>>>>> @POST
>>>>>> @Consumes("application/xml")
>>>>>> public void start(XML xml)
>>>>>>
>>>>>>
>>>>>> I have 2 different test cases whose solutions currently conflict.
>>>>>>
>>>>>>
>>>>>> Case #1:
>>>>>>
>>>>>> The TCK is posting a NULL entity with no Content-Type header to:
>>>>>>
>>>>>> POST /plain
>>>>>>
>>>>>> The TCK is expecting this to match tckPOST() even though two
>>>>>> different sections of the spec conflict:
>>>>>>
>>>>>> - Section 4.2.1.1 Says that if the request does not contain a
>>>>>> Content-Type, then application/octet-stream is used. This is for
>>>>>> matching bodies though.
>>>>>
>>>>> Yes, I think that one should not apply to requests without a body.
>>>>>
>>>>>>
>>>>>> - The matching algorithm in Step 3(a) says:
>>>>>>
>>>>>> "The media type of the request entity body *(if any)* is supported
>>>>>> by the input format"
>>>>>>
>>>>>> What does *if any* mean? The TCK seems to assume that if the
>>>>>> Content-Type header is null, then the @Consumes annotation is
>>>>>> ignored. Or am I supposed to look at the method to see if it is
>>>>>> expecting a request body?
>>>>>
>>>>> I guess that's the correct interpretation. FWIW, the whole test is
>>>>> good in that it uncovers these hidden portability issues, but I
>>>>> would in this case even support removing the test as it is testing a
>>>>> completely artificial use case.
>>>>>
>>>>
>>>> Only real way to test for a body is to either a) check the
>>>> Content-Type header is null or b) check the resource method to see if
>>>> it expects a body. So the 2 start() methods would be ambiguous so
>>>> I'm free to match them however I see fit. This is another user
>>>> posted use case where they want a no-param start() method to match if
>>>> there is no content.
>>>
>>> What about checking Content-Length and/or trying to read from an
>>> entity input stream?
>>>
>>
>> You can't read from the input stream. Bytes may not be ready and you
>> probably do not want to block for any amount of time. I guess checking
>> for Content-Length or Transfer-Encoding would work as long as you're not
>> doing some COMET protocol with JAX-RS.
>>
>>
> I opened a JIRA request recently for the spec to stay that checking for
> 'Content-Length: 0' was the only portable way for the JAX-RS runtime to
> tell if a request was empty or not. I tried checking for Content-Length,
> in one case (with async client via HTTP client) I got a non empty
> payload with no Content-Length at all, and when I tried to do
> InputStream.available() I got one of security tests failing...
>

I guess checking to see if the resource method expects a body is the
only thing you can reliably do then?

-- 
Bill Burke
JBoss, a division of Red Hat
http://bill.burkecentral.com