ChatGPT解决这个技术问题 Extra ChatGPT

Securing an API: SSL & HTTP Basic Authentication vs Signature

When designing an API for our web app, we'll use the their subdomain as the 'username' and generate an API key/shared secret. Firstly, is it ok to use the subdomain as the username? I don't see the benefit of generating another key.

Different APIs seem to do one of two things:

Use HTTP Basic Authentication with SSL

In every request the username is set to the subdomain and the password to the API key. Since we're using SSL then this should be safe from spoofing.

Notable APIs: Google Checkout, Freshbooks, GitHub, Zendesk

Create a Signature of the Request with the Shared Secret

Normally achieved by ordering the key/value pairs and using HMAC-SHA1 with the shared secret to generate the signature. The signature is then sent with the request and verified at the other end.

Notable APIs: Google Checkout, Amazon AWS

PS: thats no mistake, Google Checkout supports both

Edit: Just read that OAuth 2 is dropping signatures in favour of sending a username/password via SSL.

Any opinions from anyone on what to pick: SSL vs Signature?


M
Marcus

HTTP Basic Authentication over SSL is perfectly secure from my research.

After all, using SSL (strictly TLS now) means the transport layer is encrypted and we can safely assume any information passed over this is secure and has not been tampered with.

Therefore passing the username and password without generating a signature is sufficient.


e
emboss

Igor's answer is not entirely true. Although TLS does ensure that the transport layer is encrypted and secure, it is still not as secure as using for instance TLS with mutual authentication where the client authenticates using "strong cryptography" in the form of a digital signature. There are two major reasons why this is still better than Basic Authentication over TLS:

Passwords are passwords and I'd assume three out of the now 7 billion people on our planet use a 30 character password that is completely random. The rest of us chose something with a lot less entropy. Therefore it is much easier for an attacker to brute-force a service that uses passwords instead of digital signatures.

One could argue that for client-side digital signatures there is also a password involved, for accessing the private key usually. But this is still a much different situation than the one we have with Basic Auth: first the private key resides as a resource on the client's machine so even if it is recovered it will only affect one person instead of everyone and second, for typical key container formats such as PKCS#12 there is also Password-Based Encryption used for accessing the key. These algorithms were specifically designed to slow attackers down to reduce their rate of brute-force attempts per unit of time, again an advantage for digital signatures.

There's no doubt that TLS Basic Auth is much more convenient to set up and use, but for high security environments I would always prefer "strong cryptography" over user/password solutions, it's worth the trouble.


Curious what your thoughts are on a potential middle ground: api keys over SSL? This uses a longer "password" that won't get brute forced. But still no signing. So I guess it still relies 100% on SSL working, but just as easy as basic auth to integrate (if not easier, 1 field instead of 2).
@BrianArmstrong: I'd agree. Better entropy, but still needs SSL. I really like the decentralized aspect of client-side authentication schemes, though. On the other hand, a client machine is probably much easier to infiltrate than a server.
M
Matt H

The Heartbleed issue with OpenSSL illustrates the potential pitfalls of relying solely on SSL for securing an API. Depending on the API's use and implications if the SSL transport were compromised, additional security measures may need to be taken as mentioned in Emboss's answer.


E
Evert

It's ok to use a subdomain as username, as long as there's some form of a secret.

The benefit of using a shared secret, is that the 'party' doing the request does not need to know the secret, it only needs to know signature to perform the request. This is beneficial if you want your users to allow requests to be made through a browser, for instance.

Using S3 you are able to create a signature, send it to the browser and do direct uploads from a browser to S3.

You could also use HTTP Digest, which has benefits from both. You can still easily test the API in a browser, because browsers support Digest and Basic, and a plain-text password is never sent over the wire.


Thanks, however if using a shared secret of course the party doing the request must know the secret so it can calculate the signature!
The calculation of the signature can be done on a server, and then the sig can be sent to a different client performing the actual request. Take a look at AWS authentication, I love their authentication method and you could apply it to your API as-is. Better than developing your own.
Well, think I've answered my own question here. OAuth 2.0 uses SSL without signatures, I think anything over SSL is secure and fine.
O
Ogglas

I would like to point out some things mentioned at security.stackexchange.com since you say "HTTP Basic Authentication over SSL is perfectly secure from my research.". You could argue that point 3 and 4 below are rarely valid for REST APIs but it really depends on how they are implemented.

"There are a few issues with HTTP Basic Auth:

The password is sent over the wire in base64 encoding (which can be easily converted to plaintext).

The password is sent repeatedly, for each request. (Larger attack window)

The password is cached by the webbrowser, at a minimum for the length of the window / process. (Can be silently reused by any other request to the server, e.g. CSRF).

The password may be stored permanently in the browser, if the user requests. (Same as previous point, in addition might be stolen by another user on a shared machine).

Of those, using SSL only solves the first. And even with that, SSL only protects until the webserver - any internal routing, server logging, etc, will see the plaintext password.

So, as with anything its important to look at the whole picture. Does HTTPS protect the password in transit? - Yes.

Is that enough? Usually, no. (I want to say, always no - but it really depends on what your site is and how secure it needs to be.)"


C
Community

Answering on an old thread as nobody really touched on the main point

SSL/TLS is fundamentally flawed like all PKIs as they rely on a chain of trust that has been proven more and more times susceptible to MiM attacks:

Certification authorities have been and can be hacked. One example among many is the DigiNotar case where a CA was compromised for months before the breach was acknowledged all certificates revoked. In the meantime the Iranian government had forged nice perfectly valid SSL certificates for google.com, facebook.com, twitter.com etc

Company proxy filtering tools like Zscaler that decrypt and re-encrypt the all the traffic on the fly for unspecified "security purposes". See this question/answer on SO

Bugs with the most common SSL implementation (openSSL) are discovered all the time (but things should get better over time? )

Hence big players don't like to rely on SSL only:

In those cases an HMAC token doesn't give you confidentiality but won't allow whoever is spying on you to forge requests with your credentials, which would be otherwise trivial if you just passed them via basic auth.

An alternative to the PKI model is the Web of trust that doesn't rely on a single authority to verify the authenticity of certificates but rather on the opinion provided by the majority of - known and trusted peers OR - known but not necessarily trusted peers

This model isn't still perfect though as it's subject to the notorious 51% attack exactly like for the Bitcoin Blockchain (that is an example of a distributed trusted model)