Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Unable to exchange code for access_token on server side #7

Open
teq opened this issue Oct 10, 2014 · 3 comments
Open

Unable to exchange code for access_token on server side #7

teq opened this issue Oct 10, 2014 · 3 comments

Comments

@teq
Copy link

teq commented Oct 10, 2014

I am trying to authenticate user on server side (node.js based REST API) as it described here: https://github.com/oauth-io/sdk-node#auth-method, section 'Authenticating the user from the frontend JS SDK'.

Client side (Phonegap oauth.io SDK) works OK and returns code after successful authentication.

Server side code:

  // Called before auth from client
  oauthioStateToken: function(req, res, next) {
    res.json({
      // Our API does not use session, I pass empty object here for now.
      token: oauthio.generateStateToken({})
    });
  },

  // Called after auth from client
  google: function(req, res, next) {
    if (!req.body || !req.body.code) {
      return next(new BadRequestError('No Google access code found'));
    }
    // Again, empty object instead of session for now.
    // This call fails with Error: State is missing from response
    oauthio.auth('google_plus', {} , { code: req.body.code })
    .then(function(reqObject) {
      return reqObject.get("/me");
    })
    .then(function(info) {
      res.json(info);
    })
    .fail(next);
  },

Trying to track down a problem I found this code (oauth.is node.js SDK, file lib/authentication.js):

    authenticate: function(code, session) {
      var defer;
      defer = Q.defer();
      request.post({
        url: cache.oauthd_url + cache.oauthd_base + '/access_token', // https://oauth.io/auth/access_token
        form: {
          code: code, // code, received from client
          key: cache.public_key, // public key from oauth.io. I checked, it matches with client one
          secret: cache.secret_key
        }
      }, function(e, r, body) {
        // Body is {"status":"fail","data":{"code":"invalid or expired"}}
        // Seems like `response.status=="fail"` is unhandled and it falls to
        // "Error State is missing from response" (see below).
        var response, _ref;
        if (e) {
          defer.reject(e);
          return;
        }
        try {
          response = JSON.parse(body);
        } catch (_error) {
          e = _error;
          defer.reject(new Error('OAuth.io response could not be parsed'));
          return;
        }
        if ((response.status != null) && response.status === 'error' && (response.message != null)) {
          defer.reject(new Error('OAuth.io / oauthd responded with : ' + response.message));
        }
        if (response.state == null) {
          defer.reject(new Error('State is missing from response'));
          return;
        }
        if (((session != null ? session.csrf_tokens : void 0) == null) || (_ref = response.state, __indexOf.call(session.csrf_tokens, _ref) < 0)) {
          defer.reject(new Error('State is not matching'));
        }
        if (response.expires_in) {
          response.expires = new Date().getTime() + response.expires_in * 1000;
        }
        response = a.construct_request_object(response);
        if ((session != null)) {
          session.oauth = session.oauth || {};
          session.oauth[response.provider] = response;
        }
        return defer.resolve(response);
      });
      return defer.promise;
    }

I double checked all settings. Public/Secret keys matching. Added localhost and * to domains whitelist (I am testing from localhost). Maybe I messed something important?
Thank you!

@sparkyfen
Copy link

For Google I have more success with the me() method.

See if you can do:

oauthio.auth('google', {} , { code: req.body.code })
    .then(function(reqObject) {
      return reqObject.me();
    })
    .then(function(info) {
      res.json(info);
    })
    .fail(next);

@sparkyfen
Copy link

@teq You can also take a look at the tutorial SDK project OAuth.io made here:

https://github.com/oauth-io/sdk-node-tutorial

Some of that repo is broken and I've been able to get a version working, you can check out my fork here:

https://github.com/brutalhonesty/sdk-node-tutorial

@teq
Copy link
Author

teq commented Oct 31, 2014

@brutalhonesty Thank you for links, I'll give it a try.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants