Scenario: you run an app OurApp
which deals with users' sensitive data, some of which you are allowed to share with third parties (with the user's consent, of course) and some of which you are not allowed to share even if the user consents. You wish to integrate with a site MiddlemanSite
which the user already has an account with. MiddlemanSite
will display a dashboard page which directly incorporates the data you are allowed to share, with click-through links to ourapp.com to view the data that isn't allowed to be shared.
Example: MiddlemanSite
is the classic petstore app, and OurApp
is a veterinary practice, which is allowed to share data like notifications that a user's pet is due a vaccination or checkup, but not the pet's full medical history.
Challenge: what workflow do I use for authenticating the user to OurApp
which ensures that the private data is only accessible to the user directly, and not to a compromised or malicious MiddlemanSite
, notwithstanding the fact that most of the user's interaction takes place on MiddlemanSite?
Thus far the best authentication workflow I can come up with is this:
It's clear that we need to have a direct dialogue with the user when first linking the two accounts: we need to do this anyway because we need to collect a secret (in our case an API key for yet another service, which we need in order to make our service work) directly from the user. So when MS
posts details to the "this user of ours has just asked to affiliate their account with OurApp
, here are their details" endpoint, we return a redirect url for the user to be directed to, where we ask for the SuperSecret. We can consider the user to be 'verified' if they know the SuperSecret.
Then we can set a cookie in the response to that submission which will allow us to identify that user in future visits; so when they click links on the MS
dashboard they authenticate with both a token in the link query string (which MS will have access to) and the cookie (which MS won't).
However, re-validating the user on a different device or after a long time is more challenging. I don't want to require the user to re-submit the SuperSecret because generating it is a pain, and we don't want the user to have to set a separate password for OurApp
. The best I can come up with is a quasi-two-factor-auth link sent directly from OurApp
to the user's email or phone, which the user has to access in order to re-validate. But given that the email/phone data was submitted to OurApp
by MiddlemanSite in the first place, I'm uneasy about this being easily spoofable. The best I can think of in terms of mitigation is to display the submitted information back to the user on the signup screen, so the user has a chance to see if it's being mitm'd. And I can't think of a way of supporting the user changing their email/phone settings on MiddlemanSite
and safely propagating that change to OurApp
.
Questions:
0) Is there a standard protocol for this sort of authentication workflow that I should be using instead of reinventing a wheel?
1) Are there obvious security weaknesses in this workflow, beyond its extreme verbosity? Assume that MiddlemanSite
is either fully compromised or itself malicious, and seeks to gain access to users' non-shareable data.
2) Is there a better protocol I could use for re-validating users to replace using their email/phone records? Needs to support the user logging in to MiddlemanSite
on a new device and immediately clicking through from their dashboard to a page on OurApp
.