Re: [cors] JAX-RS and preflight

2011-12-02 Thread Benson Margulies
Jonas,

Let me circle back to the top now and see if I can play this back.

1. Of course, when writing a server, it's up to me to implement access
control decisions.

2. To protect a plethora of poorly-protected servers out there, CORS
puts an additional level of access control in clients.

3. To expose resources cross-origin, my service has to reassure the
client that it does, indeed, know what it is doing. That  reassurance
is delivers via the CORS headers.

4. There's a impedance mismatch between the CORS model of resource
control, which is URI+method, and the JAX-RS model, which adds other
headers.

5. A server thus must return CORS indications at the level  of
URI+method. This 'opens the door' in the client -- and then the server
is responsible for imposing any fine-grained access control that it
wants at the level of the other headers.

--benson


On Thu, Dec 1, 2011 at 8:07 PM, Jonas Sicking jo...@sicking.cc wrote:
 On Thu, Dec 1, 2011 at 4:35 PM, Benson Margulies bimargul...@gmail.com 
 wrote:
 Here's where I am not following:

 If I am trying to protect a server, I will look at the request, and if
 I don't like it, I will return a 401. Period. I'm happy to have the
 Origin header to help me do that. I don't see what the rest of the
 complex processing does for me.

 As someone aware of CORS the rest of the processing doesn't really do
 anything for you.

 However, imagine that you set up your server 5 years ago. Or that you
 weren't aware of the existence of CORS. Then you obviously wouldn't be
 looking at the Origin header. Or return a 401. You would just gladly
 server whatever request that was posed to you.

 This is why CORS has additional checks in the client. To ensure that
 servers that aren't aware of CORS don't return any sensitive
 information to the requesting page, or that the requesting page can't
 case sensitive side effects on the server.

 In particular, would I delegate the work to the CORS client? How do I
 know that the client really implements the spec?  Consider
 'Expose-Headers' ... If I don't want them to go to a particular
 origin, why would I bother to return all this metadata in a preflight
 instead of, well, just not returning them? Am I just trying to make it
 easier for client-side processes to understand my rules?

 The idea is to give you plenty of tools to make it easy to protect yourself.

 If you have lots of code running on your server and you are not fully
 sure what all of it does, but you still want to expose some specific
 header to the requesting page, you simply whitelist that header. That
 way you don't have to worry about making the rest of your code
 foolproof.

 So while you can provide belts, we'll still provide suspenders :-)

 / Jonas



Re: [cors] JAX-RS and preflight

2011-12-02 Thread Jonas Sicking
On Fri, Dec 2, 2011 at 5:29 AM, Benson Margulies bimargul...@gmail.com wrote:
 Jonas,

 Let me circle back to the top now and see if I can play this back.

 1. Of course, when writing a server, it's up to me to implement access
 control decisions.

 2. To protect a plethora of poorly-protected servers out there, CORS
 puts an additional level of access control in clients.

 3. To expose resources cross-origin, my service has to reassure the
 client that it does, indeed, know what it is doing. That  reassurance
 is delivers via the CORS headers.

Correct so far.

 4. There's a impedance mismatch between the CORS model of resource
 control, which is URI+method, and the JAX-RS model, which adds other
 headers.

CORS provides the ability for fine-grained opt-in to various aspects
of http. This so that you can choose which parts of http you want to
guarantee that you have secured in your server-side scripts. I.e. CORS
isn't simply a on/off switch requiring perfect knowledge of everything
you do on your server in order to flip to the on mode.

However the fine-grained opt-in is only so fine-grained. We don't for
example have the ability to say I'm only fine with receiving the
x-my-header header if it contains one of the following values, or say
I only want to expose the x-my-response-header if it isn't doesn't
start with 'user-id:.

Similarly, we don't provide the values of any headers when making the
preflight OPTIONS request.

My english isn't good enough to say if this qualifies as an impidence
mismatch or not (wikipedia was unhelpful [1]). But I agree that it
means that means that you have to do some security checks in the code
that handles the request, and can't rely exclusively on CORS enforcing
your security model.

[1] http://en.wikipedia.org/wiki/Impedance_mismatch

 5. A server thus must return CORS indications at the level  of
 URI+method. This 'opens the door' in the client -- and then the server
 is responsible for imposing any fine-grained access control that it
 wants at the level of the other headers.

Yup.

/ Jonas



[cors] JAX-RS and preflight

2011-12-01 Thread Benson Margulies
There's a problem with REST-ful services, as exemplified by the JAX-RS
standard, and CORS as drafted.

A JAX-RS server names a resource, in part, via the content-type of a
request. A POST with content-type of application/json names a
different resource (in as much as it selects a different method to
call) that a POST with content-type text/plain.

The problem here is that a preflight OPTIONS is defined to *not* pass
the content type unless it is simple. Thus, the service implementation
can't reliably tell what resource is under discussion.

As things are, a service would have to take a common posture for all
preflights given the URL and Accept(-*) headers, and ignoring the
content type.

Would you consider defining an Ac-Request-Content-Type header to pass
a non-simple content type on a preflight?




Re: [cors] JAX-RS and preflight

2011-12-01 Thread Julian Reschke

On 2011-12-01 21:20, Benson Margulies wrote:

There's a problem with REST-ful services, as exemplified by the JAX-RS
standard, and CORS as drafted.

A JAX-RS server names a resource, in part, via the content-type of a
request. A POST with content-type of application/json names a
different resource (in as much as it selects a different method to
call) that a POST with content-type text/plain.


That seems to be entirely JAX-RS problem. The *resource* is supposed to 
be identified by the request-URI.



The problem here is that a preflight OPTIONS is defined to *not* pass
the content type unless it is simple. Thus, the service implementation
can't reliably tell what resource is under discussion.


Even if OPTIONS would be sent with a Content-Type header field, that 
field, by definition, would identify the internet media type of the 
request body.



As things are, a service would have to take a common posture for all
preflights given the URL and Accept(-*) headers, and ignoring the
content type.


Absolutely.


Would you consider defining an Ac-Request-Content-Type header to pass
a non-simple content type on a preflight?


Unless I'm missing something here you are definitively trying to do the 
wrong thing.


Best regards, Julian




Re: [cors] JAX-RS and preflight

2011-12-01 Thread Benson Margulies
Let me try to present this more clearly.

First of all, I did not design or implement JAX-RS itself. The
committee that designed it might have done something wrong in their
dispatching approach. However, *I* am merely working on implementing a
facility for the resource side of CORS in a JAX-RS framework.

Perhaps it would be less disturbing if I characterized the situation
as follows: JAX-RS dispatches the job of serving content at a smaller
granularity than an HTTP/CORS 'resource'. It operates on the
combination of resource+content-type+accepts+accepts-language.

All of those facts are available to a preflight except for the content
type when the content-type is non-simple.

My humble request is for you to consider defining one more 'request'
header for preflight: access-control-request-content-type -- that the
client would send to the server on the OPTIONS command.

There are many, many, services written with JAX-RS -- representing  a
classic case of that old standardization chestnut: 'existing
practice.' What I'm proposing here would be trivial for client
implementations, so I would think that the authors of the CORS
proposal would at least grant this idea a full 5 minutes of thought
before rejecting it.

Obviously, if you do reject this, it will not be the end of the
internet as we know it.



On Thu, Dec 1, 2011 at 3:57 PM, Julian Reschke julian.resc...@gmx.de wrote:
 On 2011-12-01 21:20, Benson Margulies wrote:

 There's a problem with REST-ful services, as exemplified by the JAX-RS
 standard, and CORS as drafted.

 A JAX-RS server names a resource, in part, via the content-type of a
 request. A POST with content-type of application/json names a
 different resource (in as much as it selects a different method to
 call) that a POST with content-type text/plain.


 That seems to be entirely JAX-RS problem. The *resource* is supposed to be
 identified by the request-URI.


 The problem here is that a preflight OPTIONS is defined to *not* pass
 the content type unless it is simple. Thus, the service implementation
 can't reliably tell what resource is under discussion.


 Even if OPTIONS would be sent with a Content-Type header field, that field,
 by definition, would identify the internet media type of the request body.


 As things are, a service would have to take a common posture for all
 preflights given the URL and Accept(-*) headers, and ignoring the
 content type.


 Absolutely.


 Would you consider defining an Ac-Request-Content-Type header to pass
 a non-simple content type on a preflight?


 Unless I'm missing something here you are definitively trying to do the
 wrong thing.

 Best regards, Julian




Re: [cors] JAX-RS and preflight

2011-12-01 Thread Julian Reschke

On 2011-12-02 00:11, Benson Margulies wrote:

Let me try to present this more clearly.

First of all, I did not design or implement JAX-RS itself. The
committee that designed it might have done something wrong in their
dispatching approach. However, *I* am merely working on implementing a
facility for the resource side of CORS in a JAX-RS framework.


And I have to admit that I'm a member of that Expert Group. Apparently 
not paying sufficient attention, though.



Perhaps it would be less disturbing if I characterized the situation
as follows: JAX-RS dispatches the job of serving content at a smaller
granularity than an HTTP/CORS 'resource'. It operates on the
combination of resource+content-type+accepts+accepts-language.


Varying the *response* based on Accept and Accept-Language is ok. It 
doesn't change the resource you're talking to, though.


Content-Type really doesn't belong into this at all.


All of those facts are available to a preflight except for the content
type when the content-type is non-simple.


That may be true, but doesn't affect what HTTP resource you're talking to.


My humble request is for you to consider defining one more 'request'
header for preflight: access-control-request-content-type -- that the
client would send to the server on the OPTIONS command.

There are many, many, services written with JAX-RS -- representing  a
classic case of that old standardization chestnut: 'existing
practice.' What I'm proposing here would be trivial for client
implementations, so I would think that the authors of the CORS
proposal would at least grant this idea a full 5 minutes of thought
before rejecting it.


Please don't. It's totally the wrong thing to do here.

If JAX-RS takes the position that the Content-Type on a request affects 
the resource being identified it totally needs to be fixed.



...


Best regards, Julian



Re: [cors] JAX-RS and preflight

2011-12-01 Thread Jonas Sicking
On Thu, Dec 1, 2011 at 12:20 PM, Benson Margulies bimargul...@gmail.com wrote:
 There's a problem with REST-ful services, as exemplified by the JAX-RS
 standard, and CORS as drafted.

 A JAX-RS server names a resource, in part, via the content-type of a
 request. A POST with content-type of application/json names a
 different resource (in as much as it selects a different method to
 call) that a POST with content-type text/plain.

 The problem here is that a preflight OPTIONS is defined to *not* pass
 the content type unless it is simple. Thus, the service implementation
 can't reliably tell what resource is under discussion.

 As things are, a service would have to take a common posture for all
 preflights given the URL and Accept(-*) headers, and ignoring the
 content type.

 Would you consider defining an Ac-Request-Content-Type header to pass
 a non-simple content type on a preflight?

You can always allow the OPTIONS request and make the security
decision once you get the actual request.

The main point of the OPTIONS request is to protect servers that
aren't aware of CORS at all. Clearly a CORS+JAX-RS doesn't fall into
this category.

/ Jonas



Re: [cors] JAX-RS and preflight

2011-12-01 Thread Benson Margulies
On Thu, Dec 1, 2011 at 6:53 PM, Jonas Sicking jo...@sicking.cc wrote:
 On Thu, Dec 1, 2011 at 12:20 PM, Benson Margulies bimargul...@gmail.com 
 wrote:
 There's a problem with REST-ful services, as exemplified by the JAX-RS
 standard, and CORS as drafted.

 A JAX-RS server names a resource, in part, via the content-type of a
 request. A POST with content-type of application/json names a
 different resource (in as much as it selects a different method to
 call) that a POST with content-type text/plain.

 The problem here is that a preflight OPTIONS is defined to *not* pass
 the content type unless it is simple. Thus, the service implementation
 can't reliably tell what resource is under discussion.

 As things are, a service would have to take a common posture for all
 preflights given the URL and Accept(-*) headers, and ignoring the
 content type.

 Would you consider defining an Ac-Request-Content-Type header to pass
 a non-simple content type on a preflight?

 You can always allow the OPTIONS request and make the security
 decision once you get the actual request.

Sure, if the server is the concerned party  but 


 The main point of the OPTIONS request is to protect servers that
 aren't aware of CORS at all. Clearly a CORS+JAX-RS doesn't fall into
 this category.

As a superannuated security person, I thought that the point of CORS
was to protect clients from cross-scripting pranks of web pages, not
to protect servers from anything. Nothing in CORS involves returning a
401. Wouldn't the actual access decision be made on the server instead
of on the client if we were protecting the server? Why return all this
stuff to the client instead of failing requests or censoring headers?

Something tells me that there's a theory here that I haven't read yet.



 / Jonas



Re: [cors] JAX-RS and preflight

2011-12-01 Thread Jonas Sicking
On Thu, Dec 1, 2011 at 4:14 PM, Benson Margulies bimargul...@gmail.com wrote:
 On Thu, Dec 1, 2011 at 6:53 PM, Jonas Sicking jo...@sicking.cc wrote:
 On Thu, Dec 1, 2011 at 12:20 PM, Benson Margulies bimargul...@gmail.com 
 wrote:
 There's a problem with REST-ful services, as exemplified by the JAX-RS
 standard, and CORS as drafted.

 A JAX-RS server names a resource, in part, via the content-type of a
 request. A POST with content-type of application/json names a
 different resource (in as much as it selects a different method to
 call) that a POST with content-type text/plain.

 The problem here is that a preflight OPTIONS is defined to *not* pass
 the content type unless it is simple. Thus, the service implementation
 can't reliably tell what resource is under discussion.

 As things are, a service would have to take a common posture for all
 preflights given the URL and Accept(-*) headers, and ignoring the
 content type.

 Would you consider defining an Ac-Request-Content-Type header to pass
 a non-simple content type on a preflight?

 You can always allow the OPTIONS request and make the security
 decision once you get the actual request.

 Sure, if the server is the concerned party  but 


 The main point of the OPTIONS request is to protect servers that
 aren't aware of CORS at all. Clearly a CORS+JAX-RS doesn't fall into
 this category.

 As a superannuated security person, I thought that the point of CORS
 was to protect clients from cross-scripting pranks of web pages, not
 to protect servers from anything. Nothing in CORS involves returning a
 401. Wouldn't the actual access decision be made on the server instead
 of on the client if we were protecting the server? Why return all this
 stuff to the client instead of failing requests or censoring headers?

 Something tells me that there's a theory here that I haven't read yet.

CORS isn't intended to fix cross-scripting pranks at all. At least
if you are referring to the traditional meaning of XSS attacks.

The intent of CORS is to allow websites to communicate with other
servers without exposing existing web servers to new attack vectors.
Specifically to CSRF-like attacks.

So CORS is very much designed to protect (or rather not harm)
servers. Not to do anything related to XSS.

However, in allowing websites to talk to other servers in a safe
manner, it removes the need to use script elements to do so. This
use of script elements has traditionally opened up websites to XSS
attack vectors. So while CORS isn't designed to protect against XSS
attacks, it does obsolete XSS sensitive technology.

I hope that makes sense?

/ Jonas