Any chance for OAuth from 1 server, for 2 domains?

Given a single server running a single Meteor app
When there are multiple inbound domain names (branding reasons)
Then I can not use OAuth from any but the ROOT_URL configured “main” domain name

Ideally, I’d like my client to be able to determine it’s domain based on what’s in the URL and the server to “know” what that domain is.

I was able to monkey patch the Package['oauth'].OAuth._redirectUri function on the client and send the correct redirect_uri to the OAuth provider, but because the server was on the wrong domain, the OAuth handshake failed.

I was able to monkey patch the Package['oauth'].OAuth._redirectUri function on the server, but there’s nothing that I can tell, from the server, to indicate what domain the client requested from.

I am assuming this is basically impossible with Meteor auth as it exists now… but is there a chance the client could tell the server what domain it started from?

1 Like

I think what you’re trying to do here (redirect the oauth flow to an arbitrary endpoint) is basically trying to hijack the flow: “don’t redirect to the specified endpoint, instead redirect somewhere completely different.”

There are two ways to safely achieve what you want to do:

  1. Add the (all) other endpoints as new oauth redirects - i.e. make them legal.
  2. Redirect to a single endpoint and then, in that endpoint, redirect again to the chosen endpoint.

Both these approaches guarantee the integrity of the flow.

Well - the server is answering on both domains, but ROOT_URL is only setup to one of them.

When accessing on the secondary domain, OAuth would redirect to the primary, authenticate, and then I’d be logged in on the primary domain — if I redirected to the secondary domain, I’d no longer be logged in… right?

Yes, but after the oauth flow completes you have the “keys to the kingdom” - the access and refresh tokens and the token expiry time. All these can be handed off to the secondary domain. In the case of two or more Meteor apps, all that stuff is also available in the users collection.

Have you managed to get it working after all?
I’ve got similar set up and while running Google Auth I see cross-origin error if redirect to ROOT_URL of the main domain. I can register both end-points with Google but it doesn’t help much.
Also tried adding the handler below, which made no difference either:

  WebApp.rawConnectHandlers.use("/_oauth", function(req, res, next) {
    res.setHeader("Access-Control-Allow-Origin", "*");
    return next();
  });

nope - I’ve been solidly ignoring this, since I asked the question.

I’ve thought about it a bit, here are my options:

Option 1: all OAuth happens via the main domain, subsequent redirect could force auth afterwards. This sucks though, because the main domain shows up all over the place, and the force auth afterwards is janky.

Option 2: make the client tell the server where to auth against (core patch needed).

Option 3: custom auth, not meteor accounts… (meh. this is a terrible idea, if using meteor)

Rob,
Could you clarify the option 1 above?
I have registered another set of authorised origin and redirect URI with Google API manager, i.e. it’s legal now. On the client side rootUrl can be changed using Meteor.absoluteUrl.defaultOptions.rootUrl. This makes the obtaining the authorization code part working ok. Unfortunately, when Meteor Google module executes getTokens function it ignores the original redirect_uri and makes another one using the server side Meteor.absoluteUrl.defaultOptions.rootUrl. That’s where things get messy because it cannot be changed that easily 'cos it’s shared across all connections.
Would you see any security concerns if getToken function reused the original redirect_uri, known from the query?
– Nick

I got it working as expected but with slight change in the core packages. Two functions in particular - (1) getTokens(query) [google_server.js] (this one requires the package override unless patched in master), (2) OAuth._stateParam(loginStyle, credentialToken, redirectUrl) [oauth_client.js] (just did the function override to avoid another local package). Can’t tell the impact on other use-cases, such as Cordova.

1 Like

Just to clarify @nbusy - “you got it working” meaning: “you are able to OAuth on the main $ROOT_URL domain and then redirect to an alternate domain, passing through the token & expiry information.”

Is that true?

Either way, I’d love to see a gist or PR for it - not sure if @mdg would accept a PR which “hijacks” auth, at this point, but we could try :slight_smile:

thanks!

Not quite, there’s no “hijacking” involved in the suggested solution.
The OAuth flow is completed on the same domain as in the client’s browser window. I.e. main domain won’t show up during the login.
It doesn’t break the option when one uses the main domain OAuth and the second redirect or shares the login results with the main window by other means (message or cookies).
Basically, the only thing we do here is matching the redirect_uri parameters in the first (authorisation code) and the second (access token) OAuth2 requests.

The changed function in Google package is not exposed for override, so I keep a local copy of the package, which I’m not 100% happy about but I can live with it for now.

Here is the gist link.

Hi @robfallows
I am facing the same problem @zeroasterisk, and I can not make other oauth redirects legal, so I’m stuck with second option.

  1. Redirect to a single endpoint and then, in that endpoint, redirect again to the chosen endpoint.

I wanted to know what do you mean by that? Do you imply creating a separate login service, which all apps on all domains could use?

I initially thought of modifying ROOT_URL and then use the response to continue with the login flow, but couldn’t figure that part out. Figured out it’s a security concern with Meteor Accounts package.

I also don’t really want to modify meteor packages source code as some people with similar problems do.