0

I'm using firebase UI to authenticate users in a given frontend. Facebook authentication is enabled. I need to implement a facebook data deletion callback so I need to make my backend do two things:

  1. delete/disable the facebook sign in method from the user that issued the data deletion request from facebook
  2. delete every trace of facebook data from my firebase user (the provider user info) but without deleting the user

However, I can't find anything in firebase admin's documentation to delete facebook data. So, how can I delete the data?

PD: Keep in mind that I want to delete the user's provider user info, but not the whole user (because I need the user to stay there for data consistency)

xNicoPaz
  • 21
  • 2
  • In Node.js you can probably use [this API](https://firebase.google.com/docs/reference/admin/node/admin.auth.UpdateRequest#optional-providerstounlink) to unlink a given auth provider from a user account. But it's not available in Python yet. – Hiranya Jayathilaka Apr 10 '21 at 00:23
  • There is currently a [PR](https://github.com/firebase/firebase-admin-python/pull/383) to fix this. – Lucas Apr 13 '21 at 14:48

1 Answers1

1

If someone is looking for a NodeJS implementation, this is how you can do it:

module.exports = functions.https.onRequest(async (req, res) => {
  try {
    const signedRequest = req.body.signed_request;
    const userObj = parseSignedRequest(signedRequest, FB_SECRET_KEY);
    const userRecord = await admin
      .auth()
      .getUserByProviderUid("facebook.com", userObj.user_id);
    await admin.auth().deleteUser(userRecord.uid);
    res.json({
      url: "<status_url>",
      confirmation_code: "<code>",
    });
  } catch (e) {
    // console.log(e);
    res.status(400).json({
      message: "Bad Request",
    });
  }
});

function base64decode(data: string) {
  while (data.length % 4 !== 0) {
    data += "=";
  }
  data = data.replace(/-/g, "+").replace(/_/g, "/");
  return Buffer.from(data, "base64").toString("utf-8");
}

function parseSignedRequest(signedRequest: string, secret: string) {
  var encoded_data = signedRequest.split(".", 2);
  // decode the data
  var sig = encoded_data[0];
  var json = base64decode(encoded_data[1]);
  var data = JSON.parse(json);
  if (!data.algorithm || data.algorithm.toUpperCase() != "HMAC-SHA256") {
    throw Error(
      "Unknown algorithm: " + data.algorithm + ". Expected HMAC-SHA256"
    );
  }
  var expected_sig = crypto
    .createHmac("sha256", secret)
    .update(encoded_data[1])
    .digest("base64")
    .replace(/\+/g, "-")
    .replace(/\//g, "_")
    .replace("=", "");
  if (sig !== expected_sig) {
    throw Error("Invalid signature: " + sig + ". Expected " + expected_sig);
  }
  return data;
}

PS. There is no way to just unlink providers via Firebase Admin SDK for now so best we can do is delete the user data.

dsaket
  • 1,827
  • 2
  • 19
  • 30
  • How exactly do I create a url? – Andrew Dec 30 '21 at 12:53
  • @Andrew you can just create a express api endpoint which returns the current status of user data. – dsaket Jan 04 '22 at 06:01
  • @dskaet How exactly does this status have to look like? Is a web page with a text like "your account is deleted", enough? I mean my deletion takes like 5 seconds – Andrew Jan 04 '22 at 07:41
  • yes its only for the user to confirm whether the data was deleted or not...so yes only a text would suffice. – dsaket Jan 04 '22 at 08:24