I'm in the process of implementing a public API for my web service. Security is a key concern as money is involved.
It seems the current common practice for "authenticating" users in API requests is by confirming message authenticity, having the user send along a HMAC of the parameters (including a unique nonce), for each request.
This is fine, but it uses a shared secret: both the server and the client have to store the private key in order to generate the HMAC.
I don't like this. What's the point in going to all the hoopla with salting/hashing passwords, if I'm then going to start storing unencrypted shared secrets in the database?
Is there a better way? I was thinking of using GPG, and having the user provide their own GPG public key for me to store; they could then sign messages using their private key. However, I fear this might be a bit of a pain for Windows users to play with.
In general, isn't public/private key signing a much better way to do this? There must be some reason why everyone is choosing HMAC with a shared secret... what am I missing?
I will of course set limits on customer interactions via APIs, provide notifications and limit removing money from the system, but a great deal of damage could still be done if the shared secrets were leaked.