6

We are going to serve content to a Content Management System that embeds it through an iframe (yuck). Some pages that we serve need to be authenticated before – only a valid user should be able to see them.

The company who previously implemented what we're about to do did this through the requests. Of course, since there was no session management. The use of iframes kinda made it impossible to use cookies, etc. This is no real authentication, but that's what they did…

http://example.com/get.php?ID=1234&[email protected]

Believe it or not: One could easily get the content of another user by exchanging ID or e-mail. Now we want (or, have) to change that. The problem is that we do not have access to the customer data. We don't know e-mail address and user IDs of the CMS.

The initial plan that had been developed was to send us a salted hash with e-mail and ID, and somebody thought it was possible to extract e-mail and ID from the hash again if we knew the salt. Well, turns out they didn't know how hashes work… so it's on me to come up with something new.

Here is the first scenario I thought of:

In this case we only receive a list of valid hashes from the CMS and check if the hash the user sent us is valid. The problem here is that we need a list of hashes and the CMS needs to send them to our backend some way. Is there any other issue I'm missing? What about users trying all possible hashes?

Second scenario:

We receive the user's hash and send it back to the CMS. The CMS verifies that this hash really exists and tells us whether we can serve the content. Here, the problem is that extra requests have to be made (performance?).

Third scenario – which I think should fit in our case:

The user sends us their e-mail, ID and the hash the CMS generated for them. We share a secret key (the salt) with the CMS, and try to reconstruct the hash from e-mail and ID. If it matches, the user must've been authenticated in the CMS before, so we can serve the content.

The problem here is that we send the e-mail via URL. Now, the previous (insecure) implementation also did this, but I don't know how much of a privacy issue this is.

Bottom line: Is there anything I've missed in the above examples? Would the last scenario fit our case, or is there another easy method to authenticate a user when you don't have access to private data on your side of the scheme?

4
  • Beautiful problem. In the third case scenario where the e-mail is sent via the URL: Are you using HTTPS? The problem with parameters (such as the e-mail address) being sent on the URL string via GET is that URLs usually get logged in several different places like logs, bookmarks and proxies. Is it not possible to send them over the body of a POST method?
    – Lex
    Commented Apr 17, 2013 at 14:57
  • We might be able to use HTTPS for all communication. POST is out of the question because we're literally just embedding the content into an iframe, like in the URL example above. Maybe we could authenticate once via POST and then through our backend store… a cookie? Would that cookie work even though we're accessing within an iframe?
    – slhck
    Commented Apr 17, 2013 at 15:03
  • Do you only have access to an IFRAME? If you have IFRAME + JavaScript, you can whip up a form inside the iframe, which gives you access to POST. Not just this, but if you can serve JS in your IFRAME, you can in theory create a secure channel using requests made in there. Commented Apr 17, 2013 at 15:16
  • @SébastienRenauld We only supply pages that are loaded in an iframe, that's it. Could you elaborate on how that would work? The customer has to log in at the CMS – then the CMS can request almost anything from us, but it has to be via GET.
    – slhck
    Commented Apr 17, 2013 at 20:08

1 Answer 1

3

This proposed design does not take replay attacks into consideration. In the first scenario the "hash" is now the password, and therefore this hash (and the information used to create this hash), must be protected in the database and during transmission.

What you are trying to do is not new or unique. When you build something from scratch there are problems with design, implementation and compatibility with other systems. To avoid all of these pitfalls you should implement an RFC'ed standard such as 3-legged oauth:

image of oauth flow

4
  • Sounds closer to openID than to OAuth1, to be honest. Needless to say, your advice is sound - he shouldn't try homebrewed solutions for something where solutions have been built and extensively tested. Commented Apr 17, 2013 at 16:29
  • @Sébastien Renauld I agree, openid could be used for sharing information and is not off the table.
    – rook
    Commented Apr 17, 2013 at 16:31
  • In the 3-legged OAuth scheme, I take it we are the service provider and the consumer is the CMS. However, this requires the user to actively log in at the service provider, which authenticates the user. This is not possible in our case—the user will authenticate against the CMS first. Or am I missing something?
    – slhck
    Commented Apr 17, 2013 at 20:11
  • @slhck In that case the CMS would be the service provider and you can expose an API to the user using OAuth or exchange information using OpenID.
    – rook
    Commented Apr 17, 2013 at 20:56

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .