Matt C
Matt C

Reputation: 903

One-Way Site-to-Site Authentication (PHP/Apache)

I have a site which offers help information for users of a much larger application. Until recently both my help site and the main application were behind a corporate firewall. Now that the main application has been moved outside the firewall, I'll have to move my help site as well.

My only security requirement is that users reaching my help site are only permitted to enter if they clicked the 'Help' link in the main application. (Obviously the company doesn't want them to have to enter their credentials again.) I don't need to exchange information back and forth between the sites.

I have looked at $_SERVER['HTTP_REFERER'] (not secure), Oauth and OpenID (which seem like overkill). I'm wondering if the answer lies in one-way SSL authentication (the main app has a cert), but I'm gettting a little lost here.

So the question is: what is the simplest way to do this, and what would that look like in terms of Apache and PHP?

Thank you very much for any advice!

Upvotes: 3

Views: 453

Answers (2)

Rudu
Rudu

Reputation: 15892

Depends on just how independent the two sites are. If they share access to something private (a database or some file space) then you could consider passing a random value between them. Otherwise if you can use a time + salt approach which allows only those with the same salt/algorithm to generate valid URLs.

M = Main site
H = Help site
K = Key value passed between them (in plain text is fine)

A: Server time + Salt:

XMIT: M hashes time (rounded to -say- nearest ten minute marker) + some random value (salt) to make K. And appends K to the help URL (better yet the help request is a POST so K isn't visible to the user).

RCV: H completes the same hash using the same algorithm and if it's hash matches the supplied K then access is granted. Otherwise H shows a blank page (perhaps for security they'd prefer details of the site are kept secret?) or an error message (more risk, but helpful to legitimate users).

REQ: Both sites on same server OR both sites on servers that are reasonably synchronized in time - no need for perfect sync because of the 10 minute quantization. It's important the salt value be identical on both servers and not publicly accessible (it could also be updated if there was ever a risk a third party had figured it out).

SECURITY: The salt is never passed plain text between the two servers, but because the key passed only works for a period of time even someone sniffing the value (or copying it out of source from M) can only get access temporarily. You need to round to the nearest n minute marker to (a) give reasonable time for a page visitor to request help (b) because the request and check will be a small amount of time apart and (c) because the if the sites are on different servers the time won't be identical. The safety comes from keeping salt and the time calculation algorithm private.

NOTE: On H you may need to test two values of K to allow for cusp cases where rounding leads M and H to different times (because of different times or because of delay in processing)

B: Database/file key:

XMIT: M generates a random value for K and stores it and an expire time in a database table or file that H can access. Again M attaches K (not timeout) to the GET or POST request to H.

RCV: H checks the value against the list of stored values and if found and not timed out then access is granted.

REQ: Both sites have access to shared file storage or database. The database table or file will need to store multiple random values. Either M or H should clean up expired entries (either as part of their operation code, or a scheduled task [cron job] could be setup to complete this at regular intervals)

SECURITY: While K is out there in plain text, there's no advantage to knowing it - again, sniffing the value or copying it out of source from somewhere will only grant access to H temporarily.

Overall

Depending on how tolerant you are of user's hitting timeouts, or unauthorized sources using "found" keys you can use AJAX to generate the value when the help button is clicked, and keep the timeout very low (17 seconds?)

Upvotes: 0

Bob Baddeley
Bob Baddeley

Reputation: 2262

The link to help could contain a token string. When the user clicks the link, the help system sees that token and makes a web service call to your application asking if that token is valid. If the token is valid, then the web service responds in the affirmative and the help site lets the user in. You could have the token be valid only if that user is signed in. Additionally, you could encode the IP address of the client in the URL and verify that the person trying to enter the help system is from the same IP address. So like this:

  1. You have a link to help with a token: http: //help.yoursite.com/?token=< unique id>&client=md5(< client ip>)
  2. The user clicks that link, which takes them to help.yoursite.com.
  3. help.yoursite.com checks that the md5(< client ip>) matches the client parameter of the url. If so, it's probably the same person and not a spoof.
  4. help.yoursite.com then makes a web service call to yoursite.com asking if the unique id for that client ip is valid.
  5. yoursite.com checks if it's valid and returns yes or no, and possibly the username of the person logged in so that help.yoursite.com will have the username of the person logged in.
  6. help.yoursite.com takes the response and either lets the user in or not.

That way you've made sure the client is the same one, and that they were logged in to the other site. Your communication between yoursite and help.yoursite will have to be secure. It's a lot simpler than oauth, and even kinda follows a similar protocal, BUT it's not as secure overall. There are still ways around it, but it's all up to how much risk you're willing to accept.

Upvotes: 1

Related Questions