views:

622

answers:

4

I'm working on a REST service that has a few requirements:

  1. It has to be secure.
  2. Users should not be able to forge requests.

My current proposed solution is to have a custom Authorization header that look like this (this is the same way that the amazon web services work):

Authorization: MYAPI username:signature

My question is how to form the signature. When the user logs into the service they are given a secret key which they should be able to use to sign requests. This will stop other users submitting requests on their behalf, but will not stop them forging requests.

The application that will be using this service is an iPhone application, so I was thinking we could have a public key embedded in the application which we can do an additional signature with, but does this mean we'll have to have two signatures, one for the user key and one for the app key?

Any advice would be greatly appreciated, I'd quite like to get this right the first time.

+1  A: 

I think the simplest way to do this right would be to use HTTPS client authentication. Apple's site has a thread on this very subject.

Edit: to handle authorization, I would create a separate resource (URI) on the server for each user, and only permit that (authenticated) user to manipulate this resource.

Steven Huwig
How does this stop users from forging requests?
jonnii
HTTPS client authentication requires the client to have a valid public key certificate. Unless you mean by "forging requests" that an authenticated user is somehow making unauthorized requests, which is an authorization problem not an authentication problem.
Steven Huwig
That's the problem i'm trying to address, I updated the topic to reflect this. How would you suggest authorizing valid requests?
jonnii
+2  A: 

What's wrong with HTTP Digest Authentication?

S.Lott
Firstly I'm going to have to use SSL for the requests (which is fine), but it doesn't stop a user logging into the API from a non iPhone device and submitting forged requests.
jonnii
How can they forge a request via digest authentication? How did they get the current nonce value and create an acceptable digest response?
S.Lott
They can forge a request because they can create a 3rd party client application that logs into the api, at which point they can submit their own requests. I need to verify the source of the api request.
jonnii
Why can't you use a client nonce in the response which is a signature string unique to each iPhone?
S.Lott
When the user logs in we get their device id, so that might work. I'll investigate this and see what I come up with.
jonnii
If you can read the device id, so can the attacker. It is no complete protection. It does however make the attack difficult which might be good enough. Combine it with extensive logging and you should be able to identify cheating and delete all entries for (and block?) that user.
Johan Öbrink
A: 

There is a better discussion of this here:

http://stackoverflow.com/questions/7551/best-practices-for-securing-a-rest-api-web-service

jonnii
+2  A: 

The answer is simple: It cannot be done. As soon as you ship any solution to the end user, he or she can allways attack the server it is communicating with. The most common version of this problem is cheating with hi-score lists in Flash games. You can make it harder by embedding some sort of encryption in the client and obfuscating the code... But all compiled and obfuscated code can allways be decompiled and unobfuscated. It is just a matter of how much time and money you are willing to spend and likewise for the potential attacker.

So your concern is not how to try to prevent the user from sending faulty data to your system. It is how to prevent the user from damaging your system. You have to design your interfaces so that all damage done by faulty data only affects the user sending it.

Johan Öbrink
In this case we're going to be deploying to the iphone, so there is a risk of someone decompiling the code. You raise very valid points in your post about limiting the ability to damage only that users data, in this case they'd be able to cheat in a game, so we need to be able to identify cheaters and deal with them effectively. No easy task.
jonnii
The only way to secure av game is to run it entirely ön the server and only sending the users actions over the wire. What I usually do is:1. Make cheating difficult2. Save as much information as possible. Cheating is usually reasonably easy to spot so you can delete all entries for that user afterwards.
Johan Öbrink
If you are developing a GAME, and this is a CHEATING problem, then you have a whole other host of tools available to you - depending on whether it's a game of skill or game of chance. Generally speaking, player performance can be measured statistically and strange patterns can be spotted - that's how many fraud detection systems work in the entertainment industry. Another thing that instantly comes to mind is algorithmic design which introduces certain measurable properties to the game - for example, error accumulation in floating point numbers.
mst