Auth0 Home Blog Docs

Changing Callback URL within Rule

Hi Everyone.

I’ve been struggling with a problem. We have Okta setup as SAMLP Identity Provider which links in with a custom WordPress plugin. All works great. There is two flows through that a user can take.

  1. Visit the site, click login with Okta, passed to Auth0, Okta details entered and back round to that site.
  2. Click on button in Okta dashboard, passed to Auth0 and back to the site.

In option 2 Okta doesn’t set callback url and we have to set a default state. As there is no callback url set Auth0 uses the first of callback urls set on the app which is fine and easy to manage. However today I was asked if I could make the Okta button take users to different sites based on there email. So I wrote a rule (at end of this message). Basically does the logic to work out who should go where then triggers a redirect using:

context.redirect = {
    url: redirect_uri
}; 

However this causes the state to change therefore the site can’t log them in. Is there any way to do this without the state changing?

Thanks
Jason

function (user, context, callback) {
    
  var config = {
  'CLIENT_ID_HERE': {
    'CALLBACK_URL_ONE': {
      'domains': [
        'site1.com'
      ],
      'emails': []
    },
    'CALLBACK_URL_TWO': {
      'domains': [
        'site2.com'
      ],
      'emails': []
    },
    'CALLBACK_URL_THREE': {
      'domains': [
        'site3.com'
      ],
      'emails': []
    },
  }
 };

  const clientIDS = ['CLIENT_ID_HERE'];
  
  if (clientIDS.indexOf(context.clientID) === -1) {
    return callback(null, user, context);
  }
   
  var state = false;
  
  if ( context.request.query && context.request.query.state !== 'undefined' ) {
    state = context.request.query.state;
  } else if ( context.request.body && context.request.body.state !== 'undefined' ) {
    state = context.request.body.state;
  }
  
  if ( state !== configuration.OKTA_STATE ) {
    return callback(null, user, context);  
  }
  
  if (config[context.clientID] === 'undefined') {
    return callback(null, user, context);
  }
  
  var redirect_uri = getUserRedirect(user, context.clientID, config);
  
  if ( redirect_uri ) {
    context.redirect = {
        url: redirect_uri
    };
  }
  
  callback(null, user, context);

  function getUserRedirect(user, clientID, config) {
    var newConfig = config[clientID];
    
    if (!newConfig) {
      return false;
    }
    
    var urls = Object.keys(newConfig);
    
    var email = user.email.toLowerCase();
    var domain = email.split('@').pop();
    
    var redirect = false;
    var fromEmail = false;
    
    urls.forEach(function(url) {
      var conf = newConfig[url];
      
      if (redirect && fromEmail) {
        return;
      }
      
      if (conf.domains && !redirect) {
        conf.domains = conf.domains.map(function (d) { return d.toLowerCase(); });
        
        if (conf.domains.indexOf(domain) !== -1) {
          redirect = url;
        }
      }
      
      if (conf.emails) {
        conf.emails = conf.emails.map(function (e) { return e.toLowerCase(); });
        
        if (conf.emails.indexOf(email) !== -1) {
          redirect = url;
          fromEmail = true;
        }
      }
    });
   
    return redirect;
  }
}

Hey there!

Sorry for such huge delay in response! We’re doing our best in providing you with best developer support experience out there, but sometimes our bandwidth is not enough comparing to the number of incoming questions.

Wanted to reach out to know if you still require further assistance?