0

I'm developing a REST API that may take in private information. To make it secure, I want to have the API only accessible using HTTPS. Basically, what is the best way to enforce HTTPS only?

Here are some things I was thinking for when an insecure HTTP request is made:

  • Set the HTTP status code to 403 Forbidden
  • Send the Strict-Transport-Security header
  • Redirect to the HTTPS URL using the Location header
  • That's pretty much the standard these days. – Jesse K Aug 1 '17 at 16:46
  • 3
    D. Turn off the HTTP port. (I mean that literally. With API consumers there will always be someone stupid enough to ignore what you're telling them over HTTP, so just turn it off and let them bang their head against the wall.) – gowenfawr Aug 1 '17 at 17:02
  • In addition to @gowenfawr without TCP80 an accidental clear text transmission won't occur. – user2320464 Aug 1 '17 at 18:27
  • @user2320464 never underestimate the genius of a foolish programmer... you can easily follow a TCP handshake with a data packet instead of a TLS CLIENT_HELLO. It doesn't work but the data crosses the wire before you get a chance to figure that out... been there, seen that. – gowenfawr Aug 1 '17 at 19:18
3

I'm developing a REST API that may take in private information. To make it secure, I want to have the API only accessible using HTTPS. Basically, what is the best way to enforce HTTPS only?

If you're doing an API, the best way is to turn off HTTP and only publish an HTTPS interface.

  • Down-level HTTP is a crutch for puny humans. If you're running a UI site, then you have to expect humans will try to go to the unencrypted HTTP version, because they're like that - that's why we have so many fancy ways of redirecting them. With an API, you can demand people code to HTTPS, and simply not provide HTTP, because it isn't users with browsers specifying your address.
  • Puny humans at least have browsers working for them, which try to take into account all the neat things you've mentioned (status codes, headers). When an API programmer slaps together an API client, they'll often ignore or be creative with things like that. The 8 lines of RESTful Python they pulled off of StackExchange doesn't emphasize error handling or RFC-compliant header hewing. You simply can't trust that they'll respond to HTTP protocol and header hints and redirections.
  • APIs are less likely to shove unencrypted input over your TCP if you're running HTTPS... but it's not impossible. (Their first packet after the 3WHS could be a data-laden JSON request instead of a TLS CLIENT_HELLO... but if they never get a response back (and they won't if they do that) they'll learn to stop sticking their finger that socket soon enough.) The lesson here is, again, please don't trust API client programmers to do the right thing. And never reward them ignoring encryption with a legitimate response, even a 403 Forbidden (as they might get if you support HTTP).
  • Set the HTTP status code to 403 Forbidden
  • Send the Strict-Transport-Security header
  • Redirect to the HTTPS URL using the Location header

These are all excellent things if you have a HTTP site and want to push humans bearing browsers over. But when dealing with an API, instead of a browser, it's a set of assumptions that are less likely to be true and less necessary in the first place.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.