0
votes

I want to use firebase to authenticate users and then firebase functions to insert users into Hasura but having problems with the firebase functions.

When I try to create a user from the app the "registerUser" function, which can be found below, it ends with an error:

Error detected in registerUser:
{"@type":"type.googleapis.com/google.devtools.clouderrorreporting.v1beta1.Insight",
"errorGroup":"CLic1cmw6emOsAE",
"errorEvent":{"message":"Error: The uid must be a non-empty string with at most 128 characters.
at FirebaseAuthError.FirebaseError [as constructor] (/srv/node_modules/firebase-admin/lib/utils/error.js:42:28)
at FirebaseAuthError.PrefixedFirebaseError [as constructor] (/srv/node_modules/firebase-admin/lib/utils/error.js:88:28)\
at new FirebaseAuthError (/srv/node_modules/firebase-admin/lib/utils/error.js:147:16)
at AuthRequestHandler.AbstractAuthRequestHandler.setCustomUserClaims (/srv/node_modules/firebase-admin/lib/auth/auth-api-request.js:996:35)
at Auth.BaseAuth.setCustomUserClaims (/srv/node_modules/firebase-admin/lib/auth/auth.js:342:40)
at exports.registerUser.functions.https.onCall (/srv/index.js:32:18)
at func (/srv/node_modules/firebase-functions/lib/providers/https.js:272:32)
at corsHandler (/srv/node_modules/firebase-functions/lib/providers/https.js:292:44)\n    at cors (/srv/node_modules/cors/lib/index.js:188:7)
at /srv/node_modules/cors/lib/index.js:224:17","eventTime":"2020-06-10T08:25:03.017Z","serviceContext":{"service":"registerUser","resourceType":"cloud_function"}}}

If I instead create a user directly via the firebase console my "processSignUp" runs but ends with another error:

ReferenceError: fetch is not defined
    at GraphQLClient.<anonymous> (/srv/node_modules/graphql-request/dist/src/index.js:108:25)
    at step (/srv/node_modules/graphql-request/dist/src/index.js:44:23)
    at Object.next (/srv/node_modules/graphql-request/dist/src/index.js:25:53)
    at /srv/node_modules/graphql-request/dist/src/index.js:19:71
    at new Promise (<anonymous>)
    at __awaiter (/srv/node_modules/graphql-request/dist/src/index.js:15:12)
    at GraphQLClient.request (/srv/node_modules/graphql-request/dist/src/index.js:98:16)
    at exports.processSignUp.functions.auth.user.onCreate (/srv/index.js:60:25)
    at cloudFunction (/srv/node_modules/firebase-functions/lib/cloud-functions.js:132:23)
    at /worker/worker.js:825:24 

I've tried pretty much everything I could think of. I've used https://hasura.io/jwt-config/ to setup the JWT on Heroku. I've triple checked passwords and graphQL endpoint. I have no problems with the mutations or query variables when I play around in hasura console but I'm unable to connect the firebase functions to hasura. Thanks in advance.

functions/index.js

...

const client = new request.GraphQLClient(
  "https://app-name.herokuapp.com/v1/graphql",
  {
    headers: {
      "content-type": "application/json",
      "x-hasura-admin-secret": "Password",
    },
  }
);
...
// On register.
exports.registerUser = functions.https.onCall((data) => {
  const { email, password } = data;

  try {
    const userRecord = admin.auth().createUser({ email, password });

    const customClaims = {
      "https://hasura.io/jwt/claims": {
        "x-hasura-default-role": "user",
        "x-hasura-allowed-roles": ["user"],
        "x-hasura-user-id": userRecord.uid,
      },
    };

    admin.auth().setCustomUserClaims(userRecord.uid, customClaims);
    return userRecord.toJSON();
  } catch (e) {
    let errorCode = "unknown";
    let msg = "Something went wrong, please try again later";
    if (e.code === "auth/email-already-exists") {
      errorCode = "already-exists";
      msg = e.message;
    }
    throw new functions.https.HttpsError(errorCode, msg, JSON.stringify(e));
  }
});

...

// On sign up.
exports.processSignUp = functions.auth.user().onCreate(async (user) => {
  const { uid: id, email } = user;
  const mutation = `
    mutation($id: String!, $email: String) {
      insert_users(objects: [{
        id: $id,
        email: $email,
      }]) {
        affected_rows
      }
    }
  `;

  try {
    const data = await client.request(mutation, { id, email });

    return data;
  } catch (e) {
    throw new functions.https.HttpsError("invalid-argument", e.message);
  }
});
1

1 Answers

2
votes

In the package.json for your functions, try changing the node engine to 10 and your grapql-request package to 1.8.2.