6

I am following the firebase documentation here to set custom auth claims for users logging into my app for the first time using firebase auth + identify platform but it does not seem to be working.

When a user logs in for the first time, I want them to get the admin custom claim. I have created the following blocking function and have verified from the logs that it runs when I log in for the first time to my app using sign-in with google:

exports.beforeCreate = functions.auth.user().beforeCreate((user, context) => {
  return {
    customClaims: {
      admin: true,
    },
  };
});

I would expect this to create the admin custom claim in the user's token. However, when I get a list of claims using another cloud function the admin claim does not appear.

exports.getclaims = functions.https.onRequest(async (req, res) => {
  const uid = req.query.uid as string;
  if (uid) {
    const user = await admin.auth().getUser(uid);
    res.send(user.customClaims);
  } else {
    res.sendStatus(500);
  }
});

If I set the claim using the admin SDK directly using the below cloud function, the admin claim does appear.

exports.setclaim = functions.https.onRequest(async (req, res) => {
  const uid = req.query.uid as string;
  if (uid) {
    await admin.auth().setCustomUserClaims(uid, {admin: true});
    res.sendStatus(200);
  } else {
    res.sendStatus(500);
  }
});

What am I doing wrong in the beforeCreate function?

  • FYI I've tested your code in my own test environment and I have the same behaviour: The claim is not set. All packages were updated before tests. I would suggest you contact the Firebase support. – Renaud Tarnec Aug 03 '22 at 16:42
  • Same behaviour. Have you found an answer @treesandgreens? – Gorka Molero Aug 24 '22 at 00:04
  • It seems to be a bug. There is some discussion on this [question](https://stackoverflow.com/questions/73535561/firebase-beforecreate-not-adding-custom-claims) – treesandgreens Aug 30 '22 at 20:20

3 Answers3

1

From the snippet you provided, there does not appear to be anything wrong with beforeCreate as coded.

You may want to check you do not have a beforeSignIn that is overwriting the customClaims directly or via sessionClaims.

https://firebase.google.com/docs/auth/extend-with-blocking-functions#modifying_a_user

M. Gallant
  • 236
  • 2
  • 5
1

Try to use onCreate method instead of beforeCreate how it is shown on the official docs

functions.auth.user().onCreate(async (user) => {
    try {
      // Set custom user claims on this newly created user.
      await getAuth().setCustomUserClaims(user.uid, {admin: true});

      // Update real-time database to notify client to force refresh.
      const metadataRef = getDatabase().ref('metadata/' + user.uid);

      // Set the refresh time to the current UTC timestamp.
      // This will be captured on the client to force a token refresh.
      await  metadataRef.set({refreshTime: new Date().getTime()});
    } catch (error) {
      console.log(error);
    }
  }
});

The main point here is that you need to create the user at first and then update claims and make the force update of the token at the client side:

firebase.auth().currentUser.getIdToken(true);
Shmyhelskyi
  • 157
  • 4
1

There's an open GitHub issue regarding that. See sessionClaims content not getting added to the decoded token. Also, there's a fix that has been recently merged regarding this issue.

Gremash
  • 8,158
  • 6
  • 30
  • 44