From 5062c76ac28473ed47e87abf9369590c979ef088 Mon Sep 17 00:00:00 2001 From: Ian Tay Date: Fri, 15 Oct 2021 12:01:07 -0700 Subject: [PATCH 01/38] Add SAML provider snippets. (#246) * Add SAML provider snippets. This is a Google Cloud Identity Platform provider. * Add OIDC provider snippets. This is a Google Cloud Identity Platform provider. * add generated snippets --- auth-next/oidc.js | 96 +++++++++++++++++++ auth-next/saml.js | 68 +++++++++++++ auth/oidc.js | 71 ++++++++++++++ auth/saml.js | 56 +++++++++++ .../oidc/auth_oidc_direct_sign_in.js | 31 ++++++ .../oidc/auth_oidc_provider_create.js | 11 +++ .../auth-next/oidc/auth_oidc_signin_popup.js | 27 ++++++ .../oidc/auth_oidc_signin_redirect.js | 12 +++ .../oidc/auth_oidc_signin_redirect_result.js | 28 ++++++ .../saml/auth_saml_provider_create.js | 11 +++ .../auth-next/saml/auth_saml_signin_popup.js | 27 ++++++ .../saml/auth_saml_signin_redirect.js | 12 +++ .../saml/auth_saml_signin_redirect_result.js | 28 ++++++ .../auth/oidc/auth_oidc_direct_sign_in.js | 19 ++++ .../auth/oidc/auth_oidc_provider_create.js | 9 ++ snippets/auth/oidc/auth_oidc_signin_popup.js | 18 ++++ .../auth/oidc/auth_oidc_signin_redirect.js | 11 +++ .../oidc/auth_oidc_signin_redirect_result.js | 20 ++++ .../auth/saml/auth_saml_provider_create.js | 9 ++ snippets/auth/saml/auth_saml_signin_popup.js | 21 ++++ .../auth/saml/auth_saml_signin_redirect.js | 9 ++ .../saml/auth_saml_signin_redirect_result.js | 20 ++++ 22 files changed, 614 insertions(+) create mode 100644 auth-next/oidc.js create mode 100644 auth-next/saml.js create mode 100644 auth/oidc.js create mode 100644 auth/saml.js create mode 100644 snippets/auth-next/oidc/auth_oidc_direct_sign_in.js create mode 100644 snippets/auth-next/oidc/auth_oidc_provider_create.js create mode 100644 snippets/auth-next/oidc/auth_oidc_signin_popup.js create mode 100644 snippets/auth-next/oidc/auth_oidc_signin_redirect.js create mode 100644 snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js create mode 100644 snippets/auth-next/saml/auth_saml_provider_create.js create mode 100644 snippets/auth-next/saml/auth_saml_signin_popup.js create mode 100644 snippets/auth-next/saml/auth_saml_signin_redirect.js create mode 100644 snippets/auth-next/saml/auth_saml_signin_redirect_result.js create mode 100644 snippets/auth/oidc/auth_oidc_direct_sign_in.js create mode 100644 snippets/auth/oidc/auth_oidc_provider_create.js create mode 100644 snippets/auth/oidc/auth_oidc_signin_popup.js create mode 100644 snippets/auth/oidc/auth_oidc_signin_redirect.js create mode 100644 snippets/auth/oidc/auth_oidc_signin_redirect_result.js create mode 100644 snippets/auth/saml/auth_saml_provider_create.js create mode 100644 snippets/auth/saml/auth_saml_signin_popup.js create mode 100644 snippets/auth/saml/auth_saml_signin_redirect.js create mode 100644 snippets/auth/saml/auth_saml_signin_redirect_result.js diff --git a/auth-next/oidc.js b/auth-next/oidc.js new file mode 100644 index 00000000..5dc20e81 --- /dev/null +++ b/auth-next/oidc.js @@ -0,0 +1,96 @@ +// [SNIPPET_REGISTRY disabled] +// [SNIPPETS_SEPARATION enabled] + +function oidcProvider() { + // [START auth_oidc_provider_create] + const { OAuthProvider } = require("firebase/auth"); + + const provider = new OAuthProvider("oidc.myProvider"); + // [END auth_oidc_provider_create] +} + +function oidcSignInPopup(provider) { + // [START auth_oidc_signin_popup] + const { getAuth, signInWithPopup, OAuthProvider } = require("firebase/auth"); + + const auth = getAuth(); + signInWithPopup(auth, provider) + .then((result) => { + // User is signed in. + const credential = OAuthProvider.credentialFromResult(result); + // This gives you an access token for the OIDC provider. You can use it to directly interact with that provider + }).catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = OAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); + // [END auth_oidc_signin_popup] +} + +function oidcSignInRedirect(provider) { + // [START auth_oidc_signin_redirect] + const { getAuth, signInWithRedirect } = require("firebase/auth"); + + const auth = getAuth(); + signInWithRedirect(auth, provider); + // [END auth_oidc_signin_redirect] +} + +function oidcSignInRedirectResult(provider) { + // [START auth_oidc_signin_redirect_result] + const { getAuth, getRedirectResult, OAuthProvider } = require("firebase/auth"); + + const auth = getAuth(); + getRedirectResult(auth) + .then((result) => { + // User is signed in. + const credential = OAuthProvider.credentialFromResult(result); + // This gives you an access token for the OIDC provider. You can use it to directly interact with that provider + }) + .catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = OAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); + // [END auth_oidc_signin_redirect_result] +} + +function oidcDirectSignIn(provider, oidcIdToken) { + // [START auth_oidc_direct_sign_in] + const { getAuth, OAuthProvider, signInWithCredential } = require("firebase/auth"); + + const auth = getAuth(); + const credential = provider.credential({ + idToken: oidcIdToken, + }); + signInWithCredential(auth, credential) + .then((result) => { + // User is signed in. + const newCredential = OAuthProvider.credentialFromResult(result); + // This gives you a new access token for the OIDC provider. You can use it to directly interact with that provider. + }) + .catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = OAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); + // [END auth_oidc_direct_sign_in] +} \ No newline at end of file diff --git a/auth-next/saml.js b/auth-next/saml.js new file mode 100644 index 00000000..9a5683d9 --- /dev/null +++ b/auth-next/saml.js @@ -0,0 +1,68 @@ +// [SNIPPET_REGISTRY disabled] +// [SNIPPETS_SEPARATION enabled] + +function samlProvider() { + // [START auth_saml_provider_create] + const { SAMLAuthProvider } = require("firebase/auth"); + + const provider = new SAMLAuthProvider("saml.myProvider"); + // [END auth_saml_provider_create] +} + +function samlSignInPopup(provider) { + // [START auth_saml_signin_popup] + const { getAuth, signInWithPopup, SAMLAuthProvider } = require("firebase/auth"); + + const auth = getAuth(); + signInWithPopup(auth, provider) + .then((result) => { + // User is signed in. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }).catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = SAMLAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); + // [END auth_saml_signin_popup] +} + +function samlSignInRedirect(provider) { + // [START auth_saml_signin_redirect] + const { getAuth, signInWithRedirect } = require("firebase/auth"); + + const auth = getAuth(); + signInWithRedirect(auth, provider); + // [END auth_saml_signin_redirect] +} + +function samlSignInRedirectResult(provider) { + // [START auth_saml_signin_redirect_result] + const { getAuth, getRedirectResult, SAMLAuthProvider } = require("firebase/auth"); + + const auth = getAuth(); + getRedirectResult(auth) + .then((result) => { + // User is signed in. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }) + .catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = SAMLAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); + // [END auth_saml_signin_redirect_result] +} \ No newline at end of file diff --git a/auth/oidc.js b/auth/oidc.js new file mode 100644 index 00000000..4c056e52 --- /dev/null +++ b/auth/oidc.js @@ -0,0 +1,71 @@ +// These samples are intended for Web so this import would normally be +// done in HTML however using modules here is more convenient for +// ensuring sample correctness offline. +import firebase from "firebase/app"; +import "firebase/auth"; + +// [SNIPPET_REGISTRY disabled] +// [SNIPPETS_SEPARATION enabled] + +function oidcProvider() { + // [START auth_oidc_provider_create] + const provider = new firebase.auth.OAuthProvider('oidc.myProvider'); + // [END auth_oidc_provider_create] +} + +function oidcSignInPopup(provider) { + // [START auth_oidc_signin_popup] + firebase.auth().signInWithPopup(provider) + .then((result) => { + // User is signed in. + // result.credential is a firebase.auth().OAuthCredential object. + // result.credential.providerId is equal to 'oidc.myProvider'. + // result.credential.idToken is the OIDC provider's ID token. + }) + .catch((error) => { + // Handle error. + }); + // [END auth_oidc_signin_popup] +} + +function oidcSignInRedirect(provider) { + // [START auth_oidc_signin_redirect] + firebase.auth().signInWithRedirect(provider).catch((error) => { + // Handle error. + }); + // [END auth_oidc_signin_redirect] +} + +function oidcSignInRedirectResult(provider) { + // [START auth_oidc_signin_redirect_result] + // On return. + firebase.auth().getRedirectResult() + .then((result) => { + // User is signed in. + // result.credential is a firebase.auth().OAuthCredential object. + // result.credential.providerId is equal to 'oidc.myProvider'. + // result.credential.idToken is the OIDC provider's ID token. + }) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END auth_oidc_signin_redirect_result] +} + +function oidcDirectSignIn(provider, oidcIdToken) { + // [START auth_oidc_direct_sign_in] + const credential = provider.credential(oidcIdToken, null); + + firebase.auth().signInWithCredential(credential) + .then((result) => { + // User is signed in. + // User now has a odic.myProvider UserInfo in providerData. + }) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END auth_oidc_direct_sign_in] +} + diff --git a/auth/saml.js b/auth/saml.js new file mode 100644 index 00000000..a55b691c --- /dev/null +++ b/auth/saml.js @@ -0,0 +1,56 @@ +// These samples are intended for Web so this import would normally be +// done in HTML however using modules here is more convenient for +// ensuring sample correctness offline. +import firebase from "firebase/app"; +import "firebase/auth"; + +// [SNIPPET_REGISTRY disabled] +// [SNIPPETS_SEPARATION enabled] + +function samlProvider() { + // [START auth_saml_provider_create] + const provider = new firebase.auth.SAMLAuthProvider('saml.myProvider'); + // [END auth_saml_provider_create] +} + +function samlSignInPopup(provider) { + // [START auth_saml_signin_popup] + firebase.auth().signInWithPopup(provider) + .then((result) => { + // User is signed in. + // Identity provider data available in result.additionalUserInfo.profile, + // or from the user's ID token obtained from result.user.getIdToken() + // as an object in the firebase.sign_in_attributes custom claim + // This is also available from result.user.getIdTokenResult() + // idTokenResult.claims.firebase.sign_in_attributes. + }) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END auth_saml_signin_popup] +} + +function samlSignInRedirect(provider) { + // [START auth_saml_signin_redirect] + firebase.auth().signInWithRedirect(provider); + // [END auth_saml_signin_redirect] +} + +function samlSignInRedirectResult(provider) { + // [START auth_saml_signin_redirect_result] + firebase.auth().getRedirectResult() + .then((result) => { + // User is signed in. + // Provider data available in result.additionalUserInfo.profile, + // or from the user's ID token obtained from result.user.getIdToken() + // as an object in the firebase.sign_in_attributes custom claim + // This is also available from result.user.getIdTokenResult() + // idTokenResult.claims.firebase.sign_in_attributes. + }).catch((error) => { + // Handle / display error. + // ... + }); + // [END auth_saml_signin_redirect_result] +} + diff --git a/snippets/auth-next/oidc/auth_oidc_direct_sign_in.js b/snippets/auth-next/oidc/auth_oidc_direct_sign_in.js new file mode 100644 index 00000000..65f693a6 --- /dev/null +++ b/snippets/auth-next/oidc/auth_oidc_direct_sign_in.js @@ -0,0 +1,31 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_direct_sign_in_modular] +import { getAuth, OAuthProvider, signInWithCredential } from "firebase/auth"; + +const auth = getAuth(); +const credential = provider.credential({ + idToken: oidcIdToken, +}); +signInWithCredential(auth, credential) + .then((result) => { + // User is signed in. + const newCredential = OAuthProvider.credentialFromResult(result); + // This gives you a new access token for the OIDC provider. You can use it to directly interact with that provider. + }) + .catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = OAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); +// [END auth_oidc_direct_sign_in_modular] \ No newline at end of file diff --git a/snippets/auth-next/oidc/auth_oidc_provider_create.js b/snippets/auth-next/oidc/auth_oidc_provider_create.js new file mode 100644 index 00000000..ce1846b9 --- /dev/null +++ b/snippets/auth-next/oidc/auth_oidc_provider_create.js @@ -0,0 +1,11 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_provider_create_modular] +import { OAuthProvider } from "firebase/auth"; + +const provider = new OAuthProvider("oidc.myProvider"); +// [END auth_oidc_provider_create_modular] \ No newline at end of file diff --git a/snippets/auth-next/oidc/auth_oidc_signin_popup.js b/snippets/auth-next/oidc/auth_oidc_signin_popup.js new file mode 100644 index 00000000..76b01b1d --- /dev/null +++ b/snippets/auth-next/oidc/auth_oidc_signin_popup.js @@ -0,0 +1,27 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_signin_popup_modular] +import { getAuth, signInWithPopup, OAuthProvider } from "firebase/auth"; + +const auth = getAuth(); +signInWithPopup(auth, provider) + .then((result) => { + // User is signed in. + const credential = OAuthProvider.credentialFromResult(result); + // This gives you an access token for the OIDC provider. You can use it to directly interact with that provider + }).catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = OAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); +// [END auth_oidc_signin_popup_modular] \ No newline at end of file diff --git a/snippets/auth-next/oidc/auth_oidc_signin_redirect.js b/snippets/auth-next/oidc/auth_oidc_signin_redirect.js new file mode 100644 index 00000000..2038d116 --- /dev/null +++ b/snippets/auth-next/oidc/auth_oidc_signin_redirect.js @@ -0,0 +1,12 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_signin_redirect_modular] +import { getAuth, signInWithRedirect } from "firebase/auth"; + +const auth = getAuth(); +signInWithRedirect(auth, provider); +// [END auth_oidc_signin_redirect_modular] \ No newline at end of file diff --git a/snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js b/snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js new file mode 100644 index 00000000..ae5a441d --- /dev/null +++ b/snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js @@ -0,0 +1,28 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_signin_redirect_result_modular] +import { getAuth, getRedirectResult, OAuthProvider } from "firebase/auth"; + +const auth = getAuth(); +getRedirectResult(auth) + .then((result) => { + // User is signed in. + const credential = OAuthProvider.credentialFromResult(result); + // This gives you an access token for the OIDC provider. You can use it to directly interact with that provider + }) + .catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = OAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); +// [END auth_oidc_signin_redirect_result_modular] \ No newline at end of file diff --git a/snippets/auth-next/saml/auth_saml_provider_create.js b/snippets/auth-next/saml/auth_saml_provider_create.js new file mode 100644 index 00000000..e492d490 --- /dev/null +++ b/snippets/auth-next/saml/auth_saml_provider_create.js @@ -0,0 +1,11 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_provider_create_modular] +import { SAMLAuthProvider } from "firebase/auth"; + +const provider = new SAMLAuthProvider("saml.myProvider"); +// [END auth_saml_provider_create_modular] \ No newline at end of file diff --git a/snippets/auth-next/saml/auth_saml_signin_popup.js b/snippets/auth-next/saml/auth_saml_signin_popup.js new file mode 100644 index 00000000..8010a17b --- /dev/null +++ b/snippets/auth-next/saml/auth_saml_signin_popup.js @@ -0,0 +1,27 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_signin_popup_modular] +import { getAuth, signInWithPopup, SAMLAuthProvider } from "firebase/auth"; + +const auth = getAuth(); +signInWithPopup(auth, provider) + .then((result) => { + // User is signed in. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }).catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = SAMLAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); +// [END auth_saml_signin_popup_modular] \ No newline at end of file diff --git a/snippets/auth-next/saml/auth_saml_signin_redirect.js b/snippets/auth-next/saml/auth_saml_signin_redirect.js new file mode 100644 index 00000000..619af67f --- /dev/null +++ b/snippets/auth-next/saml/auth_saml_signin_redirect.js @@ -0,0 +1,12 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_signin_redirect_modular] +import { getAuth, signInWithRedirect } from "firebase/auth"; + +const auth = getAuth(); +signInWithRedirect(auth, provider); +// [END auth_saml_signin_redirect_modular] \ No newline at end of file diff --git a/snippets/auth-next/saml/auth_saml_signin_redirect_result.js b/snippets/auth-next/saml/auth_saml_signin_redirect_result.js new file mode 100644 index 00000000..4e4d4260 --- /dev/null +++ b/snippets/auth-next/saml/auth_saml_signin_redirect_result.js @@ -0,0 +1,28 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_signin_redirect_result_modular] +import { getAuth, getRedirectResult, SAMLAuthProvider } from "firebase/auth"; + +const auth = getAuth(); +getRedirectResult(auth) + .then((result) => { + // User is signed in. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }) + .catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // The email of the user's account used. + const email = error.email; + // The AuthCredential type that was used. + const credential = SAMLAuthProvider.credentialFromError(error); + // Handle / display error. + // ... + }); +// [END auth_saml_signin_redirect_result_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_direct_sign_in.js b/snippets/auth/oidc/auth_oidc_direct_sign_in.js new file mode 100644 index 00000000..5a0c629d --- /dev/null +++ b/snippets/auth/oidc/auth_oidc_direct_sign_in.js @@ -0,0 +1,19 @@ +// This snippet file was generated by processing the source file: +// ./auth/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_direct_sign_in_modular] +const credential = provider.credential(oidcIdToken, null); + +firebase.auth().signInWithCredential(credential) + .then((result) => { + // User is signed in. + // User now has a odic.myProvider UserInfo in providerData. + }) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END auth_oidc_direct_sign_in_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_provider_create.js b/snippets/auth/oidc/auth_oidc_provider_create.js new file mode 100644 index 00000000..09e08ad8 --- /dev/null +++ b/snippets/auth/oidc/auth_oidc_provider_create.js @@ -0,0 +1,9 @@ +// This snippet file was generated by processing the source file: +// ./auth/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_provider_create_modular] +const provider = new firebase.auth.OAuthProvider('oidc.myProvider'); +// [END auth_oidc_provider_create_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_signin_popup.js b/snippets/auth/oidc/auth_oidc_signin_popup.js new file mode 100644 index 00000000..c5ff4afa --- /dev/null +++ b/snippets/auth/oidc/auth_oidc_signin_popup.js @@ -0,0 +1,18 @@ +// This snippet file was generated by processing the source file: +// ./auth/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_signin_popup_modular] +firebase.auth().signInWithPopup(provider) + .then((result) => { + // User is signed in. + // result.credential is a firebase.auth().OAuthCredential object. + // result.credential.providerId is equal to 'oidc.myProvider'. + // result.credential.idToken is the OIDC provider's ID token. + }) + .catch((error) => { + // Handle error. + }); +// [END auth_oidc_signin_popup_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_signin_redirect.js b/snippets/auth/oidc/auth_oidc_signin_redirect.js new file mode 100644 index 00000000..4951c4bf --- /dev/null +++ b/snippets/auth/oidc/auth_oidc_signin_redirect.js @@ -0,0 +1,11 @@ +// This snippet file was generated by processing the source file: +// ./auth/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_signin_redirect_modular] +firebase.auth().signInWithRedirect(provider).catch((error) => { + // Handle error. +}); +// [END auth_oidc_signin_redirect_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_signin_redirect_result.js b/snippets/auth/oidc/auth_oidc_signin_redirect_result.js new file mode 100644 index 00000000..2cd0eaa7 --- /dev/null +++ b/snippets/auth/oidc/auth_oidc_signin_redirect_result.js @@ -0,0 +1,20 @@ +// This snippet file was generated by processing the source file: +// ./auth/oidc.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_oidc_signin_redirect_result_modular] +// On return. +firebase.auth().getRedirectResult() + .then((result) => { + // User is signed in. + // result.credential is a firebase.auth().OAuthCredential object. + // result.credential.providerId is equal to 'oidc.myProvider'. + // result.credential.idToken is the OIDC provider's ID token. + }) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END auth_oidc_signin_redirect_result_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_provider_create.js b/snippets/auth/saml/auth_saml_provider_create.js new file mode 100644 index 00000000..a9765e5e --- /dev/null +++ b/snippets/auth/saml/auth_saml_provider_create.js @@ -0,0 +1,9 @@ +// This snippet file was generated by processing the source file: +// ./auth/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_provider_create_modular] +const provider = new firebase.auth.SAMLAuthProvider('saml.myProvider'); +// [END auth_saml_provider_create_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_signin_popup.js b/snippets/auth/saml/auth_saml_signin_popup.js new file mode 100644 index 00000000..1fb3b4f6 --- /dev/null +++ b/snippets/auth/saml/auth_saml_signin_popup.js @@ -0,0 +1,21 @@ +// This snippet file was generated by processing the source file: +// ./auth/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_signin_popup_modular] +firebase.auth().signInWithPopup(provider) + .then((result) => { + // User is signed in. + // Identity provider data available in result.additionalUserInfo.profile, + // or from the user's ID token obtained from result.user.getIdToken() + // as an object in the firebase.sign_in_attributes custom claim + // This is also available from result.user.getIdTokenResult() + // idTokenResult.claims.firebase.sign_in_attributes. + }) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END auth_saml_signin_popup_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_signin_redirect.js b/snippets/auth/saml/auth_saml_signin_redirect.js new file mode 100644 index 00000000..bd328a57 --- /dev/null +++ b/snippets/auth/saml/auth_saml_signin_redirect.js @@ -0,0 +1,9 @@ +// This snippet file was generated by processing the source file: +// ./auth/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_signin_redirect_modular] +firebase.auth().signInWithRedirect(provider); +// [END auth_saml_signin_redirect_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_signin_redirect_result.js b/snippets/auth/saml/auth_saml_signin_redirect_result.js new file mode 100644 index 00000000..65a9f38b --- /dev/null +++ b/snippets/auth/saml/auth_saml_signin_redirect_result.js @@ -0,0 +1,20 @@ +// This snippet file was generated by processing the source file: +// ./auth/saml.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_saml_signin_redirect_result_modular] +firebase.auth().getRedirectResult() + .then((result) => { + // User is signed in. + // Provider data available in result.additionalUserInfo.profile, + // or from the user's ID token obtained from result.user.getIdToken() + // as an object in the firebase.sign_in_attributes custom claim + // This is also available from result.user.getIdTokenResult() + // idTokenResult.claims.firebase.sign_in_attributes. + }).catch((error) => { + // Handle / display error. + // ... + }); +// [END auth_saml_signin_redirect_result_modular] \ No newline at end of file From 20d5d980c84eb7f59547b3007dfb518098877248 Mon Sep 17 00:00:00 2001 From: Ian Tay Date: Fri, 15 Oct 2021 13:33:07 -0700 Subject: [PATCH 02/38] add initialization with custom domain code (#247) remove wrong tags (supposed to be for auth-next) --- auth-next/index.js | 16 +++++++++++++- auth/index.js | 11 ++++++++++ auth/oidc.js | 3 --- auth/saml.js | 3 --- .../index/auth_init_custom_domain.js | 17 +++++++++++++++ .../auth/oidc/auth_oidc_direct_sign_in.js | 19 ----------------- .../auth/oidc/auth_oidc_provider_create.js | 9 -------- snippets/auth/oidc/auth_oidc_signin_popup.js | 18 ---------------- .../auth/oidc/auth_oidc_signin_redirect.js | 11 ---------- .../oidc/auth_oidc_signin_redirect_result.js | 20 ------------------ .../auth/saml/auth_saml_provider_create.js | 9 -------- snippets/auth/saml/auth_saml_signin_popup.js | 21 ------------------- .../auth/saml/auth_saml_signin_redirect.js | 9 -------- .../saml/auth_saml_signin_redirect_result.js | 20 ------------------ 14 files changed, 43 insertions(+), 143 deletions(-) create mode 100644 snippets/auth-next/index/auth_init_custom_domain.js delete mode 100644 snippets/auth/oidc/auth_oidc_direct_sign_in.js delete mode 100644 snippets/auth/oidc/auth_oidc_provider_create.js delete mode 100644 snippets/auth/oidc/auth_oidc_signin_popup.js delete mode 100644 snippets/auth/oidc/auth_oidc_signin_redirect.js delete mode 100644 snippets/auth/oidc/auth_oidc_signin_redirect_result.js delete mode 100644 snippets/auth/saml/auth_saml_provider_create.js delete mode 100644 snippets/auth/saml/auth_saml_signin_popup.js delete mode 100644 snippets/auth/saml/auth_saml_signin_redirect.js delete mode 100644 snippets/auth/saml/auth_saml_signin_redirect_result.js diff --git a/auth-next/index.js b/auth-next/index.js index 73d33219..c4dadfe0 100644 --- a/auth-next/index.js +++ b/auth-next/index.js @@ -26,7 +26,7 @@ function makeFacebookCredential(response) { function makeEmailCredential(email, password) { // [START auth_make_email_credential] const { EmailAuthProvider } = require("firebase/auth"); - + const credential = EmailAuthProvider.credential(email, password); // [END auth_make_email_credential] } @@ -121,3 +121,17 @@ function signInRedirect(provider) { signInWithRedirect(auth, provider); // [END auth_signin_redirect] } + +function initializeWithCustomDomain() { + // [START auth_init_custom_domain] + const { initializeApp } = require("firebase/app"); + + const firebaseConfig = { + apiKey: "...", + // By default, authDomain is '[YOUR_APP].firebaseapp.com'. + // You may replace it with a custom domain. + authDomain: '[YOUR_CUSTOM_DOMAIN]' + }; + const firebaseApp = initializeApp(firebaseConfig); + // [END auth_init_custom_domain] +} diff --git a/auth/index.js b/auth/index.js index 6ea5d587..6567c030 100644 --- a/auth/index.js +++ b/auth/index.js @@ -101,3 +101,14 @@ function signInRedirect(provider) { firebase.auth().signInWithRedirect(provider); // [END auth_signin_redirect] } + +function initializeWithCustomDomain() { + // [START auth_init_custom_domain] + firebase.initializeApp({ + apiKey: '...', + // By default, authDomain is '[YOUR_APP].firebaseapp.com'. + // You may replace it with a custom domain. + authDomain: '[YOUR_CUSTOM_DOMAIN]' + }); + // [END auth_init_custom_domain] +} diff --git a/auth/oidc.js b/auth/oidc.js index 4c056e52..e3a3e01e 100644 --- a/auth/oidc.js +++ b/auth/oidc.js @@ -4,9 +4,6 @@ import firebase from "firebase/app"; import "firebase/auth"; -// [SNIPPET_REGISTRY disabled] -// [SNIPPETS_SEPARATION enabled] - function oidcProvider() { // [START auth_oidc_provider_create] const provider = new firebase.auth.OAuthProvider('oidc.myProvider'); diff --git a/auth/saml.js b/auth/saml.js index a55b691c..e3a99cde 100644 --- a/auth/saml.js +++ b/auth/saml.js @@ -4,9 +4,6 @@ import firebase from "firebase/app"; import "firebase/auth"; -// [SNIPPET_REGISTRY disabled] -// [SNIPPETS_SEPARATION enabled] - function samlProvider() { // [START auth_saml_provider_create] const provider = new firebase.auth.SAMLAuthProvider('saml.myProvider'); diff --git a/snippets/auth-next/index/auth_init_custom_domain.js b/snippets/auth-next/index/auth_init_custom_domain.js new file mode 100644 index 00000000..971e5c56 --- /dev/null +++ b/snippets/auth-next/index/auth_init_custom_domain.js @@ -0,0 +1,17 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/index.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_init_custom_domain_modular] +import { initializeApp } from "firebase/app"; + +const firebaseConfig = { + apiKey: "...", + // By default, authDomain is '[YOUR_APP].firebaseapp.com'. + // You may replace it with a custom domain. + authDomain: '[YOUR_CUSTOM_DOMAIN]' +}; +const firebaseApp = initializeApp(firebaseConfig); +// [END auth_init_custom_domain_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_direct_sign_in.js b/snippets/auth/oidc/auth_oidc_direct_sign_in.js deleted file mode 100644 index 5a0c629d..00000000 --- a/snippets/auth/oidc/auth_oidc_direct_sign_in.js +++ /dev/null @@ -1,19 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/oidc.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_oidc_direct_sign_in_modular] -const credential = provider.credential(oidcIdToken, null); - -firebase.auth().signInWithCredential(credential) - .then((result) => { - // User is signed in. - // User now has a odic.myProvider UserInfo in providerData. - }) - .catch((error) => { - // Handle / display error. - // ... - }); -// [END auth_oidc_direct_sign_in_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_provider_create.js b/snippets/auth/oidc/auth_oidc_provider_create.js deleted file mode 100644 index 09e08ad8..00000000 --- a/snippets/auth/oidc/auth_oidc_provider_create.js +++ /dev/null @@ -1,9 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/oidc.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_oidc_provider_create_modular] -const provider = new firebase.auth.OAuthProvider('oidc.myProvider'); -// [END auth_oidc_provider_create_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_signin_popup.js b/snippets/auth/oidc/auth_oidc_signin_popup.js deleted file mode 100644 index c5ff4afa..00000000 --- a/snippets/auth/oidc/auth_oidc_signin_popup.js +++ /dev/null @@ -1,18 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/oidc.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_oidc_signin_popup_modular] -firebase.auth().signInWithPopup(provider) - .then((result) => { - // User is signed in. - // result.credential is a firebase.auth().OAuthCredential object. - // result.credential.providerId is equal to 'oidc.myProvider'. - // result.credential.idToken is the OIDC provider's ID token. - }) - .catch((error) => { - // Handle error. - }); -// [END auth_oidc_signin_popup_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_signin_redirect.js b/snippets/auth/oidc/auth_oidc_signin_redirect.js deleted file mode 100644 index 4951c4bf..00000000 --- a/snippets/auth/oidc/auth_oidc_signin_redirect.js +++ /dev/null @@ -1,11 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/oidc.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_oidc_signin_redirect_modular] -firebase.auth().signInWithRedirect(provider).catch((error) => { - // Handle error. -}); -// [END auth_oidc_signin_redirect_modular] \ No newline at end of file diff --git a/snippets/auth/oidc/auth_oidc_signin_redirect_result.js b/snippets/auth/oidc/auth_oidc_signin_redirect_result.js deleted file mode 100644 index 2cd0eaa7..00000000 --- a/snippets/auth/oidc/auth_oidc_signin_redirect_result.js +++ /dev/null @@ -1,20 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/oidc.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_oidc_signin_redirect_result_modular] -// On return. -firebase.auth().getRedirectResult() - .then((result) => { - // User is signed in. - // result.credential is a firebase.auth().OAuthCredential object. - // result.credential.providerId is equal to 'oidc.myProvider'. - // result.credential.idToken is the OIDC provider's ID token. - }) - .catch((error) => { - // Handle / display error. - // ... - }); -// [END auth_oidc_signin_redirect_result_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_provider_create.js b/snippets/auth/saml/auth_saml_provider_create.js deleted file mode 100644 index a9765e5e..00000000 --- a/snippets/auth/saml/auth_saml_provider_create.js +++ /dev/null @@ -1,9 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/saml.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_saml_provider_create_modular] -const provider = new firebase.auth.SAMLAuthProvider('saml.myProvider'); -// [END auth_saml_provider_create_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_signin_popup.js b/snippets/auth/saml/auth_saml_signin_popup.js deleted file mode 100644 index 1fb3b4f6..00000000 --- a/snippets/auth/saml/auth_saml_signin_popup.js +++ /dev/null @@ -1,21 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/saml.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_saml_signin_popup_modular] -firebase.auth().signInWithPopup(provider) - .then((result) => { - // User is signed in. - // Identity provider data available in result.additionalUserInfo.profile, - // or from the user's ID token obtained from result.user.getIdToken() - // as an object in the firebase.sign_in_attributes custom claim - // This is also available from result.user.getIdTokenResult() - // idTokenResult.claims.firebase.sign_in_attributes. - }) - .catch((error) => { - // Handle / display error. - // ... - }); -// [END auth_saml_signin_popup_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_signin_redirect.js b/snippets/auth/saml/auth_saml_signin_redirect.js deleted file mode 100644 index bd328a57..00000000 --- a/snippets/auth/saml/auth_saml_signin_redirect.js +++ /dev/null @@ -1,9 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/saml.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_saml_signin_redirect_modular] -firebase.auth().signInWithRedirect(provider); -// [END auth_saml_signin_redirect_modular] \ No newline at end of file diff --git a/snippets/auth/saml/auth_saml_signin_redirect_result.js b/snippets/auth/saml/auth_saml_signin_redirect_result.js deleted file mode 100644 index 65a9f38b..00000000 --- a/snippets/auth/saml/auth_saml_signin_redirect_result.js +++ /dev/null @@ -1,20 +0,0 @@ -// This snippet file was generated by processing the source file: -// ./auth/saml.js -// -// To update the snippets in this file, edit the source and then run -// 'npm run snippets'. - -// [START auth_saml_signin_redirect_result_modular] -firebase.auth().getRedirectResult() - .then((result) => { - // User is signed in. - // Provider data available in result.additionalUserInfo.profile, - // or from the user's ID token obtained from result.user.getIdToken() - // as an object in the firebase.sign_in_attributes custom claim - // This is also available from result.user.getIdTokenResult() - // idTokenResult.claims.firebase.sign_in_attributes. - }).catch((error) => { - // Handle / display error. - // ... - }); -// [END auth_saml_signin_redirect_result_modular] \ No newline at end of file From e2a9d336d42add89bc3f504e4143300adea25685 Mon Sep 17 00:00:00 2001 From: Ian Tay Date: Mon, 18 Oct 2021 16:51:42 -0700 Subject: [PATCH 03/38] add multi-tenancy snippets (#250) --- auth-next/multi-tenancy.js | 347 ++++++++++++++++++ auth/multi-tenancy.js | 312 ++++++++++++++++ .../multitenant_account_exists_popup.js | 44 +++ .../multitenant_account_exists_redirect.js | 51 +++ .../multitenant_account_linking.js | 34 ++ .../multitenant_create_custom_token.js | 20 + .../multitenant_send_emaillink.js | 23 ++ .../multi-tenancy/multitenant_set_tenant.js | 12 + .../multitenant_signin_custom_token.js | 16 + .../multitenant_signin_emaillink.js | 29 ++ .../multitenant_signin_password.js | 19 + .../multitenant_signin_password_demo.js | 33 ++ .../multitenant_signin_saml_popup.js | 25 ++ .../multitenant_signin_saml_redirect.js | 29 ++ .../multitenant_signup_password.js | 19 + .../multitenant_switch_tenant.js | 15 + ...multitenant_switch_tenant_multiinstance.js | 19 + 17 files changed, 1047 insertions(+) create mode 100644 auth-next/multi-tenancy.js create mode 100644 auth/multi-tenancy.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_account_linking.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_create_custom_token.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_send_emaillink.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_set_tenant.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_signin_custom_token.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_signin_emaillink.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_signin_password.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_signin_password_demo.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_signin_saml_popup.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_signin_saml_redirect.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_signup_password.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_switch_tenant.js create mode 100644 snippets/auth-next/multi-tenancy/multitenant_switch_tenant_multiinstance.js diff --git a/auth-next/multi-tenancy.js b/auth-next/multi-tenancy.js new file mode 100644 index 00000000..c0c86662 --- /dev/null +++ b/auth-next/multi-tenancy.js @@ -0,0 +1,347 @@ +// [SNIPPET_REGISTRY disabled] +// [SNIPPETS_SEPARATION enabled] + +function setTenant() { + // [START multitenant_set_tenant] + const { getAuth } = require("firebase/auth"); + const auth = getAuth(); + const tenantId = "TENANT_ID1"; + auth.tenantId = tenantId; + // [END multitenant_set_tenant] +} + +function switchTenantSingleAuth(auth) { + // [START multitenant_switch_tenant] + // One Auth instance + // Switch to tenant1 + auth.tenantId = "TENANT_ID1"; + // Switch to tenant2 + auth.tenantId = "TENANT_ID2"; + // Switch back to project level IdPs + auth.tenantId = null; + // [END multitenant_switch_tenant] +} + +function switchTenantMultiAuth(firebaseConfig1, firebaseConfig2) { + // [START multitenant_switch_tenant_multiinstance] + // Multiple Auth instances + const { initializeApp } = require("firebase/app"); + const { getAuth } = require("firebase/auth"); + const firebaseApp1 = initializeApp(firebaseConfig1, 'app1_for_tenantId1'); + const firebaseApp2 = initializeApp(firebaseConfig2, 'app2_for_tenantId2'); + + const auth1 = getAuth(firebaseApp1); + const auth2 = getAuth(firebaseApp2); + + auth1.tenantId = "TENANT_ID1"; + auth2.tenantId = "TENANT_ID2"; + // [END multitenant_switch_tenant_multiinstance] +} + +function passwordSignInWithTenantDemo(auth, email, password) { + // [START multitenant_signin_password_demo] + const { signInWithEmailAndPassword, onAuthStateChanged } = require("firebase/auth"); + // Switch to TENANT_ID1 + auth.tenantId = 'TENANT_ID1'; + + // Sign in with tenant + signInWithEmailAndPassword(auth, email, password) + .then((userCredential) => { + // User is signed in. + const user = userCredential.user; + // user.tenantId is set to 'TENANT_ID1'. + // Switch to 'TENANT_ID2'. + auth.tenantId = 'TENANT_ID2'; + // auth.currentUser still points to the user. + // auth.currentUser.tenantId is 'TENANT_ID1'. + }); + + // You could also get the current user from Auth state observer. + onAuthStateChanged(auth, (user) => { + if (user) { + // User is signed in. + // user.tenantId is set to 'TENANT_ID1'. + } else { + // No user is signed in. + } + }); + // [END multitenant_signin_password_demo] +} + +function signUpWithTenant(auth, email, password) { + // [START multitenant_signup_password] + const { createUserWithEmailAndPassword } = require("firebase/auth"); + auth.tenantId = 'TENANT_ID'; + + createUserWithEmailAndPassword(auth, email, password) + .then((userCredential) => { + // User is signed in. + // userCredential.user.tenantId is 'TENANT_ID'. + }).catch((error) => { + // Handle / display error. + // ... + }); + // [END multitenant_signup_password] +} + + +function passwordSignInWithTenant(auth, email, password) { + // [START multitenant_signin_password] + const { signInWithEmailAndPassword } = require("firebase/auth"); + auth.tenantId = 'TENANT_ID'; + + signInWithEmailAndPassword(auth, email, password) + .then((userCredential) => { + // User is signed in. + // userCredential.user.tenantId is 'TENANT_ID'. + }).catch((error) => { + // Handle / display error. + // ... + }); + // [END multitenant_signin_password] +} + +function samlSignInPopupTenant(auth, provider) { + // [START multitenant_signin_saml_popup] + const { signInWithPopup } = require("firebase/auth"); + // Switch to TENANT_ID1. + auth.tenantId = 'TENANT_ID1'; + + // Sign-in with popup. + signInWithPopup(auth, provider) + .then((userCredential) => { + // User is signed in. + const user = userCredential.user; + // user.tenantId is set to 'TENANT_ID1'. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END multitenant_signin_saml_popup] +} + +function samlSignInRedirectTenant(auth, provider) { + // [START multitenant_signin_saml_redirect] + const { signInWithRedirect, getRedirectResult } = require("firebase/auth"); + // Switch to TENANT_ID1. + auth.tenantId = 'TENANT_ID1'; + + // Sign-in with redirect. + signInWithRedirect(auth, provider); + + // After the user completes sign-in and returns to the app, you can get + // the sign-in result by calling getRedirectResult. However, if they sign out + // and sign in again with an IdP, no tenant is used. + getRedirectResult(auth) + .then((result) => { + // User is signed in. + // The tenant ID available in result.user.tenantId. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END multitenant_signin_saml_redirect] +} + +function sendSignInLinkToEmailTenant(auth, email, actionCodeSettings) { + // [START multitenant_send_emaillink] + const { sendSignInLinkToEmail } = require("firebase/auth"); + // Switch to TENANT_ID1 + auth.tenantId = 'TENANT_ID1'; + + sendSignInLinkToEmail(auth, email, actionCodeSettings) + .then(() => { + // The link was successfully sent. Inform the user. + // Save the email locally so you don't need to ask the user for it again + // if they open the link on the same device. + window.localStorage.setItem('emailForSignIn', email); + }) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END multitenant_send_emaillink] +} + +function signInWithEmailLinkTenant(auth) { + // [START multitenant_signin_emaillink] + const { isSignInWithEmailLink, parseActionCodeURL, signInWithEmailLink } = require("firebase/auth"); + if (isSignInWithEmailLink(auth, window.location.href)) { + const actionCodeUrl = parseActionCodeURL(window.location.href); + if (actionCodeUrl.tenantId) { + auth.tenantId = actionCodeUrl.tenantId; + } + let email = window.localStorage.getItem('emailForSignIn'); + if (!email) { + // User opened the link on a different device. To prevent session fixation + // attacks, ask the user to provide the associated email again. For example: + email = window.prompt('Please provide your email for confirmation'); + } + // The client SDK will parse the code from the link for you. + signInWithEmailLink(auth, email, window.location.href) + .then((result) => { + // User is signed in. + // tenant ID available in result.user.tenantId. + // Clear email from storage. + window.localStorage.removeItem('emailForSignIn'); + }); + } + // [END multitenant_signin_emaillink] +} + +// Same as the code in auth/ since this is the admin SDK. +function createCustomTokenTenant(admin, uid) { + // [START multitenant_create_custom_token] + // Ensure you're using a tenant-aware auth instance + const tenantManager = admin.auth().tenantManager(); + const tenantAuth = tenantManager.authForTenant('TENANT_ID1'); + + // Create a custom token in the usual manner + tenantAuth.createCustomToken(uid) + .then((customToken) => { + // Send token back to client + }) + .catch((error) => { + console.log('Error creating custom token:', error); + }); + // [END multitenant_create_custom_token] +} + +function signInWithCustomTokenTenant(auth, token) { + // [START multitenant_signin_custom_token] + const { signInWithCustomToken } = require("firebase/auth"); + auth.tenantId = 'TENANT_ID1'; + + signInWithCustomToken(auth, token) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END multitenant_signin_custom_token] +} + +function linkAccountTenant(auth, provider, email, password) { + // [START multitenant_account_linking] + const { signInWithPopup, EmailAuthProvider, linkWithCredential, SAMLAuthProvider, signInWithCredential } = require("firebase/auth"); + // Switch to TENANT_ID1 + auth.tenantId = 'TENANT_ID1'; + + // Sign-in with popup + signInWithPopup(auth, provider) + .then((userCredential) => { + // Existing user with e.g. SAML provider. + const prevUser = userCredential.user; + const emailCredential = + EmailAuthProvider.credential(email, password); + return linkWithCredential(prevUser, emailCredential) + .then((linkResult) => { + // Sign in with the newly linked credential + const linkCredential = SAMLAuthProvider.credentialFromResult(linkResult); + return signInWithCredential(auth, linkCredential); + }) + .then((signInResult) => { + // Handle sign in of merged user + // ... + }); + }) + .catch((error) => { + // Handle / display error. + // ... + }); + // [END multitenant_account_linking] +} + +function accountExistsPopupTenant(auth, samlProvider, googleProvider, goToApp) { + // [START multitenant_account_exists_popup] + const { signInWithPopup, fetchSignInMethodsForEmail, linkWithCredential } = require("firebase/auth"); + // Step 1. + // User tries to sign in to the SAML provider in that tenant. + auth.tenantId = 'TENANT_ID'; + signInWithPopup(auth, samlProvider) + .catch((error) => { + // An error happened. + if (error.code === 'auth/account-exists-with-different-credential') { + // Step 2. + // User's email already exists. + // The pending SAML credential. + const pendingCred = error.credential; + // The credential's tenantId if needed: error.tenantId + // The provider account's email address. + const email = error.email; + // Get sign-in methods for this email. + fetchSignInMethodsForEmail(email, auth) + .then((methods) => { + // Step 3. + // Ask the user to sign in with existing Google account. + if (methods[0] == 'google.com') { + signInWithPopup(auth, googleProvider) + .then((result) => { + // Step 4 + // Link the SAML AuthCredential to the existing user. + linkWithCredential(result.user, pendingCred) + .then((linkResult) => { + // SAML account successfully linked to the existing + // user. + goToApp(); + }); + }); + } + }); + } + }); + // [END multitenant_account_exists_popup] +} + +function accountExistsRedirectTenant(auth, samlProvider, googleProvider, goToApp) { + // [START multitenant_account_exists_redirect] + const { signInWithRedirect, getRedirectResult, fetchSignInMethodsForEmail, linkWithCredential } = require("firebase/auth"); + // Step 1. + // User tries to sign in to SAML provider. + auth.tenantId = 'TENANT_ID'; + signInWithRedirect(auth, samlProvider); + var pendingCred; + // Redirect back from SAML IDP. auth.tenantId is null after redirecting. + getRedirectResult(auth).catch((error) => { + if (error.code === 'auth/account-exists-with-different-credential') { + // Step 2. + // User's email already exists. + const tenantId = error.tenantId; + // The pending SAML credential. + pendingCred = error.credential; + // The provider account's email address. + const email = error.email; + // Need to set the tenant ID again as the page was reloaded and the + // previous setting was reset. + auth.tenantId = tenantId; + // Get sign-in methods for this email. + fetchSignInMethodsForEmail(auth, email) + .then((methods) => { + // Step 3. + // Ask the user to sign in with existing Google account. + if (methods[0] == 'google.com') { + signInWithRedirect(auth, googleProvider); + } + }); + } + }); + + // Redirect back from Google. auth.tenantId is null after redirecting. + getRedirectResult(auth).then((result) => { + // Step 4 + // Link the SAML AuthCredential to the existing user. + // result.user.tenantId is 'TENANT_ID'. + linkWithCredential(result.user, pendingCred) + .then((linkResult) => { + // SAML account successfully linked to the existing + // user. + goToApp(); + }); + }); + // [END multitenant_account_exists_redirect] +} \ No newline at end of file diff --git a/auth/multi-tenancy.js b/auth/multi-tenancy.js new file mode 100644 index 00000000..8afc1a5c --- /dev/null +++ b/auth/multi-tenancy.js @@ -0,0 +1,312 @@ +// These samples are intended for Web so this import would normally be +// done in HTML however using modules here is more convenient for +// ensuring sample correctness offline. +import firebase from "firebase/app"; +import "firebase/auth"; + +function setTenant() { + // [START multitenant_set_tenant] + const tenantId = "TENANT_ID1"; + firebase.auth().tenantId = tenantId; + // [END multitenant_set_tenant] +} + +function switchTenantSingleAuth() { + // [START multitenant_switch_tenant] + // One Auth instance + // Switch to tenant1 + firebase.auth().tenantId = "TENANT_ID1"; + // Switch to tenant2 + firebase.auth().tenantId = "TENANT_ID2"; + // Switch back to project level IdPs + firebase.auth().tenantId = null; + // [END multitenant_switch_tenant] +} + +function switchTenantMultiAuthInstance(config) { + // [START multitenant_switch_tenant_multiinstance] + // Multiple Auth instances + firebase.initializeApp(config, 'app1_for_tenantId1'); + firebase.initializeApp(config, 'app2_for_tenantId2'); + + const auth1 = firebase.app('app1').auth(); + const auth2 = firebase.app('app2').auth(); + + auth1.tenantId = "TENANT_ID1"; + auth2.tenantId = "TENANT_ID2"; + // [END multitenant_switch_tenant_multiinstance] +} + +function passwordSignInWithTenantDemo(email, password) { + // [START multitenant_signin_password_demo] + // Switch to TENANT_ID1 + firebase.auth().tenantId = 'TENANT_ID1'; + + // Sign in with tenant + firebase.auth().signInWithEmailAndPassword(email, password) + .then((result) => { + const user = result.user; + // user.tenantId is set to 'TENANT_ID1'. + // Switch to 'TENANT_ID2'. + firebase.auth().tenantId = 'TENANT_ID2'; + // firebase.auth().currentUser still point to the user. + // firebase.auth().currentUser.tenantId is 'TENANT_ID1'. + }); + + // You could also get the current user from Auth state observer. + firebase.auth().onAuthStateChanged((user) => { + if (user) { + // User is signed in. + // user.tenantId is set to 'TENANT_ID1'. + } else { + // No user is signed in. + } + }); + // [END multitenant_signin_password_demo] +} + +function signUpWithTenant(email, password) { + // [START multitenant_signup_password] + firebase.auth().tenantId = 'TENANT_ID'; + + firebase.auth().createUserWithEmailAndPassword(email, password) + .then((result) => { + // result.user.tenantId is 'TENANT_ID'. + }).catch((error) => { + // Handle error. + }); + // [END multitenant_signup_password] +} + + +function passwordSignInWithTenant(email, password) { + // [START multitenant_signin_password] + firebase.auth().tenantId = 'TENANT_ID'; + + firebase.auth().signInWithEmailAndPassword(email, password) + .then((result) => { + // result.user.tenantId is 'TENANT_ID'. + }).catch((error) => { + // Handle error. + }); + // [END multitenant_signin_password] +} + +function samlSignInPopupTenant(provider) { + // [START multitenant_signin_saml_popup] + // Switch to TENANT_ID1. + firebase.auth().tenantId = 'TENANT_ID1'; + + // Sign-in with popup. + firebase.auth().signInWithPopup(provider) + .then((result) => { + // User is signed in. + // tenant ID is available in result.user.tenantId. + // Identity provider data is available in result.additionalUserInfo.profile. + }) + .catch((error) => { + // Handle error. + }); + // [END multitenant_signin_saml_popup] +} + +function samlSignInRedirectTenant(provider) { + // [START multitenant_signin_saml_redirect] + // Switch to TENANT_ID1. + firebase.auth().tenantId = 'TENANT_ID1'; + + // Sign-in with redirect. + firebase.auth().signInWithRedirect(provider); + + // After the user completes sign-in and returns to the app, you can get + // the sign-in result by calling getRedirectResult. However, if they sign out + // and sign in again with an IdP, no tenant is used. + firebase.auth().getRedirectResult() + .then((result) => { + // User is signed in. + // The tenant ID available in result.user.tenantId. + // Identity provider data is available in result.additionalUserInfo.profile. + }) + .catch((error) => { + // Handle error. + }); + // [END multitenant_signin_saml_redirect] +} + +function sendSignInLinkToEmailTenant(email, actionCodeSettings) { + // [START multitenant_send_emaillink] + // Switch to TENANT_ID1 + firebase.auth().tenantId = 'TENANT_ID1'; + + firebase.auth().sendSignInLinkToEmail(email, actionCodeSettings) + .then(() => { + // The link was successfully sent. Inform the user. + // Save the email locally so you don't need to ask the user for it again + // if they open the link on the same device. + window.localStorage.setItem('emailForSignIn', email); + }) + .catch((error) => { + // Some error occurred, you can inspect the code: error.code + }); + // [END multitenant_send_emaillink] +} + +function signInWithEmailLinkTenant() { + // [START multitenant_signin_emaillink] + if (firebase.auth().isSignInWithEmailLink(window.location.href)) { + const actionCodeUrl = firebase.auth.ActionCodeURL.parseLink(window.location.href); + if (actionCodeUrl.tenantId) { + firebase.auth().tenantId = actionCodeUrl.tenantId; + } + let email = window.localStorage.getItem('emailForSignIn'); + if (!email) { + // User opened the link on a different device. To prevent session fixation + // attacks, ask the user to provide the associated email again. For example: + email = window.prompt('Please provide your email for confirmation'); + } + firebase.auth().signInWithEmailLink(email, window.location.href) + .then((result) => { + // User is signed in. + // tenant ID available in result.user.tenantId. + }); + } + // [END multitenant_signin_emaillink] +} + +function createCustomTokenTenant(admin, uid) { + // [START multitenant_create_custom_token] + // Ensure you're using a tenant-aware auth instance + const tenantManager = admin.auth().tenantManager(); + const tenantAuth = tenantManager.authForTenant('TENANT_ID1'); + + // Create a custom token in the usual manner + tenantAuth.createCustomToken(uid) + .then((customToken) => { + // Send token back to client + }) + .catch((error) => { + console.log('Error creating custom token:', error); + }); + // [END multitenant_create_custom_token] +} + +function signInWithCustomTokenTenant(token) { + // [START multitenant_signin_custom_token] + firebase.auth().tenantId = 'TENANT_ID1'; + + firebase.auth().signInWithCustomToken(token) + .catch((error) => { + // Handle Errors here. + const errorCode = error.code; + const errorMessage = error.message; + // ... + }); + // [END multitenant_signin_custom_token] +} + +function linkAccountTenant(provider, email, password) { + // [START multitenant_account_linking] + // Switch to TENANT_ID1 + firebase.auth().tenantId = 'TENANT_ID1'; + + // Sign-in with popup + firebase.auth().signInWithPopup(provider) + .then((result) => { + // Existing user with e.g. SAML provider. + const user = result.user; + const emailCredential = + firebase.auth.EmailAuthProvider.credential(email, password); + return user.linkWithCredential(emailCredential); + }) + .then((linkResult) => { + // The user can sign in with both SAML and email/password now. + }); + // [END multitenant_account_linking] +} + +function accountExistsPopupTenant(samlProvider, googleProvider, goToApp) { + // [START multitenant_account_exists_popup] + // Step 1. + // User tries to sign in to the SAML provider in that tenant. + firebase.auth().tenantId = 'TENANT_ID'; + firebase.auth().signInWithPopup(samlProvider) + .catch((error) => { + // An error happened. + if (error.code === 'auth/account-exists-with-different-credential') { + // Step 2. + // User's email already exists. + // The pending SAML credential. + const pendingCred = error.credential; + // The credential's tenantId if needed: error.tenantId + // The provider account's email address. + const email = error.email; + // Get sign-in methods for this email. + firebase.auth().fetchSignInMethodsForEmail(email) + .then((methods) => { + // Step 3. + // Ask the user to sign in with existing Google account. + if (methods[0] == 'google.com') { + firebase.auth().signInWithPopup(googleProvider) + .then((result) => { + // Step 4 + // Link the SAML AuthCredential to the existing user. + result.user.linkWithCredential(pendingCred) + .then((linkResult) => { + // SAML account successfully linked to the existing + // user. + goToApp(); + }); + }); + } + }); + } + }); + // [END multitenant_account_exists_popup] +} + +function accountExistsRedirectTenant(samlProvider, googleProvider, goToApp) { + // [START multitenant_account_exists_redirect] + // Step 1. + // User tries to sign in to SAML provider. + firebase.auth().tenantId = 'TENANT_ID'; + firebase.auth().signInWithRedirect(samlProvider); + var pendingCred; + // Redirect back from SAML IDP. auth.tenantId is null after redirecting. + firebase.auth().getRedirectResult().catch((error) => { + if (error.code === 'auth/account-exists-with-different-credential') { + // Step 2. + // User's email already exists. + const tenantId = error.tenantId; + // The pending SAML credential. + pendingCred = error.credential; + // The provider account's email address. + const email = error.email; + // Need to set the tenant ID again as the page was reloaded and the + // previous setting was reset. + firebase.auth().tenantId = tenantId; + // Get sign-in methods for this email. + firebase.auth().fetchSignInMethodsForEmail(email) + .then((methods) => { + // Step 3. + // Ask the user to sign in with existing Google account. + if (methods[0] == 'google.com') { + firebase.auth().signInWithRedirect(googleProvider); + } + }); + } + }); + + // Redirect back from Google. auth.tenantId is null after redirecting. + firebase.auth().getRedirectResult().then((result) => { + // Step 4 + // Link the SAML AuthCredential to the existing user. + // result.user.tenantId is 'TENANT_ID'. + result.user.linkWithCredential(pendingCred) + .then((linkResult) => { + // SAML account successfully linked to the existing + // user. + goToApp(); + }); + }); + // [END multitenant_account_exists_redirect] +} \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js b/snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js new file mode 100644 index 00000000..43734616 --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js @@ -0,0 +1,44 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_account_exists_popup_modular] +import { signInWithPopup, fetchSignInMethodsForEmail, linkWithCredential } from "firebase/auth"; +// Step 1. +// User tries to sign in to the SAML provider in that tenant. +auth.tenantId = 'TENANT_ID'; +signInWithPopup(auth, samlProvider) + .catch((error) => { + // An error happened. + if (error.code === 'auth/account-exists-with-different-credential') { + // Step 2. + // User's email already exists. + // The pending SAML credential. + const pendingCred = error.credential; + // The credential's tenantId if needed: error.tenantId + // The provider account's email address. + const email = error.email; + // Get sign-in methods for this email. + fetchSignInMethodsForEmail(email, auth) + .then((methods) => { + // Step 3. + // Ask the user to sign in with existing Google account. + if (methods[0] == 'google.com') { + signInWithPopup(auth, googleProvider) + .then((result) => { + // Step 4 + // Link the SAML AuthCredential to the existing user. + linkWithCredential(result.user, pendingCred) + .then((linkResult) => { + // SAML account successfully linked to the existing + // user. + goToApp(); + }); + }); + } + }); + } + }); +// [END multitenant_account_exists_popup_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js b/snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js new file mode 100644 index 00000000..f8a3942d --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js @@ -0,0 +1,51 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_account_exists_redirect_modular] +import { signInWithRedirect, getRedirectResult, fetchSignInMethodsForEmail, linkWithCredential } from "firebase/auth"; +// Step 1. +// User tries to sign in to SAML provider. +auth.tenantId = 'TENANT_ID'; +signInWithRedirect(auth, samlProvider); +var pendingCred; +// Redirect back from SAML IDP. auth.tenantId is null after redirecting. +getRedirectResult(auth).catch((error) => { + if (error.code === 'auth/account-exists-with-different-credential') { + // Step 2. + // User's email already exists. + const tenantId = error.tenantId; + // The pending SAML credential. + pendingCred = error.credential; + // The provider account's email address. + const email = error.email; + // Need to set the tenant ID again as the page was reloaded and the + // previous setting was reset. + auth.tenantId = tenantId; + // Get sign-in methods for this email. + fetchSignInMethodsForEmail(auth, email) + .then((methods) => { + // Step 3. + // Ask the user to sign in with existing Google account. + if (methods[0] == 'google.com') { + signInWithRedirect(auth, googleProvider); + } + }); + } +}); + +// Redirect back from Google. auth.tenantId is null after redirecting. +getRedirectResult(auth).then((result) => { + // Step 4 + // Link the SAML AuthCredential to the existing user. + // result.user.tenantId is 'TENANT_ID'. + linkWithCredential(result.user, pendingCred) + .then((linkResult) => { + // SAML account successfully linked to the existing + // user. + goToApp(); + }); +}); +// [END multitenant_account_exists_redirect_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_account_linking.js b/snippets/auth-next/multi-tenancy/multitenant_account_linking.js new file mode 100644 index 00000000..c43ff90d --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_account_linking.js @@ -0,0 +1,34 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_account_linking_modular] +import { signInWithPopup, EmailAuthProvider, linkWithCredential, SAMLAuthProvider, signInWithCredential } from "firebase/auth"; +// Switch to TENANT_ID1 +auth.tenantId = 'TENANT_ID1'; + +// Sign-in with popup +signInWithPopup(auth, provider) + .then((userCredential) => { + // Existing user with e.g. SAML provider. + const prevUser = userCredential.user; + const emailCredential = + EmailAuthProvider.credential(email, password); + return linkWithCredential(prevUser, emailCredential) + .then((linkResult) => { + // Sign in with the newly linked credential + const linkCredential = SAMLAuthProvider.credentialFromResult(linkResult); + return signInWithCredential(auth, linkCredential); + }) + .then((signInResult) => { + // Handle sign in of merged user + // ... + }); + }) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END multitenant_account_linking_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_create_custom_token.js b/snippets/auth-next/multi-tenancy/multitenant_create_custom_token.js new file mode 100644 index 00000000..1426cf8a --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_create_custom_token.js @@ -0,0 +1,20 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_create_custom_token_modular] +// Ensure you're using a tenant-aware auth instance +const tenantManager = admin.auth().tenantManager(); +const tenantAuth = tenantManager.authForTenant('TENANT_ID1'); + +// Create a custom token in the usual manner +tenantAuth.createCustomToken(uid) + .then((customToken) => { + // Send token back to client + }) + .catch((error) => { + console.log('Error creating custom token:', error); + }); +// [END multitenant_create_custom_token_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_send_emaillink.js b/snippets/auth-next/multi-tenancy/multitenant_send_emaillink.js new file mode 100644 index 00000000..4c4d95c5 --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_send_emaillink.js @@ -0,0 +1,23 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_send_emaillink_modular] +import { sendSignInLinkToEmail } from "firebase/auth"; +// Switch to TENANT_ID1 +auth.tenantId = 'TENANT_ID1'; + +sendSignInLinkToEmail(auth, email, actionCodeSettings) + .then(() => { + // The link was successfully sent. Inform the user. + // Save the email locally so you don't need to ask the user for it again + // if they open the link on the same device. + window.localStorage.setItem('emailForSignIn', email); + }) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END multitenant_send_emaillink_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_set_tenant.js b/snippets/auth-next/multi-tenancy/multitenant_set_tenant.js new file mode 100644 index 00000000..9510bc5e --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_set_tenant.js @@ -0,0 +1,12 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_set_tenant_modular] +import { getAuth } from "firebase/auth"; +const auth = getAuth(); +const tenantId = "TENANT_ID1"; +auth.tenantId = tenantId; +// [END multitenant_set_tenant_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_signin_custom_token.js b/snippets/auth-next/multi-tenancy/multitenant_signin_custom_token.js new file mode 100644 index 00000000..b9fa9c58 --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_signin_custom_token.js @@ -0,0 +1,16 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_signin_custom_token_modular] +import { signInWithCustomToken } from "firebase/auth"; +auth.tenantId = 'TENANT_ID1'; + +signInWithCustomToken(auth, token) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END multitenant_signin_custom_token_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_signin_emaillink.js b/snippets/auth-next/multi-tenancy/multitenant_signin_emaillink.js new file mode 100644 index 00000000..0032af1c --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_signin_emaillink.js @@ -0,0 +1,29 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_signin_emaillink_modular] +import { isSignInWithEmailLink, parseActionCodeURL, signInWithEmailLink } from "firebase/auth"; +if (isSignInWithEmailLink(auth, window.location.href)) { + const actionCodeUrl = parseActionCodeURL(window.location.href); + if (actionCodeUrl.tenantId) { + auth.tenantId = actionCodeUrl.tenantId; + } + let email = window.localStorage.getItem('emailForSignIn'); + if (!email) { + // User opened the link on a different device. To prevent session fixation + // attacks, ask the user to provide the associated email again. For example: + email = window.prompt('Please provide your email for confirmation'); + } + // The client SDK will parse the code from the link for you. + signInWithEmailLink(auth, email, window.location.href) + .then((result) => { + // User is signed in. + // tenant ID available in result.user.tenantId. + // Clear email from storage. + window.localStorage.removeItem('emailForSignIn'); + }); +} +// [END multitenant_signin_emaillink_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_signin_password.js b/snippets/auth-next/multi-tenancy/multitenant_signin_password.js new file mode 100644 index 00000000..73642a8d --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_signin_password.js @@ -0,0 +1,19 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_signin_password_modular] +import { signInWithEmailAndPassword } from "firebase/auth"; +auth.tenantId = 'TENANT_ID'; + +signInWithEmailAndPassword(auth, email, password) + .then((userCredential) => { + // User is signed in. + // userCredential.user.tenantId is 'TENANT_ID'. + }).catch((error) => { + // Handle / display error. + // ... + }); +// [END multitenant_signin_password_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_signin_password_demo.js b/snippets/auth-next/multi-tenancy/multitenant_signin_password_demo.js new file mode 100644 index 00000000..87882773 --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_signin_password_demo.js @@ -0,0 +1,33 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_signin_password_demo_modular] +import { signInWithEmailAndPassword, onAuthStateChanged } from "firebase/auth"; +// Switch to TENANT_ID1 +auth.tenantId = 'TENANT_ID1'; + +// Sign in with tenant +signInWithEmailAndPassword(auth, email, password) + .then((userCredential) => { + // User is signed in. + const user = userCredential.user; + // user.tenantId is set to 'TENANT_ID1'. + // Switch to 'TENANT_ID2'. + auth.tenantId = 'TENANT_ID2'; + // auth.currentUser still points to the user. + // auth.currentUser.tenantId is 'TENANT_ID1'. + }); + +// You could also get the current user from Auth state observer. +onAuthStateChanged(auth, (user) => { + if (user) { + // User is signed in. + // user.tenantId is set to 'TENANT_ID1'. + } else { + // No user is signed in. + } +}); +// [END multitenant_signin_password_demo_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_signin_saml_popup.js b/snippets/auth-next/multi-tenancy/multitenant_signin_saml_popup.js new file mode 100644 index 00000000..6aa90550 --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_signin_saml_popup.js @@ -0,0 +1,25 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_signin_saml_popup_modular] +import { signInWithPopup } from "firebase/auth"; +// Switch to TENANT_ID1. +auth.tenantId = 'TENANT_ID1'; + +// Sign-in with popup. +signInWithPopup(auth, provider) + .then((userCredential) => { + // User is signed in. + const user = userCredential.user; + // user.tenantId is set to 'TENANT_ID1'. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END multitenant_signin_saml_popup_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_signin_saml_redirect.js b/snippets/auth-next/multi-tenancy/multitenant_signin_saml_redirect.js new file mode 100644 index 00000000..d3552a56 --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_signin_saml_redirect.js @@ -0,0 +1,29 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_signin_saml_redirect_modular] +import { signInWithRedirect, getRedirectResult } from "firebase/auth"; +// Switch to TENANT_ID1. +auth.tenantId = 'TENANT_ID1'; + +// Sign-in with redirect. +signInWithRedirect(auth, provider); + +// After the user completes sign-in and returns to the app, you can get +// the sign-in result by calling getRedirectResult. However, if they sign out +// and sign in again with an IdP, no tenant is used. +getRedirectResult(auth) + .then((result) => { + // User is signed in. + // The tenant ID available in result.user.tenantId. + // Provider data available from the result.user.getIdToken() + // or from result.user.providerData + }) + .catch((error) => { + // Handle / display error. + // ... + }); +// [END multitenant_signin_saml_redirect_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_signup_password.js b/snippets/auth-next/multi-tenancy/multitenant_signup_password.js new file mode 100644 index 00000000..d89d5edf --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_signup_password.js @@ -0,0 +1,19 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_signup_password_modular] +import { createUserWithEmailAndPassword } from "firebase/auth"; +auth.tenantId = 'TENANT_ID'; + +createUserWithEmailAndPassword(auth, email, password) + .then((userCredential) => { + // User is signed in. + // userCredential.user.tenantId is 'TENANT_ID'. + }).catch((error) => { + // Handle / display error. + // ... + }); +// [END multitenant_signup_password_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_switch_tenant.js b/snippets/auth-next/multi-tenancy/multitenant_switch_tenant.js new file mode 100644 index 00000000..455e4e3b --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_switch_tenant.js @@ -0,0 +1,15 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_switch_tenant_modular] +// One Auth instance +// Switch to tenant1 +auth.tenantId = "TENANT_ID1"; +// Switch to tenant2 +auth.tenantId = "TENANT_ID2"; +// Switch back to project level IdPs +auth.tenantId = null; +// [END multitenant_switch_tenant_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_switch_tenant_multiinstance.js b/snippets/auth-next/multi-tenancy/multitenant_switch_tenant_multiinstance.js new file mode 100644 index 00000000..72550493 --- /dev/null +++ b/snippets/auth-next/multi-tenancy/multitenant_switch_tenant_multiinstance.js @@ -0,0 +1,19 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/multi-tenancy.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START multitenant_switch_tenant_multiinstance_modular] +// Multiple Auth instances +import { initializeApp } from "firebase/app"; +import { getAuth } from "firebase/auth"; +const firebaseApp1 = initializeApp(firebaseConfig1, 'app1_for_tenantId1'); +const firebaseApp2 = initializeApp(firebaseConfig2, 'app2_for_tenantId2'); + +const auth1 = getAuth(firebaseApp1); +const auth2 = getAuth(firebaseApp2); + +auth1.tenantId = "TENANT_ID1"; +auth2.tenantId = "TENANT_ID2"; +// [END multitenant_switch_tenant_multiinstance_modular] \ No newline at end of file From 1c4c6834f310bf53a98b3fa3c2e2191396cacd69 Mon Sep 17 00:00:00 2001 From: Ian Tay Date: Thu, 21 Oct 2021 10:38:57 -0700 Subject: [PATCH 04/38] add provider_credential snippets for the social Idps that don't have it. (#253) --- auth-next/facebook.js | 9 +++++++++ auth-next/google-signin.js | 9 +++++++++ auth-next/twitter.js | 7 +++++++ auth/facebook.js | 6 ++++++ auth/google-signin.js | 6 ++++++ auth/initialization.txt | 9 +++++++++ auth/multi-tenancy.js | 2 +- auth/twitter.js | 6 ++++++ .../facebook/auth_facebook_provider_credential.js | 11 +++++++++++ .../google-signin/auth_google_provider_credential.js | 11 +++++++++++ .../twitter/auth_twitter_provider_credential.js | 11 +++++++++++ 11 files changed, 86 insertions(+), 1 deletion(-) create mode 100644 auth/initialization.txt create mode 100644 snippets/auth-next/facebook/auth_facebook_provider_credential.js create mode 100644 snippets/auth-next/google-signin/auth_google_provider_credential.js create mode 100644 snippets/auth-next/twitter/auth_twitter_provider_credential.js diff --git a/auth-next/facebook.js b/auth-next/facebook.js index 4b61f4be..90414d7e 100644 --- a/auth-next/facebook.js +++ b/auth-next/facebook.js @@ -163,3 +163,12 @@ function authWithCredential(credential) { }); // [END auth_facebook_signin_credential] } + +function facebookProviderCredential(accessToken) { + // [START auth_facebook_provider_credential] + const { FacebookAuthProvider } = require("firebase/auth"); + + const credential = FacebookAuthProvider.credential(accessToken); + // [END auth_facebook_provider_credential] +} + diff --git a/auth-next/google-signin.js b/auth-next/google-signin.js index 78b79a61..1e1cee59 100644 --- a/auth-next/google-signin.js +++ b/auth-next/google-signin.js @@ -157,4 +157,13 @@ function isUserEqual_wrapper() { // [END auth_google_checksameuser] } +function googleProviderCredential(idToken) { + // [START auth_google_provider_credential] + const { GoogleAuthProvider } = require("firebase/auth"); + + const credential = GoogleAuthProvider.credential(idToken); + // [END auth_google_provider_credential] +} + + diff --git a/auth-next/twitter.js b/auth-next/twitter.js index 8024bbe5..57416b03 100644 --- a/auth-next/twitter.js +++ b/auth-next/twitter.js @@ -73,3 +73,10 @@ function twitterSignInRedirectResult() { // [END auth_twitter_signin_redirect_result] } +function twitterProviderCredential(accessToken, secret) { + // [START auth_twitter_provider_credential] + const { TwitterAuthProvider } = require("firebase/auth"); + + const credential = TwitterAuthProvider.credential(accessToken, secret); + // [END auth_twitter_provider_credential] +} \ No newline at end of file diff --git a/auth/facebook.js b/auth/facebook.js index 3e5c5b14..4259960d 100644 --- a/auth/facebook.js +++ b/auth/facebook.js @@ -151,3 +151,9 @@ function authWithCredential(credential) { }); // [END auth_facebook_signin_credential] } + +function facebookProviderCredential(accessToken) { + // [START auth_facebook_provider_credential] + var credential = firebase.auth.FacebookAuthProvider.credential(accessToken); + // [END auth_facebook_provider_credential] +} diff --git a/auth/google-signin.js b/auth/google-signin.js index 908a32e1..fcc32dc8 100644 --- a/auth/google-signin.js +++ b/auth/google-signin.js @@ -142,3 +142,9 @@ function isUserEqual(googleUser, firebaseUser) { return false; } // [END auth_google_checksameuser] + +function googleProviderCredential(idToken) { + // [START auth_google_provider_credential] + var credential = firebase.auth.GoogleAuthProvider.credential(idToken); + // [END auth_google_provider_credential] +} diff --git a/auth/initialization.txt b/auth/initialization.txt new file mode 100644 index 00000000..bccb0571 --- /dev/null +++ b/auth/initialization.txt @@ -0,0 +1,9 @@ + + \ No newline at end of file diff --git a/auth/multi-tenancy.js b/auth/multi-tenancy.js index 8afc1a5c..8b31e145 100644 --- a/auth/multi-tenancy.js +++ b/auth/multi-tenancy.js @@ -23,7 +23,7 @@ function switchTenantSingleAuth() { // [END multitenant_switch_tenant] } -function switchTenantMultiAuthInstance(config) { +function switchTenantMultiAuth(config) { // [START multitenant_switch_tenant_multiinstance] // Multiple Auth instances firebase.initializeApp(config, 'app1_for_tenantId1'); diff --git a/auth/twitter.js b/auth/twitter.js index b1ca2581..a78370b7 100644 --- a/auth/twitter.js +++ b/auth/twitter.js @@ -76,3 +76,9 @@ function twitterSignInRedirectResult() { }); // [END auth_twitter_signin_redirect_result] } + +function twitterProviderCredential(accessToken, secret) { + // [START auth_twitter_provider_credential] + var credential = firebase.auth.TwitterAuthProvider.credential(accessToken, secret); + // [END auth_twitter_provider_credential] +} \ No newline at end of file diff --git a/snippets/auth-next/facebook/auth_facebook_provider_credential.js b/snippets/auth-next/facebook/auth_facebook_provider_credential.js new file mode 100644 index 00000000..b7bbca25 --- /dev/null +++ b/snippets/auth-next/facebook/auth_facebook_provider_credential.js @@ -0,0 +1,11 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/facebook.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_facebook_provider_credential_modular] +import { FacebookAuthProvider } from "firebase/auth"; + +const credential = FacebookAuthProvider.credential(accessToken); +// [END auth_facebook_provider_credential_modular] \ No newline at end of file diff --git a/snippets/auth-next/google-signin/auth_google_provider_credential.js b/snippets/auth-next/google-signin/auth_google_provider_credential.js new file mode 100644 index 00000000..924aa167 --- /dev/null +++ b/snippets/auth-next/google-signin/auth_google_provider_credential.js @@ -0,0 +1,11 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/google-signin.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_google_provider_credential_modular] +import { GoogleAuthProvider } from "firebase/auth"; + +const credential = GoogleAuthProvider.credential(idToken); +// [END auth_google_provider_credential_modular] \ No newline at end of file diff --git a/snippets/auth-next/twitter/auth_twitter_provider_credential.js b/snippets/auth-next/twitter/auth_twitter_provider_credential.js new file mode 100644 index 00000000..e25b369c --- /dev/null +++ b/snippets/auth-next/twitter/auth_twitter_provider_credential.js @@ -0,0 +1,11 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/twitter.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START auth_twitter_provider_credential_modular] +import { TwitterAuthProvider } from "firebase/auth"; + +const credential = TwitterAuthProvider.credential(accessToken, secret); +// [END auth_twitter_provider_credential_modular] \ No newline at end of file From 509769a817d7437616bcfcb816f783b29aaca843 Mon Sep 17 00:00:00 2001 From: Ersin Ertan <4809853+ersin-ertan@users.noreply.github.com> Date: Fri, 21 Jan 2022 16:18:29 -0500 Subject: [PATCH 05/38] Update method in comment for getting the id token (#262) Sources - https://github.com/firebase/firebase-js-sdk/blob/master/packages/auth/src/model/user.ts#L85 - https://firebase.google.com/docs/reference/js/v8/firebase.User#getidtoken - https://firebase.google.com/docs/reference/js/auth.user.md#usergetidtoken - https://firebase.google.com/docs/auth/web/manage-users#get_a_users_profile --- auth/manage.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/auth/manage.js b/auth/manage.js index 7163ef00..217199f2 100644 --- a/auth/manage.js +++ b/auth/manage.js @@ -16,7 +16,7 @@ function getUserProfile() { // The user's ID, unique to the Firebase project. Do NOT use // this value to authenticate with your backend server, if - // you have one. Use User.getToken() instead. + // you have one. Use User.getIdToken() instead. const uid = user.uid; } // [END auth_get_user_profile] From 9bdf357b4b667c71b0914f4af9fa6210b4a953d5 Mon Sep 17 00:00:00 2001 From: Yarego Brozek <78966160+devkiloton@users.noreply.github.com> Date: Thu, 21 Apr 2022 11:31:19 -0300 Subject: [PATCH 06/38] adding missing code in a snippet (#288) --- database-next/read-and-write.js | 2 +- .../database-next/read-and-write/rtdb_social_write_fan_out.js | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/database-next/read-and-write.js b/database-next/read-and-write.js index 2cbd5c5b..4196c0d7 100644 --- a/database-next/read-and-write.js +++ b/database-next/read-and-write.js @@ -74,9 +74,9 @@ function socialSingleValueRead() { } function writeNewPost_wrapped() { + // [START rtdb_social_write_fan_out] const { getDatabase, ref, child, push, update } = require("firebase/database"); - // [START rtdb_social_write_fan_out] function writeNewPost(uid, username, picture, title, body) { const db = getDatabase(); diff --git a/snippets/database-next/read-and-write/rtdb_social_write_fan_out.js b/snippets/database-next/read-and-write/rtdb_social_write_fan_out.js index f787d4bd..783eca2b 100644 --- a/snippets/database-next/read-and-write/rtdb_social_write_fan_out.js +++ b/snippets/database-next/read-and-write/rtdb_social_write_fan_out.js @@ -5,6 +5,8 @@ // 'npm run snippets'. // [START rtdb_social_write_fan_out_modular] +import { getDatabase, ref, child, push, update } from "firebase/database"; + function writeNewPost(uid, username, picture, title, body) { const db = getDatabase(); From 69c85abdc7cd6990618720cd33aa0d1ee357c652 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ros=C3=A1rio=20Pereira=20Fernandes?= Date: Thu, 19 May 2022 13:37:24 +0100 Subject: [PATCH 07/38] fix error handling on v9 auth snippets (#289) --- auth-next/apple.js | 6 +++--- auth-next/facebook.js | 8 ++++---- auth-next/github.js | 4 ++-- auth-next/google-signin.js | 8 ++++---- auth-next/index.js | 2 +- auth-next/multi-tenancy.js | 4 ++-- auth-next/oidc.js | 6 +++--- auth-next/saml.js | 4 ++-- auth-next/twitter.js | 4 ++-- .../auth-next/apple/auth_apple_reauthenticate_popup.js | 2 +- snippets/auth-next/apple/auth_apple_signin_popup.js | 2 +- .../auth-next/apple/auth_apple_signin_redirect_result.js | 2 +- snippets/auth-next/facebook/auth_facebook_callback.js | 2 +- .../auth-next/facebook/auth_facebook_signin_credential.js | 2 +- snippets/auth-next/facebook/auth_facebook_signin_popup.js | 2 +- .../facebook/auth_facebook_signin_redirect_result.js | 2 +- snippets/auth-next/github/auth_github_signin_popup.js | 2 +- .../github/auth_github_signin_redirect_result.js | 2 +- .../auth-next/google-signin/auth_google_build_signin.js | 2 +- snippets/auth-next/google-signin/auth_google_callback.js | 2 +- .../google-signin/auth_google_signin_credential.js | 2 +- .../auth-next/google-signin/auth_google_signin_popup.js | 2 +- .../google-signin/auth_google_signin_redirect_result.js | 2 +- snippets/auth-next/index/auth_signin_credential.js | 2 +- .../multi-tenancy/multitenant_account_exists_popup.js | 2 +- .../multi-tenancy/multitenant_account_exists_redirect.js | 2 +- snippets/auth-next/oidc/auth_oidc_direct_sign_in.js | 2 +- snippets/auth-next/oidc/auth_oidc_signin_popup.js | 2 +- .../auth-next/oidc/auth_oidc_signin_redirect_result.js | 2 +- snippets/auth-next/saml/auth_saml_signin_popup.js | 2 +- .../auth-next/saml/auth_saml_signin_redirect_result.js | 2 +- snippets/auth-next/twitter/auth_twitter_signin_popup.js | 2 +- .../twitter/auth_twitter_signin_redirect_result.js | 2 +- 33 files changed, 47 insertions(+), 47 deletions(-) diff --git a/auth-next/apple.js b/auth-next/apple.js index 29a33dea..7cffca8b 100644 --- a/auth-next/apple.js +++ b/auth-next/apple.js @@ -45,7 +45,7 @@ function appleSignInPopup(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = OAuthProvider.credentialFromError(error); @@ -85,7 +85,7 @@ function appleSignInRedirectResult() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = OAuthProvider.credentialFromError(error); @@ -123,7 +123,7 @@ function appleReauthenticatePopup() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = OAuthProvider.credentialFromError(error); diff --git a/auth-next/facebook.js b/auth-next/facebook.js index 90414d7e..67b397f2 100644 --- a/auth-next/facebook.js +++ b/auth-next/facebook.js @@ -40,7 +40,7 @@ function facebookSignInPopup(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); @@ -66,7 +66,7 @@ function facebookSignInRedirectResult() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); // ... @@ -102,7 +102,7 @@ function checkLoginState_wrapper() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); // ... @@ -156,7 +156,7 @@ function authWithCredential(credential) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); // ... diff --git a/auth-next/github.js b/auth-next/github.js index 941a9047..babfd1ee 100644 --- a/auth-next/github.js +++ b/auth-next/github.js @@ -46,7 +46,7 @@ function githubSignInPopup(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GithubAuthProvider.credentialFromError(error); // ... @@ -75,7 +75,7 @@ function githubSignInRedirectResult() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GithubAuthProvider.credentialFromError(error); // ... diff --git a/auth-next/google-signin.js b/auth-next/google-signin.js index 1e1cee59..136c26b5 100644 --- a/auth-next/google-signin.js +++ b/auth-next/google-signin.js @@ -39,7 +39,7 @@ function googleSignInPopup(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... @@ -65,7 +65,7 @@ function googleSignInRedirectResult() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... @@ -87,7 +87,7 @@ function googleBuildAndSignIn(id_token) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... @@ -123,7 +123,7 @@ function onSignIn_wrapper() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... diff --git a/auth-next/index.js b/auth-next/index.js index c4dadfe0..b4a17903 100644 --- a/auth-next/index.js +++ b/auth-next/index.js @@ -107,7 +107,7 @@ function authWithCredential(credential) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // ... }); // [END auth_signin_credential] diff --git a/auth-next/multi-tenancy.js b/auth-next/multi-tenancy.js index c0c86662..d7577f34 100644 --- a/auth-next/multi-tenancy.js +++ b/auth-next/multi-tenancy.js @@ -273,7 +273,7 @@ function accountExistsPopupTenant(auth, samlProvider, googleProvider, goToApp) { const pendingCred = error.credential; // The credential's tenantId if needed: error.tenantId // The provider account's email address. - const email = error.email; + const email = error.customData.email; // Get sign-in methods for this email. fetchSignInMethodsForEmail(email, auth) .then((methods) => { @@ -315,7 +315,7 @@ function accountExistsRedirectTenant(auth, samlProvider, googleProvider, goToApp // The pending SAML credential. pendingCred = error.credential; // The provider account's email address. - const email = error.email; + const email = error.customData.email; // Need to set the tenant ID again as the page was reloaded and the // previous setting was reset. auth.tenantId = tenantId; diff --git a/auth-next/oidc.js b/auth-next/oidc.js index 5dc20e81..dae69fe9 100644 --- a/auth-next/oidc.js +++ b/auth-next/oidc.js @@ -24,7 +24,7 @@ function oidcSignInPopup(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = OAuthProvider.credentialFromError(error); // Handle / display error. @@ -58,7 +58,7 @@ function oidcSignInRedirectResult(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = OAuthProvider.credentialFromError(error); // Handle / display error. @@ -86,7 +86,7 @@ function oidcDirectSignIn(provider, oidcIdToken) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = OAuthProvider.credentialFromError(error); // Handle / display error. diff --git a/auth-next/saml.js b/auth-next/saml.js index 9a5683d9..cdecce56 100644 --- a/auth-next/saml.js +++ b/auth-next/saml.js @@ -24,7 +24,7 @@ function samlSignInPopup(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = SAMLAuthProvider.credentialFromError(error); // Handle / display error. @@ -58,7 +58,7 @@ function samlSignInRedirectResult(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = SAMLAuthProvider.credentialFromError(error); // Handle / display error. diff --git a/auth-next/twitter.js b/auth-next/twitter.js index 57416b03..a386e4ab 100644 --- a/auth-next/twitter.js +++ b/auth-next/twitter.js @@ -36,7 +36,7 @@ function twitterSignInPopup(provider) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = TwitterAuthProvider.credentialFromError(error); // ... @@ -65,7 +65,7 @@ function twitterSignInRedirectResult() { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = TwitterAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/apple/auth_apple_reauthenticate_popup.js b/snippets/auth-next/apple/auth_apple_reauthenticate_popup.js index 129fe920..cd40151d 100644 --- a/snippets/auth-next/apple/auth_apple_reauthenticate_popup.js +++ b/snippets/auth-next/apple/auth_apple_reauthenticate_popup.js @@ -32,7 +32,7 @@ reauthenticateWithPopup(auth.currentUser, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = OAuthProvider.credentialFromError(error); diff --git a/snippets/auth-next/apple/auth_apple_signin_popup.js b/snippets/auth-next/apple/auth_apple_signin_popup.js index 2db09607..c2a392cf 100644 --- a/snippets/auth-next/apple/auth_apple_signin_popup.js +++ b/snippets/auth-next/apple/auth_apple_signin_popup.js @@ -25,7 +25,7 @@ signInWithPopup(auth, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = OAuthProvider.credentialFromError(error); diff --git a/snippets/auth-next/apple/auth_apple_signin_redirect_result.js b/snippets/auth-next/apple/auth_apple_signin_redirect_result.js index 68dba4ab..654f95e5 100644 --- a/snippets/auth-next/apple/auth_apple_signin_redirect_result.js +++ b/snippets/auth-next/apple/auth_apple_signin_redirect_result.js @@ -25,7 +25,7 @@ getRedirectResult(auth) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = OAuthProvider.credentialFromError(error); diff --git a/snippets/auth-next/facebook/auth_facebook_callback.js b/snippets/auth-next/facebook/auth_facebook_callback.js index 8596bb68..63106871 100644 --- a/snippets/auth-next/facebook/auth_facebook_callback.js +++ b/snippets/auth-next/facebook/auth_facebook_callback.js @@ -26,7 +26,7 @@ function checkLoginState(response) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/facebook/auth_facebook_signin_credential.js b/snippets/auth-next/facebook/auth_facebook_signin_credential.js index dcd42c7e..3b784f24 100644 --- a/snippets/auth-next/facebook/auth_facebook_signin_credential.js +++ b/snippets/auth-next/facebook/auth_facebook_signin_credential.js @@ -19,7 +19,7 @@ signInWithCredential(auth, credential) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/facebook/auth_facebook_signin_popup.js b/snippets/auth-next/facebook/auth_facebook_signin_popup.js index 2bc014ed..7d35aaf2 100644 --- a/snippets/auth-next/facebook/auth_facebook_signin_popup.js +++ b/snippets/auth-next/facebook/auth_facebook_signin_popup.js @@ -24,7 +24,7 @@ signInWithPopup(auth, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); diff --git a/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js b/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js index 49f3a494..eb6cdb30 100644 --- a/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js +++ b/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js @@ -20,7 +20,7 @@ getRedirectResult(auth) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // AuthCredential type that was used. const credential = FacebookAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/github/auth_github_signin_popup.js b/snippets/auth-next/github/auth_github_signin_popup.js index 74e76cc9..e1b4768e 100644 --- a/snippets/auth-next/github/auth_github_signin_popup.js +++ b/snippets/auth-next/github/auth_github_signin_popup.js @@ -22,7 +22,7 @@ signInWithPopup(auth, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GithubAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/github/auth_github_signin_redirect_result.js b/snippets/auth-next/github/auth_github_signin_redirect_result.js index 6147d9de..b3d31d0a 100644 --- a/snippets/auth-next/github/auth_github_signin_redirect_result.js +++ b/snippets/auth-next/github/auth_github_signin_redirect_result.js @@ -24,7 +24,7 @@ getRedirectResult(auth) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GithubAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/google-signin/auth_google_build_signin.js b/snippets/auth-next/google-signin/auth_google_build_signin.js index 6df84e3e..98f35eb2 100644 --- a/snippets/auth-next/google-signin/auth_google_build_signin.js +++ b/snippets/auth-next/google-signin/auth_google_build_signin.js @@ -17,7 +17,7 @@ signInWithCredential(auth, credential).catch((error) => { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/google-signin/auth_google_callback.js b/snippets/auth-next/google-signin/auth_google_callback.js index 27aa8dc6..873778dd 100644 --- a/snippets/auth-next/google-signin/auth_google_callback.js +++ b/snippets/auth-next/google-signin/auth_google_callback.js @@ -25,7 +25,7 @@ function onSignIn(googleUser) { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/google-signin/auth_google_signin_credential.js b/snippets/auth-next/google-signin/auth_google_signin_credential.js index a3a8808e..25c6f3ba 100644 --- a/snippets/auth-next/google-signin/auth_google_signin_credential.js +++ b/snippets/auth-next/google-signin/auth_google_signin_credential.js @@ -10,7 +10,7 @@ signInWithCredential(auth, credential).catch((error) => { const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The credential that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/google-signin/auth_google_signin_popup.js b/snippets/auth-next/google-signin/auth_google_signin_popup.js index 55c46488..d6c70eb9 100644 --- a/snippets/auth-next/google-signin/auth_google_signin_popup.js +++ b/snippets/auth-next/google-signin/auth_google_signin_popup.js @@ -21,7 +21,7 @@ signInWithPopup(auth, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js b/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js index a64977bb..50c4aded 100644 --- a/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js +++ b/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js @@ -21,7 +21,7 @@ getRedirectResult(auth) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = GoogleAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/index/auth_signin_credential.js b/snippets/auth-next/index/auth_signin_credential.js index ba2db6b8..c2b027a3 100644 --- a/snippets/auth-next/index/auth_signin_credential.js +++ b/snippets/auth-next/index/auth_signin_credential.js @@ -19,7 +19,7 @@ signInWithCredential(auth, credential) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // ... }); // [END auth_signin_credential_modular] \ No newline at end of file diff --git a/snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js b/snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js index 43734616..7bf33262 100644 --- a/snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js +++ b/snippets/auth-next/multi-tenancy/multitenant_account_exists_popup.js @@ -19,7 +19,7 @@ signInWithPopup(auth, samlProvider) const pendingCred = error.credential; // The credential's tenantId if needed: error.tenantId // The provider account's email address. - const email = error.email; + const email = error.customData.email; // Get sign-in methods for this email. fetchSignInMethodsForEmail(email, auth) .then((methods) => { diff --git a/snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js b/snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js index f8a3942d..a81617dd 100644 --- a/snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js +++ b/snippets/auth-next/multi-tenancy/multitenant_account_exists_redirect.js @@ -20,7 +20,7 @@ getRedirectResult(auth).catch((error) => { // The pending SAML credential. pendingCred = error.credential; // The provider account's email address. - const email = error.email; + const email = error.customData.email; // Need to set the tenant ID again as the page was reloaded and the // previous setting was reset. auth.tenantId = tenantId; diff --git a/snippets/auth-next/oidc/auth_oidc_direct_sign_in.js b/snippets/auth-next/oidc/auth_oidc_direct_sign_in.js index 65f693a6..558fd915 100644 --- a/snippets/auth-next/oidc/auth_oidc_direct_sign_in.js +++ b/snippets/auth-next/oidc/auth_oidc_direct_sign_in.js @@ -22,7 +22,7 @@ signInWithCredential(auth, credential) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = OAuthProvider.credentialFromError(error); // Handle / display error. diff --git a/snippets/auth-next/oidc/auth_oidc_signin_popup.js b/snippets/auth-next/oidc/auth_oidc_signin_popup.js index 76b01b1d..130d617e 100644 --- a/snippets/auth-next/oidc/auth_oidc_signin_popup.js +++ b/snippets/auth-next/oidc/auth_oidc_signin_popup.js @@ -18,7 +18,7 @@ signInWithPopup(auth, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = OAuthProvider.credentialFromError(error); // Handle / display error. diff --git a/snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js b/snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js index ae5a441d..bc76a620 100644 --- a/snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js +++ b/snippets/auth-next/oidc/auth_oidc_signin_redirect_result.js @@ -19,7 +19,7 @@ getRedirectResult(auth) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = OAuthProvider.credentialFromError(error); // Handle / display error. diff --git a/snippets/auth-next/saml/auth_saml_signin_popup.js b/snippets/auth-next/saml/auth_saml_signin_popup.js index 8010a17b..3a922a9a 100644 --- a/snippets/auth-next/saml/auth_saml_signin_popup.js +++ b/snippets/auth-next/saml/auth_saml_signin_popup.js @@ -18,7 +18,7 @@ signInWithPopup(auth, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = SAMLAuthProvider.credentialFromError(error); // Handle / display error. diff --git a/snippets/auth-next/saml/auth_saml_signin_redirect_result.js b/snippets/auth-next/saml/auth_saml_signin_redirect_result.js index 4e4d4260..e4bf73de 100644 --- a/snippets/auth-next/saml/auth_saml_signin_redirect_result.js +++ b/snippets/auth-next/saml/auth_saml_signin_redirect_result.js @@ -19,7 +19,7 @@ getRedirectResult(auth) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = SAMLAuthProvider.credentialFromError(error); // Handle / display error. diff --git a/snippets/auth-next/twitter/auth_twitter_signin_popup.js b/snippets/auth-next/twitter/auth_twitter_signin_popup.js index a5fb5a95..ae8e2007 100644 --- a/snippets/auth-next/twitter/auth_twitter_signin_popup.js +++ b/snippets/auth-next/twitter/auth_twitter_signin_popup.js @@ -24,7 +24,7 @@ signInWithPopup(auth, provider) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = TwitterAuthProvider.credentialFromError(error); // ... diff --git a/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js b/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js index 53b42c85..73e42bab 100644 --- a/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js +++ b/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js @@ -24,7 +24,7 @@ getRedirectResult(auth) const errorCode = error.code; const errorMessage = error.message; // The email of the user's account used. - const email = error.email; + const email = error.customData.email; // The AuthCredential type that was used. const credential = TwitterAuthProvider.credentialFromError(error); // ... From 2b97722e03d0276347523590ae8f6588ca5cf79b Mon Sep 17 00:00:00 2001 From: Frank van Puffelen Date: Fri, 10 Jun 2022 04:18:10 -0700 Subject: [PATCH 08/38] Fix nesting issue in collection group query sample (#280) --- firestore-next/test.firestore.js | 22 +++++++++---------- .../fs_collection_group_query_data_setup.js | 22 +++++++++---------- 2 files changed, 22 insertions(+), 22 deletions(-) diff --git a/firestore-next/test.firestore.js b/firestore-next/test.firestore.js index 71c54b95..59ab267b 100644 --- a/firestore-next/test.firestore.js +++ b/firestore-next/test.firestore.js @@ -1095,48 +1095,48 @@ describe("firestore", () => { describe('collectionGroup(landmarks)', () => { it("should setup example data", async () => { // [START fs_collection_group_query_data_setup] - const { collection, doc, setDoc } = require("firebase/firestore"); + const { collection, addDoc } = require("firebase/firestore"); const citiesRef = collection(db, 'cities'); await Promise.all([ - setDoc(doc(citiesRef, 'SF', 'landmarks'), { + addDoc(collection(citiesRef, 'SF', 'landmarks'), { name: 'Golden Gate Bridge', type: 'bridge' }), - setDoc(doc(citiesRef, 'SF', 'landmarks'), { + addDoc(collection(citiesRef, 'SF', 'landmarks'), { name: 'Legion of Honor', type: 'museum' }), - setDoc(doc(citiesRef, 'LA', 'landmarks'), { + addDoc(collection(citiesRef, 'LA', 'landmarks'), { name: 'Griffith Park', type: 'park' }), - setDoc(doc(citiesRef, 'LA', 'landmarks'), { + addDoc(collection(citiesRef, 'LA', 'landmarks'), { name: 'The Getty', type: 'museum' }), - setDoc(doc(citiesRef, 'DC', 'landmarks'), { + addDoc(collection(citiesRef, 'DC', 'landmarks'), { name: 'Lincoln Memorial', type: 'memorial' }), - setDoc(doc(citiesRef, 'DC', 'landmarks'), { + addDoc(collection(citiesRef, 'DC', 'landmarks'), { name: 'National Air and Space Museum', type: 'museum' }), - setDoc(doc(citiesRef, 'TOK', 'landmarks'), { + addDoc(collection(citiesRef, 'TOK', 'landmarks'), { name: 'Ueno Park', type: 'park' }), - setDoc(doc(citiesRef, 'TOK', 'landmarks'), { + addDoc(collection(citiesRef, 'TOK', 'landmarks'), { name: 'National Museum of Nature and Science', type: 'museum' }), - setDoc(doc(citiesRef, 'BJ', 'landmarks'), { + addDoc(collection(citiesRef, 'BJ', 'landmarks'), { name: 'Jingshan Park', type: 'park' }), - setDoc(doc(citiesRef, 'BJ', 'landmarks'), { + addDoc(collection(citiesRef, 'BJ', 'landmarks'), { name: 'Beijing Ancient Observatory', type: 'museum' }) diff --git a/snippets/firestore-next/test-firestore/fs_collection_group_query_data_setup.js b/snippets/firestore-next/test-firestore/fs_collection_group_query_data_setup.js index f4f62178..f06ea0f8 100644 --- a/snippets/firestore-next/test-firestore/fs_collection_group_query_data_setup.js +++ b/snippets/firestore-next/test-firestore/fs_collection_group_query_data_setup.js @@ -5,48 +5,48 @@ // 'npm run snippets'. // [START fs_collection_group_query_data_setup_modular] -import { collection, doc, setDoc } from "firebase/firestore"; +import { collection, addDoc } from "firebase/firestore"; const citiesRef = collection(db, 'cities'); await Promise.all([ - setDoc(doc(citiesRef, 'SF', 'landmarks'), { + addDoc(collection(citiesRef, 'SF', 'landmarks'), { name: 'Golden Gate Bridge', type: 'bridge' }), - setDoc(doc(citiesRef, 'SF', 'landmarks'), { + addDoc(collection(citiesRef, 'SF', 'landmarks'), { name: 'Legion of Honor', type: 'museum' }), - setDoc(doc(citiesRef, 'LA', 'landmarks'), { + addDoc(collection(citiesRef, 'LA', 'landmarks'), { name: 'Griffith Park', type: 'park' }), - setDoc(doc(citiesRef, 'LA', 'landmarks'), { + addDoc(collection(citiesRef, 'LA', 'landmarks'), { name: 'The Getty', type: 'museum' }), - setDoc(doc(citiesRef, 'DC', 'landmarks'), { + addDoc(collection(citiesRef, 'DC', 'landmarks'), { name: 'Lincoln Memorial', type: 'memorial' }), - setDoc(doc(citiesRef, 'DC', 'landmarks'), { + addDoc(collection(citiesRef, 'DC', 'landmarks'), { name: 'National Air and Space Museum', type: 'museum' }), - setDoc(doc(citiesRef, 'TOK', 'landmarks'), { + addDoc(collection(citiesRef, 'TOK', 'landmarks'), { name: 'Ueno Park', type: 'park' }), - setDoc(doc(citiesRef, 'TOK', 'landmarks'), { + addDoc(collection(citiesRef, 'TOK', 'landmarks'), { name: 'National Museum of Nature and Science', type: 'museum' }), - setDoc(doc(citiesRef, 'BJ', 'landmarks'), { + addDoc(collection(citiesRef, 'BJ', 'landmarks'), { name: 'Jingshan Park', type: 'park' }), - setDoc(doc(citiesRef, 'BJ', 'landmarks'), { + addDoc(collection(citiesRef, 'BJ', 'landmarks'), { name: 'Beijing Ancient Observatory', type: 'museum' }) From 71c95ee64a0ddc4e2692e0461fc5eb553cff0252 Mon Sep 17 00:00:00 2001 From: CommanderRoot Date: Fri, 10 Jun 2022 13:24:36 +0200 Subject: [PATCH 09/38] refactor: replace deprecated String.prototype.substr() (#281) .substr() is deprecated so we replace it with .slice() which works similarily but isn't deprecated --- auth-next/apple.js | 2 +- auth/apple.js | 2 +- scripts/separate-snippets.ts | 2 +- snippets/auth-next/apple/auth_apple_nonce_node.js | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/auth-next/apple.js b/auth-next/apple.js index 7cffca8b..f9670b4c 100644 --- a/auth-next/apple.js +++ b/auth-next/apple.js @@ -169,7 +169,7 @@ function appleNonceNode() { crypto.randomFillSync(buf); nonce = decoder.write(buf); } - return nonce.substr(0, length); + return nonce.slice(0, length); }; const unhashedNonce = generateNonce(10); diff --git a/auth/apple.js b/auth/apple.js index ad65ef08..e99349c8 100644 --- a/auth/apple.js +++ b/auth/apple.js @@ -170,7 +170,7 @@ function appleNonceNode() { crypto.randomFillSync(buf); nonce = decoder.write(buf); } - return nonce.substr(0, length); + return nonce.slice(0, length); }; const unhashedNonce = generateNonce(10); diff --git a/scripts/separate-snippets.ts b/scripts/separate-snippets.ts index ff93a58f..a888d908 100644 --- a/scripts/separate-snippets.ts +++ b/scripts/separate-snippets.ts @@ -77,7 +77,7 @@ function adjustIndentation(lines: string[]) { if (isBlank(line)) { outputLines.push(""); } else { - outputLines.push(line.substr(minIndent)); + outputLines.push(line.slice(minIndent)); } } return outputLines; diff --git a/snippets/auth-next/apple/auth_apple_nonce_node.js b/snippets/auth-next/apple/auth_apple_nonce_node.js index 26bb2ef0..9dd417a5 100644 --- a/snippets/auth-next/apple/auth_apple_nonce_node.js +++ b/snippets/auth-next/apple/auth_apple_nonce_node.js @@ -17,7 +17,7 @@ const generateNonce = (length) => { crypto.randomFillSync(buf); nonce = decoder.write(buf); } - return nonce.substr(0, length); + return nonce.slice(0, length); }; const unhashedNonce = generateNonce(10); From 01d37b7b0a42e5304d172543b986282d0d61d214 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ros=C3=A1rio=20Pereira=20Fernandes?= Date: Fri, 10 Jun 2022 12:33:42 +0100 Subject: [PATCH 10/38] popuation --> population (#296) --- firestore-next/test.firestore.js | 2 +- snippets/firestore-next/test-firestore/start_doc.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/firestore-next/test.firestore.js b/firestore-next/test.firestore.js index 59ab267b..17ff6d29 100644 --- a/firestore-next/test.firestore.js +++ b/firestore-next/test.firestore.js @@ -1048,7 +1048,7 @@ describe("firestore", () => { const docSnap = await getDoc(doc(citiesRef, "SF")); // Get all cities with a population bigger than San Francisco - const biggerThanSf = query(citiesRef, orderBy("popuation"), startAt(docSnap)); + const biggerThanSf = query(citiesRef, orderBy("population"), startAt(docSnap)); // ... // [END start_doc] }); diff --git a/snippets/firestore-next/test-firestore/start_doc.js b/snippets/firestore-next/test-firestore/start_doc.js index e75c7984..88448fcd 100644 --- a/snippets/firestore-next/test-firestore/start_doc.js +++ b/snippets/firestore-next/test-firestore/start_doc.js @@ -11,6 +11,6 @@ const citiesRef = collection(db, "cities"); const docSnap = await getDoc(doc(citiesRef, "SF")); // Get all cities with a population bigger than San Francisco -const biggerThanSf = query(citiesRef, orderBy("popuation"), startAt(docSnap)); +const biggerThanSf = query(citiesRef, orderBy("population"), startAt(docSnap)); // ... // [END start_doc_modular] \ No newline at end of file From 1a603211c8970d98630f0054761c9ad32620e725 Mon Sep 17 00:00:00 2001 From: Guy Torbet <61030227+Torbet@users.noreply.github.com> Date: Tue, 28 Jun 2022 19:17:23 +0100 Subject: [PATCH 11/38] shoud --> should (#298) "Should Paginate" to "Should paginate" --- firestore/test.firestore.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/firestore/test.firestore.js b/firestore/test.firestore.js index 2aadf8d5..dbf6e18e 100644 --- a/firestore/test.firestore.js +++ b/firestore/test.firestore.js @@ -1011,7 +1011,7 @@ describe("firestore", () => { // [END start_multiple_orderby] }); - it("shoud paginate", () => { + it("should paginate", () => { // [START paginate] var first = db.collection("cities") .orderBy("population") From 5879ad7dedb29c6703bf94f760f6c55073c7c4ac Mon Sep 17 00:00:00 2001 From: Frank van Puffelen Date: Wed, 6 Jul 2022 15:55:52 -0700 Subject: [PATCH 12/38] Fix tiny type (#299) --- auth/manage.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/auth/manage.js b/auth/manage.js index 217199f2..0e1f0e7b 100644 --- a/auth/manage.js +++ b/auth/manage.js @@ -144,7 +144,7 @@ function reauthenticateWithCredential() { user.reauthenticateWithCredential(credential).then(() => { // User re-authenticated. }).catch((error) => { - // An error ocurred + // An error occurred // ... }); // [END auth_reauth_with_credential] From 7403e77cc6b0c9bae8e9cd9d43f58eb93df2241a Mon Sep 17 00:00:00 2001 From: Andrea Wu <1359259+andreaowu@users.noreply.github.com> Date: Thu, 8 Sep 2022 14:24:27 +0200 Subject: [PATCH 13/38] analytics select_content should not have items (#300) --- analytics-next/index.js | 3 +-- snippets/analytics-next/index/analytics_log_event_params.js | 3 +-- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/analytics-next/index.js b/analytics-next/index.js index 510fa758..2b736cde 100644 --- a/analytics-next/index.js +++ b/analytics-next/index.js @@ -27,8 +27,7 @@ function logEventParams() { const analytics = getAnalytics(); logEvent(analytics, 'select_content', { content_type: 'image', - content_id: 'P12453', - items: [{ name: 'Kittens' }] + content_id: 'P12453' }); // [END analytics_log_event_params] } diff --git a/snippets/analytics-next/index/analytics_log_event_params.js b/snippets/analytics-next/index/analytics_log_event_params.js index 27e6528d..e79d7ec0 100644 --- a/snippets/analytics-next/index/analytics_log_event_params.js +++ b/snippets/analytics-next/index/analytics_log_event_params.js @@ -10,7 +10,6 @@ import { getAnalytics, logEvent } from "firebase/analytics"; const analytics = getAnalytics(); logEvent(analytics, 'select_content', { content_type: 'image', - content_id: 'P12453', - items: [{ name: 'Kittens' }] + content_id: 'P12453' }); // [END analytics_log_event_params_modular] \ No newline at end of file From 8eb8a7c7c59049edb01398a2743562192e397227 Mon Sep 17 00:00:00 2001 From: DPEBot Date: Thu, 20 Oct 2022 14:46:57 -0700 Subject: [PATCH 14/38] Auto-update dependencies. (#241) --- analytics-next/package.json | 2 +- appcheck-next/package.json | 2 +- auth-next/package.json | 2 +- database-next/package.json | 2 +- firebaseapp-next/package.json | 2 +- firestore-next/package.json | 2 +- functions-next/package.json | 2 +- messaging-next/package.json | 2 +- perf-next/package.json | 2 +- remoteconfig-next/package.json | 2 +- storage-next/package.json | 2 +- 11 files changed, 11 insertions(+), 11 deletions(-) diff --git a/analytics-next/package.json b/analytics-next/package.json index d0955d16..0fb07418 100644 --- a/analytics-next/package.json +++ b/analytics-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/appcheck-next/package.json b/appcheck-next/package.json index 7c84b7df..ad78db9f 100644 --- a/appcheck-next/package.json +++ b/appcheck-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/auth-next/package.json b/auth-next/package.json index 53d964a2..48adc595 100644 --- a/auth-next/package.json +++ b/auth-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/database-next/package.json b/database-next/package.json index 175d6c63..be3cab88 100644 --- a/database-next/package.json +++ b/database-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/firebaseapp-next/package.json b/firebaseapp-next/package.json index 88dd8954..d7b654df 100644 --- a/firebaseapp-next/package.json +++ b/firebaseapp-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/firestore-next/package.json b/firestore-next/package.json index 2c95f580..39b5c6a9 100644 --- a/firestore-next/package.json +++ b/firestore-next/package.json @@ -6,7 +6,7 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0", + "firebase": "^9.12.1", "geofire-common": "^5.1.0" }, "devDependencies": { diff --git a/functions-next/package.json b/functions-next/package.json index 4ddfe8c3..618ee0c5 100644 --- a/functions-next/package.json +++ b/functions-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/messaging-next/package.json b/messaging-next/package.json index fe28f50e..2eb86c54 100644 --- a/messaging-next/package.json +++ b/messaging-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/perf-next/package.json b/perf-next/package.json index 69cf753b..e05ef409 100644 --- a/perf-next/package.json +++ b/perf-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/remoteconfig-next/package.json b/remoteconfig-next/package.json index 8a072847..ffbd6c3e 100644 --- a/remoteconfig-next/package.json +++ b/remoteconfig-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } diff --git a/storage-next/package.json b/storage-next/package.json index fbce56ec..a64d67b2 100644 --- a/storage-next/package.json +++ b/storage-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.1.0" + "firebase": "^9.12.1" } } From 476223e29552c2128ac2d62e3906628130047cf8 Mon Sep 17 00:00:00 2001 From: DPEBot Date: Thu, 20 Oct 2022 14:55:19 -0700 Subject: [PATCH 15/38] Auto-update dependencies. (#242) * Auto-update dependencies. * Auto-update dependencies. Co-authored-by: Morgan Chen --- firestore/index.html | 4 ++-- messaging/service-worker.js | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/firestore/index.html b/firestore/index.html index ddc3c44d..3599ca13 100644 --- a/firestore/index.html +++ b/firestore/index.html @@ -12,8 +12,8 @@ - - + + diff --git a/messaging/service-worker.js b/messaging/service-worker.js index 3b2f7de0..26f9d097 100644 --- a/messaging/service-worker.js +++ b/messaging/service-worker.js @@ -10,8 +10,8 @@ function initInSw() { // Give the service worker access to Firebase Messaging. // Note that you can only use Firebase Messaging here. Other Firebase libraries // are not available in the service worker. - importScripts('https://www.gstatic.com/firebasejs/8.10.0/firebase-app.js'); - importScripts('https://www.gstatic.com/firebasejs/8.10.0/firebase-messaging.js'); + importScripts('https://www.gstatic.com/firebasejs/9.2.0/firebase-app.js'); + importScripts('https://www.gstatic.com/firebasejs/9.2.0/firebase-messaging.js'); // Initialize the Firebase app in the service worker by passing in // your app's Firebase config object. From 36740fb2c39383621c0c0a948236e9eab8a71516 Mon Sep 17 00:00:00 2001 From: Morgan Chen Date: Thu, 20 Oct 2022 15:15:06 -0700 Subject: [PATCH 16/38] Add count query snippet (#307) * Add count query snippet * add simpler snippet * consts * no masking * run snippets --- firestore-next/test.firestore.js | 21 +++++++++++++++++++ .../count_aggregate_collection.js | 11 ++++++++++ .../test-firestore/count_aggregate_query.js | 12 +++++++++++ 3 files changed, 44 insertions(+) create mode 100644 snippets/firestore-next/test-firestore/count_aggregate_collection.js create mode 100644 snippets/firestore-next/test-firestore/count_aggregate_query.js diff --git a/firestore-next/test.firestore.js b/firestore-next/test.firestore.js index 17ff6d29..2469b736 100644 --- a/firestore-next/test.firestore.js +++ b/firestore-next/test.firestore.js @@ -1158,6 +1158,27 @@ describe("firestore", () => { }); }); + describe("aggregate queries", () => { + it("should fetch the count of documents in a collection", async () => { + const { collection, getCountFromServer } = require("firebase/firestore"); + // [START count_aggregate_collection] + const coll = collection(db, "cities"); + const snapshot = await getCountFromServer(coll); + console.log('count: ', snapshot.data().count); + // [END count_aggregate_collection] + }); + + it("should fetch the count of documents in a query", async () => { + const { collection, getCountFromServer, where, query } = require("firebase/firestore"); + // [START count_aggregate_query] + const coll = collection(db, "cities"); + const q = query(coll, where("state", "==", "CA")); + const snapshot = await getCountFromServer(q); + console.log('count: ', snapshot.data().count); + // [END count_aggregate_query] + }); + }); + // TODO: Break out into separate file describe("solution-aggregation", () => { it("should update a restaurant in a transaction #UNVERIFIED", async () => { diff --git a/snippets/firestore-next/test-firestore/count_aggregate_collection.js b/snippets/firestore-next/test-firestore/count_aggregate_collection.js new file mode 100644 index 00000000..7dca7e37 --- /dev/null +++ b/snippets/firestore-next/test-firestore/count_aggregate_collection.js @@ -0,0 +1,11 @@ +// This snippet file was generated by processing the source file: +// ./firestore-next/test.firestore.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START count_aggregate_collection_modular] +const coll = collection(db, "cities"); +const snapshot = await getCountFromServer(coll); +console.log('count: ', snapshot.data().count); +// [END count_aggregate_collection_modular] \ No newline at end of file diff --git a/snippets/firestore-next/test-firestore/count_aggregate_query.js b/snippets/firestore-next/test-firestore/count_aggregate_query.js new file mode 100644 index 00000000..37a27458 --- /dev/null +++ b/snippets/firestore-next/test-firestore/count_aggregate_query.js @@ -0,0 +1,12 @@ +// This snippet file was generated by processing the source file: +// ./firestore-next/test.firestore.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START count_aggregate_query_modular] +const coll = collection(db, "cities"); +const q = query(coll, where("state", "==", "CA")); +const snapshot = await getCountFromServer(q); +console.log('count: ', snapshot.data().count); +// [END count_aggregate_query_modular] \ No newline at end of file From 7ca0947f12931dce792e66f986707ffa2839184a Mon Sep 17 00:00:00 2001 From: markarndt <50713862+markarndt@users.noreply.github.com> Date: Thu, 2 Feb 2023 16:02:59 -0800 Subject: [PATCH 17/38] Add Storage emulator snippets that were previously hard-coded in docs. (#304) * Initial push to prepare for review. * Fix lint error. * Generate /snippets/storage-next/emulator-suite. * Fix errant RTDB reference in comment lines. --- .../emulator-suite/storage_emulator_connect.js | 15 +++++++++++++++ storage-next/emulator-suite.js | 14 ++++++++++++++ storage/emulator-suite.js | 16 ++++++++++++++++ 3 files changed, 45 insertions(+) create mode 100644 snippets/storage-next/emulator-suite/storage_emulator_connect.js create mode 100644 storage-next/emulator-suite.js create mode 100644 storage/emulator-suite.js diff --git a/snippets/storage-next/emulator-suite/storage_emulator_connect.js b/snippets/storage-next/emulator-suite/storage_emulator_connect.js new file mode 100644 index 00000000..5cdc1589 --- /dev/null +++ b/snippets/storage-next/emulator-suite/storage_emulator_connect.js @@ -0,0 +1,15 @@ +// This snippet file was generated by processing the source file: +// ./storage-next/emulator-suite.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START storage_emulator_connect_modular] +import { getStorage, connectStorageEmulator } from "firebase/storage"; + +const storage = getStorage(); +if (location.hostname === "localhost") { + // Point to the Storage emulator running on localhost. + connectStorageEmulator(storage, "localhost", 9199); +} +// [END storage_emulator_connect_modular] \ No newline at end of file diff --git a/storage-next/emulator-suite.js b/storage-next/emulator-suite.js new file mode 100644 index 00000000..b3038033 --- /dev/null +++ b/storage-next/emulator-suite.js @@ -0,0 +1,14 @@ +// [SNIPPET_REGISTRY disabled] +// [SNIPPETS_SEPARATION enabled] + +function onDocumentReady() { + // [START storage_emulator_connect] + const { getStorage, connectStorageEmulator } = require("firebase/storage"); + + const storage = getStorage(); + if (location.hostname === "localhost") { + // Point to the Storage emulator running on localhost. + connectStorageEmulator(storage, "localhost", 9199); + } + // [END storage_emulator_connect] +} diff --git a/storage/emulator-suite.js b/storage/emulator-suite.js new file mode 100644 index 00000000..7f93e660 --- /dev/null +++ b/storage/emulator-suite.js @@ -0,0 +1,16 @@ +// These samples are intended for Web so this import would normally be +// done in HTML however using modules here is more convenient for +// ensuring sample correctness offline. +import firebase from "firebase/app"; +import "firebase/storage"; + +function onDocumentReady() { + // [START storage_emulator_connect] + var storage = firebase.storage(); + if (location.hostname === "localhost") { + // Point to the Storage emulator running on localhost. + storage.useEmulator("localhost", 9199); + } + // [END storage_emulator_connect] +} + From b48560b155e6f27db977f51070470631e7a2db56 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ros=C3=A1rio=20Pereira=20Fernandes?= Date: Fri, 3 Feb 2023 18:05:46 +0000 Subject: [PATCH 18/38] refactor: import getMessaging from messaging/sw (#320) --- messaging-next/service-worker.js | 2 +- .../service-worker/messaging_on_background_message.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/messaging-next/service-worker.js b/messaging-next/service-worker.js index a81a7c18..55f07524 100644 --- a/messaging-next/service-worker.js +++ b/messaging-next/service-worker.js @@ -40,7 +40,7 @@ function initInSw() { function onBackgroundMessage() { // [START messaging_on_background_message] - const { getMessaging } = require("firebase/messaging"); + const { getMessaging } = require("firebase/messaging/sw"); const { onBackgroundMessage } = require("firebase/messaging/sw"); const messaging = getMessaging(); diff --git a/snippets/messaging-next/service-worker/messaging_on_background_message.js b/snippets/messaging-next/service-worker/messaging_on_background_message.js index b7f65b53..79c17eea 100644 --- a/snippets/messaging-next/service-worker/messaging_on_background_message.js +++ b/snippets/messaging-next/service-worker/messaging_on_background_message.js @@ -5,7 +5,7 @@ // 'npm run snippets'. // [START messaging_on_background_message_modular] -import { getMessaging } from "firebase/messaging"; +import { getMessaging } from "firebase/messaging/sw"; import { onBackgroundMessage } from "firebase/messaging/sw"; const messaging = getMessaging(); From 73a4f0b01c7e9869e3bb8bd4494ff186eb784ba5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ros=C3=A1rio=20Pereira=20Fernandes?= Date: Fri, 3 Feb 2023 18:09:33 +0000 Subject: [PATCH 19/38] mention getAdditionalUserInfo() in oauth providers (#319) --- auth-next/apple.js | 1 + auth-next/facebook.js | 3 +++ auth-next/github.js | 3 +++ auth-next/google-signin.js | 3 +++ auth-next/twitter.js | 3 +++ auth/apple.js | 7 +++++-- auth/facebook.js | 4 ++++ auth/github.js | 5 ++++- auth/google-signin.js | 5 ++++- auth/twitter.js | 5 ++++- snippets/auth-next/apple/auth_apple_signin_popup.js | 1 + snippets/auth-next/facebook/auth_facebook_signin_popup.js | 1 + .../facebook/auth_facebook_signin_redirect_result.js | 2 ++ snippets/auth-next/github/auth_github_signin_popup.js | 1 + .../auth-next/github/auth_github_signin_redirect_result.js | 2 ++ .../auth-next/google-signin/auth_google_signin_popup.js | 1 + .../google-signin/auth_google_signin_redirect_result.js | 2 ++ snippets/auth-next/twitter/auth_twitter_signin_popup.js | 1 + .../twitter/auth_twitter_signin_redirect_result.js | 2 ++ 19 files changed, 47 insertions(+), 5 deletions(-) diff --git a/auth-next/apple.js b/auth-next/apple.js index f9670b4c..2777a085 100644 --- a/auth-next/apple.js +++ b/auth-next/apple.js @@ -38,6 +38,7 @@ function appleSignInPopup(provider) { const accessToken = credential.accessToken; const idToken = credential.idToken; + // IdP data available using getAdditionalUserInfo(result) // ... }) .catch((error) => { diff --git a/auth-next/facebook.js b/auth-next/facebook.js index 67b397f2..3c6feb8a 100644 --- a/auth-next/facebook.js +++ b/auth-next/facebook.js @@ -33,6 +33,7 @@ function facebookSignInPopup(provider) { const credential = FacebookAuthProvider.credentialFromResult(result); const accessToken = credential.accessToken; + // IdP data available using getAdditionalUserInfo(result) // ... }) .catch((error) => { @@ -61,6 +62,8 @@ function facebookSignInRedirectResult() { const token = credential.accessToken; const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; diff --git a/auth-next/github.js b/auth-next/github.js index babfd1ee..4c128721 100644 --- a/auth-next/github.js +++ b/auth-next/github.js @@ -40,6 +40,7 @@ function githubSignInPopup(provider) { // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) // ... }).catch((error) => { // Handle Errors here. @@ -70,6 +71,8 @@ function githubSignInRedirectResult() { // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; diff --git a/auth-next/google-signin.js b/auth-next/google-signin.js index 136c26b5..025eebd6 100644 --- a/auth-next/google-signin.js +++ b/auth-next/google-signin.js @@ -33,6 +33,7 @@ function googleSignInPopup(provider) { const token = credential.accessToken; // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) // ... }).catch((error) => { // Handle Errors here. @@ -60,6 +61,8 @@ function googleSignInRedirectResult() { // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; diff --git a/auth-next/twitter.js b/auth-next/twitter.js index a386e4ab..f96e574b 100644 --- a/auth-next/twitter.js +++ b/auth-next/twitter.js @@ -30,6 +30,7 @@ function twitterSignInPopup(provider) { // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) // ... }).catch((error) => { // Handle Errors here. @@ -60,6 +61,8 @@ function twitterSignInRedirectResult() { // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; diff --git a/auth/apple.js b/auth/apple.js index e99349c8..00e2598e 100644 --- a/auth/apple.js +++ b/auth/apple.js @@ -40,7 +40,8 @@ function appleSignInPopup(provider) { var accessToken = credential.accessToken; var idToken = credential.idToken; - // ... + // IdP data available using getAdditionalUserInfo(result) + // ... }) .catch((error) => { // Handle Errors here. @@ -77,6 +78,7 @@ function appleSignInRedirectResult() { var accessToken = credential.accessToken; var idToken = credential.idToken; + // IdP data available in result.additionalUserInfo.profile. // ... } // The signed-in user info. @@ -117,7 +119,8 @@ function appleReauthenticatePopup() { var accessToken = credential.accessToken; var idToken = credential.idToken; - // ... + // IdP data available in result.additionalUserInfo.profile. + // ... }) .catch((error) => { // Handle Errors here. diff --git a/auth/facebook.js b/auth/facebook.js index 4259960d..75e99d43 100644 --- a/auth/facebook.js +++ b/auth/facebook.js @@ -31,6 +31,8 @@ function facebookSignInPopup(provider) { // The signed-in user info. var user = result.user; + // IdP data available in result.additionalUserInfo.profile. + // ... // This gives you a Facebook Access Token. You can use it to access the Facebook API. var accessToken = credential.accessToken; @@ -66,6 +68,8 @@ function facebookSignInRedirectResult() { } // The signed-in user info. var user = result.user; + // IdP data available in result.additionalUserInfo.profile. + // ... }).catch((error) => { // Handle Errors here. var errorCode = error.code; diff --git a/auth/github.js b/auth/github.js index 6ae1e531..8ae9b39c 100644 --- a/auth/github.js +++ b/auth/github.js @@ -40,7 +40,8 @@ function githubSignInPopup(provider) { // The signed-in user info. var user = result.user; - // ... + // IdP data available in result.additionalUserInfo.profile. + // ... }).catch((error) => { // Handle Errors here. var errorCode = error.code; @@ -70,6 +71,8 @@ function githubSignInRedirectResult() { // The signed-in user info. var user = result.user; + // IdP data available in result.additionalUserInfo.profile. + // ... }).catch((error) => { // Handle Errors here. var errorCode = error.code; diff --git a/auth/google-signin.js b/auth/google-signin.js index fcc32dc8..06a488e4 100644 --- a/auth/google-signin.js +++ b/auth/google-signin.js @@ -34,7 +34,8 @@ function googleSignInPopup(provider) { var token = credential.accessToken; // The signed-in user info. var user = result.user; - // ... + // IdP data available in result.additionalUserInfo.profile. + // ... }).catch((error) => { // Handle Errors here. var errorCode = error.code; @@ -63,6 +64,8 @@ function googleSignInRedirectResult() { } // The signed-in user info. var user = result.user; + // IdP data available in result.additionalUserInfo.profile. + // ... }).catch((error) => { // Handle Errors here. var errorCode = error.code; diff --git a/auth/twitter.js b/auth/twitter.js index a78370b7..68ed6f35 100644 --- a/auth/twitter.js +++ b/auth/twitter.js @@ -32,7 +32,8 @@ function twitterSignInPopup(provider) { // The signed-in user info. var user = result.user; - // ... + // IdP data available in result.additionalUserInfo.profile. + // ... }).catch((error) => { // Handle Errors here. var errorCode = error.code; @@ -64,6 +65,8 @@ function twitterSignInRedirectResult() { // The signed-in user info. var user = result.user; + // IdP data available in result.additionalUserInfo.profile. + // ... }).catch((error) => { // Handle Errors here. var errorCode = error.code; diff --git a/snippets/auth-next/apple/auth_apple_signin_popup.js b/snippets/auth-next/apple/auth_apple_signin_popup.js index c2a392cf..e3a0f11b 100644 --- a/snippets/auth-next/apple/auth_apple_signin_popup.js +++ b/snippets/auth-next/apple/auth_apple_signin_popup.js @@ -18,6 +18,7 @@ signInWithPopup(auth, provider) const accessToken = credential.accessToken; const idToken = credential.idToken; + // IdP data available using getAdditionalUserInfo(result) // ... }) .catch((error) => { diff --git a/snippets/auth-next/facebook/auth_facebook_signin_popup.js b/snippets/auth-next/facebook/auth_facebook_signin_popup.js index 7d35aaf2..524a11ac 100644 --- a/snippets/auth-next/facebook/auth_facebook_signin_popup.js +++ b/snippets/auth-next/facebook/auth_facebook_signin_popup.js @@ -17,6 +17,7 @@ signInWithPopup(auth, provider) const credential = FacebookAuthProvider.credentialFromResult(result); const accessToken = credential.accessToken; + // IdP data available using getAdditionalUserInfo(result) // ... }) .catch((error) => { diff --git a/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js b/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js index eb6cdb30..c65c47d7 100644 --- a/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js +++ b/snippets/auth-next/facebook/auth_facebook_signin_redirect_result.js @@ -15,6 +15,8 @@ getRedirectResult(auth) const token = credential.accessToken; const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; diff --git a/snippets/auth-next/github/auth_github_signin_popup.js b/snippets/auth-next/github/auth_github_signin_popup.js index e1b4768e..3839a70f 100644 --- a/snippets/auth-next/github/auth_github_signin_popup.js +++ b/snippets/auth-next/github/auth_github_signin_popup.js @@ -16,6 +16,7 @@ signInWithPopup(auth, provider) // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) // ... }).catch((error) => { // Handle Errors here. diff --git a/snippets/auth-next/github/auth_github_signin_redirect_result.js b/snippets/auth-next/github/auth_github_signin_redirect_result.js index b3d31d0a..fb5f7ca2 100644 --- a/snippets/auth-next/github/auth_github_signin_redirect_result.js +++ b/snippets/auth-next/github/auth_github_signin_redirect_result.js @@ -19,6 +19,8 @@ getRedirectResult(auth) // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; diff --git a/snippets/auth-next/google-signin/auth_google_signin_popup.js b/snippets/auth-next/google-signin/auth_google_signin_popup.js index d6c70eb9..433bb88e 100644 --- a/snippets/auth-next/google-signin/auth_google_signin_popup.js +++ b/snippets/auth-next/google-signin/auth_google_signin_popup.js @@ -15,6 +15,7 @@ signInWithPopup(auth, provider) const token = credential.accessToken; // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) // ... }).catch((error) => { // Handle Errors here. diff --git a/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js b/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js index 50c4aded..2953ab5f 100644 --- a/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js +++ b/snippets/auth-next/google-signin/auth_google_signin_redirect_result.js @@ -16,6 +16,8 @@ getRedirectResult(auth) // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; diff --git a/snippets/auth-next/twitter/auth_twitter_signin_popup.js b/snippets/auth-next/twitter/auth_twitter_signin_popup.js index ae8e2007..adb7322e 100644 --- a/snippets/auth-next/twitter/auth_twitter_signin_popup.js +++ b/snippets/auth-next/twitter/auth_twitter_signin_popup.js @@ -18,6 +18,7 @@ signInWithPopup(auth, provider) // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) // ... }).catch((error) => { // Handle Errors here. diff --git a/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js b/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js index 73e42bab..357faa4e 100644 --- a/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js +++ b/snippets/auth-next/twitter/auth_twitter_signin_redirect_result.js @@ -19,6 +19,8 @@ getRedirectResult(auth) // The signed-in user info. const user = result.user; + // IdP data available using getAdditionalUserInfo(result) + // ... }).catch((error) => { // Handle Errors here. const errorCode = error.code; From 486e5c67bcb895a00ccab90f1b20cefdba6c9e3a Mon Sep 17 00:00:00 2001 From: dwyfrequency Date: Wed, 15 Feb 2023 13:28:52 -0500 Subject: [PATCH 20/38] Update gstatic url for v8 example (#325) --- messaging/service-worker.js | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/messaging/service-worker.js b/messaging/service-worker.js index 26f9d097..c0f875bb 100644 --- a/messaging/service-worker.js +++ b/messaging/service-worker.js @@ -1,5 +1,5 @@ -import firebase from "firebase/app"; -import "firebase/messaging"; +import firebase from 'firebase/app'; +import 'firebase/messaging'; // See: https://github.com/microsoft/TypeScript/issues/14877 /** @type {ServiceWorkerGlobalScope} */ @@ -10,8 +10,8 @@ function initInSw() { // Give the service worker access to Firebase Messaging. // Note that you can only use Firebase Messaging here. Other Firebase libraries // are not available in the service worker. - importScripts('https://www.gstatic.com/firebasejs/9.2.0/firebase-app.js'); - importScripts('https://www.gstatic.com/firebasejs/9.2.0/firebase-messaging.js'); + importScripts('https://www.gstatic.com/firebasejs/8.10.1/firebase-app.js'); + importScripts('https://www.gstatic.com/firebasejs/8.10.1/firebase-messaging.js'); // Initialize the Firebase app in the service worker by passing in // your app's Firebase config object. @@ -38,16 +38,18 @@ function onBackgroundMessage() { // [START messaging_on_background_message] messaging.onBackgroundMessage((payload) => { - console.log('[firebase-messaging-sw.js] Received background message ', payload); + console.log( + '[firebase-messaging-sw.js] Received background message ', + payload + ); // Customize notification here const notificationTitle = 'Background Message Title'; const notificationOptions = { body: 'Background Message body.', icon: '/firebase-logo.png' }; - - self.registration.showNotification(notificationTitle, - notificationOptions); + + self.registration.showNotification(notificationTitle, notificationOptions); }); // [END messaging_on_background_message] } From e2beb93c2842b540ce78403ff4e2b115ebc0d072 Mon Sep 17 00:00:00 2001 From: Shabbirjodhpur <62835725+Shabbirjodhpur@users.noreply.github.com> Date: Tue, 4 Apr 2023 21:43:38 +0530 Subject: [PATCH 21/38] Update get_document.js (#335) We get the snapshot of data using 'getDoc()' and get result 'docSnap' And then we perform check on this 'docSnap' in the if else block So in the else block the comment should ne docSnap.data() will ne undefined --- firestore-next/test.firestore.js | 2 +- snippets/firestore-next/test-firestore/get_document.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/firestore-next/test.firestore.js b/firestore-next/test.firestore.js index 2469b736..a430064f 100644 --- a/firestore-next/test.firestore.js +++ b/firestore-next/test.firestore.js @@ -583,7 +583,7 @@ describe("firestore", () => { if (docSnap.exists()) { console.log("Document data:", docSnap.data()); } else { - // doc.data() will be undefined in this case + // docSnap.data() will be undefined in this case console.log("No such document!"); } // [END get_document] diff --git a/snippets/firestore-next/test-firestore/get_document.js b/snippets/firestore-next/test-firestore/get_document.js index 4cfbaaf6..1653b61a 100644 --- a/snippets/firestore-next/test-firestore/get_document.js +++ b/snippets/firestore-next/test-firestore/get_document.js @@ -13,7 +13,7 @@ const docSnap = await getDoc(docRef); if (docSnap.exists()) { console.log("Document data:", docSnap.data()); } else { - // doc.data() will be undefined in this case + // docSnap.data() will be undefined in this case console.log("No such document!"); } // [END get_document_modular] \ No newline at end of file From 1852962750472181dbb4523e5185b8e0350f2f38 Mon Sep 17 00:00:00 2001 From: Juan Lara Date: Tue, 9 May 2023 02:26:28 -0700 Subject: [PATCH 22/38] Add a snippet demonstrating a subcollection query. (#339) --- firestore-next/test.firestore.js | 12 ++++++++++++ .../firestore_query_subcollection.js | 15 +++++++++++++++ 2 files changed, 27 insertions(+) create mode 100644 snippets/firestore-next/test-firestore/firestore_query_subcollection.js diff --git a/firestore-next/test.firestore.js b/firestore-next/test.firestore.js index a430064f..c961af9d 100644 --- a/firestore-next/test.firestore.js +++ b/firestore-next/test.firestore.js @@ -683,6 +683,18 @@ describe("firestore", () => { // [END get_multiple_all] }); + it("should get all documents from a subcollection", async () => { + // [START firestore_query_subcollection] + const { collection, getDocs } = require("firebase/firestore"); + // Query a reference to a subcollection + const querySnapshot = await getDocs(collection(db, "cities", "SF", "landmarks")); + querySnapshot.forEach((doc) => { + // doc.data() is never undefined for query doc snapshots + console.log(doc.id, " => ", doc.data()); + }); + // [END firestore_query_subcollection] + }); + it("should listen on multiple documents #UNVERIFIED", (done) => { // [START listen_multiple] const { collection, query, where, onSnapshot } = require("firebase/firestore"); diff --git a/snippets/firestore-next/test-firestore/firestore_query_subcollection.js b/snippets/firestore-next/test-firestore/firestore_query_subcollection.js new file mode 100644 index 00000000..76a1b847 --- /dev/null +++ b/snippets/firestore-next/test-firestore/firestore_query_subcollection.js @@ -0,0 +1,15 @@ +// This snippet file was generated by processing the source file: +// ./firestore-next/test.firestore.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + +// [START firestore_query_subcollection_modular] +import { collection, getDocs } from "firebase/firestore"; +// Query a reference to a subcollection +const querySnapshot = await getDocs(collection(db, "cities", "SF", "landmarks")); +querySnapshot.forEach((doc) => { + // doc.data() is never undefined for query doc snapshots + console.log(doc.id, " => ", doc.data()); +}); +// [END firestore_query_subcollection_modular] \ No newline at end of file From 2414b5519c79472a228a38205f646e71d43cb182 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ros=C3=A1rio=20P=2E=20Fernandes?= Date: Mon, 22 May 2023 14:32:41 +0100 Subject: [PATCH 23/38] fix broken ref docs urls (#343) * fix broken ref docs urls * update the separate-snippets script to replace ref docs urls --- auth-next/index.js | 4 +-- auth/index.js | 4 +-- firestore/test.firestore.js | 2 +- scripts/separate-snippets.ts | 27 +++++++++++++++++++ snippets/auth-next/index/auth_current_user.js | 2 +- .../auth-next/index/auth_state_listener.js | 2 +- 6 files changed, 34 insertions(+), 7 deletions(-) diff --git a/auth-next/index.js b/auth-next/index.js index b4a17903..b741a6d7 100644 --- a/auth-next/index.js +++ b/auth-next/index.js @@ -52,7 +52,7 @@ function authStateListener() { onAuthStateChanged(auth, (user) => { if (user) { // User is signed in, see docs for a list of available properties - // https://firebase.google.com/docs/reference/js/firebase.User + // https://firebase.google.com/docs/reference/js/v8/firebase.User const uid = user.uid; // ... } else { @@ -72,7 +72,7 @@ function currentUser() { if (user) { // User is signed in, see docs for a list of available properties - // https://firebase.google.com/docs/reference/js/firebase.User + // https://firebase.google.com/docs/reference/js/v8/firebase.User // ... } else { // No user is signed in. diff --git a/auth/index.js b/auth/index.js index 6567c030..35546aa3 100644 --- a/auth/index.js +++ b/auth/index.js @@ -43,7 +43,7 @@ function authStateListener() { firebase.auth().onAuthStateChanged((user) => { if (user) { // User is signed in, see docs for a list of available properties - // https://firebase.google.com/docs/reference/js/firebase.User + // https://firebase.google.com/docs/reference/js/v8/firebase.User var uid = user.uid; // ... } else { @@ -60,7 +60,7 @@ function currentUser() { if (user) { // User is signed in, see docs for a list of available properties - // https://firebase.google.com/docs/reference/js/firebase.User + // https://firebase.google.com/docs/reference/js/v8/firebase.User // ... } else { // No user is signed in. diff --git a/firestore/test.firestore.js b/firestore/test.firestore.js index dbf6e18e..ec89172e 100644 --- a/firestore/test.firestore.js +++ b/firestore/test.firestore.js @@ -600,7 +600,7 @@ describe("firestore", () => { var docRef = db.collection("cities").doc("SF"); // Valid options for source are 'server', 'cache', or - // 'default'. See https://firebase.google.com/docs/reference/js/firebase.firestore.GetOptions + // 'default'. See https://firebase.google.com/docs/reference/js/v8/firebase.firestore.GetOptions // for more information. var getOptions = { source: 'cache' diff --git a/scripts/separate-snippets.ts b/scripts/separate-snippets.ts index a888d908..b2f41de3 100644 --- a/scripts/separate-snippets.ts +++ b/scripts/separate-snippets.ts @@ -18,6 +18,15 @@ const RE_END_SNIPPET = /\[END\s+([A-Za-z_]+)\s*\]/; // TODO: Handle multiline imports? const RE_REQUIRE = /const {(.+?)} = require\((.+?)\)/; +// Regex for ref docs URLs +// eg. "https://firebase.google.com/docs/reference/js/v8/firebase.User" +const RE_REF_DOCS = /https:\/\/firebase\.google\.com\/docs\/reference\/js\/(.*)/; + +// Maps v8 ref docs URLs to their v9 counterpart +const REF_DOCS_MAPPINGS: { [key: string]: string } = { + "v8/firebase.User" : "auth.user" +}; + type SnippetsConfig = { enabled: boolean; suffix: string; @@ -30,6 +39,23 @@ function isBlank(line: string) { return line.trim().length === 0; } +/** + * Replace all v8 ref doc urls with their v9 counterpart. + */ +function replaceRefDocsUrls(lines: string[]) { + const outputLines = []; + for (const line of lines) { + if (line.match(RE_REF_DOCS)) { + outputLines.push(line.replace(RE_REF_DOCS, (match: string, p1?: string) => { + return p1 ? `https://firebase.google.com/docs/reference/js/${REF_DOCS_MAPPINGS[p1]}` : match; + })); + } else { + outputLines.push(line); + } + } + return outputLines; +} + /** * Replace all const { foo } = require('bar') with import { foo } from 'bar'; */ @@ -119,6 +145,7 @@ function processSnippet( outputLines = addSuffixToSnippetNames(outputLines, snippetSuffix); outputLines = adjustIndentation(outputLines); outputLines = removeFirstLineAfterComments(outputLines); + outputLines = replaceRefDocsUrls(outputLines); // Add a preamble to every snippet const preambleLines = [ diff --git a/snippets/auth-next/index/auth_current_user.js b/snippets/auth-next/index/auth_current_user.js index c094a464..6925b021 100644 --- a/snippets/auth-next/index/auth_current_user.js +++ b/snippets/auth-next/index/auth_current_user.js @@ -12,7 +12,7 @@ const user = auth.currentUser; if (user) { // User is signed in, see docs for a list of available properties - // https://firebase.google.com/docs/reference/js/firebase.User + // https://firebase.google.com/docs/reference/js/auth.user // ... } else { // No user is signed in. diff --git a/snippets/auth-next/index/auth_state_listener.js b/snippets/auth-next/index/auth_state_listener.js index aebe6818..0f3e4e88 100644 --- a/snippets/auth-next/index/auth_state_listener.js +++ b/snippets/auth-next/index/auth_state_listener.js @@ -11,7 +11,7 @@ const auth = getAuth(); onAuthStateChanged(auth, (user) => { if (user) { // User is signed in, see docs for a list of available properties - // https://firebase.google.com/docs/reference/js/firebase.User + // https://firebase.google.com/docs/reference/js/auth.user const uid = user.uid; // ... } else { From 8fc7be2dc9ea398e63f57222d02428f8fa506a11 Mon Sep 17 00:00:00 2001 From: gregfenton Date: Mon, 22 May 2023 13:19:10 -0400 Subject: [PATCH 24/38] Remove unused function parameter (#344) --- firestore/test.solution-counters.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/firestore/test.solution-counters.js b/firestore/test.solution-counters.js index c8c62fe6..c7c51cff 100644 --- a/firestore/test.solution-counters.js +++ b/firestore/test.solution-counters.js @@ -22,7 +22,7 @@ function createCounter(ref, num_shards) { // [END create_counter] // [START increment_counter] -function incrementCounter(db, ref, num_shards) { +function incrementCounter(ref, num_shards) { // Select a shard of the counter at random const shard_id = Math.floor(Math.random() * num_shards).toString(); const shard_ref = ref.collection('shards').doc(shard_id); @@ -67,7 +67,7 @@ describe("firestore-solution-counters", () => { // Create a counter, then increment it const ref = db.collection('counters').doc(); return createCounter(ref, 10).then(() => { - return incrementCounter(db, ref, 10); + return incrementCounter(ref, 10); }); }); @@ -75,7 +75,7 @@ describe("firestore-solution-counters", () => { // Create a counter, increment it, then get the count const ref = db.collection('counters').doc(); return createCounter(ref, 10).then(() => { - return incrementCounter(db, ref, 10); + return incrementCounter(ref, 10); }).then(() => { return getCount(ref); }); From adb06a357b6a6509019f15b88cccbdc2788353ef Mon Sep 17 00:00:00 2001 From: markarndt <50713862+markarndt@users.noreply.github.com> Date: Thu, 8 Jun 2023 15:39:37 -0700 Subject: [PATCH 25/38] Emulator localhost updates, localhost -> 127.0.0.1 (#334) * Update v8 and v9 for localhost -> 127.0.0.1 requirement. * Update Auth emulator snippets for localhost -> 127.0.0.1 requirement. * Update RTDB emulator snippet for localhost -> 127.0.0.1 requirement. * Update Storage emulator snippets for localhost -> 127.0.0.1 requirement. * More Database emulator snippet updates. * Update emulator-suite.js * Update emulator-suite.js * Update v8 and v9 for localhost -> 127.0.0.1 requirement. * Update Auth emulator snippets for localhost -> 127.0.0.1 requirement. * Update RTDB emulator snippet for localhost -> 127.0.0.1 requirement. * Update Storage emulator snippets for localhost -> 127.0.0.1 requirement. * More Database emulator snippet updates. * After running local script, new update file. * Test using "Delete" to remove file from PR, not repo * Put this file back. --- auth-next/emulator-suite.js | 2 +- auth/emulator-suite.js | 2 +- database-next/emulator-suite.js | 2 +- database/emulator-suite.js | 2 +- firestore-next/emulator-suite.js | 2 +- firestore/emulator-suite.js | 2 +- functions-next/emulator-suite.js | 2 +- functions/emulator-suite.js | 2 +- snippets/auth-next/emulator-suite/auth_emulator_connect.js | 2 +- snippets/database-next/emulator-suite/rtdb_emulator_connect.js | 2 +- snippets/firestore-next/emulator-suite/fs_emulator_connect.js | 2 +- .../emulator-suite/fb_functions_emulator_connect.js | 2 +- .../storage-next/emulator-suite/storage_emulator_connect.js | 2 +- storage-next/emulator-suite.js | 2 +- storage/emulator-suite.js | 2 +- 15 files changed, 15 insertions(+), 15 deletions(-) diff --git a/auth-next/emulator-suite.js b/auth-next/emulator-suite.js index 66507de3..13b1ba95 100644 --- a/auth-next/emulator-suite.js +++ b/auth-next/emulator-suite.js @@ -6,7 +6,7 @@ function emulatorConnect() { const { getAuth, connectAuthEmulator } = require("firebase/auth"); const auth = getAuth(); - connectAuthEmulator(auth, "http://localhost:9099"); + connectAuthEmulator(auth, "http://127.0.0.1:9099"); // [END auth_emulator_connect] } diff --git a/auth/emulator-suite.js b/auth/emulator-suite.js index b14a72db..b0f815e2 100644 --- a/auth/emulator-suite.js +++ b/auth/emulator-suite.js @@ -4,7 +4,7 @@ import "firebase/auth"; function emulatorConnect() { // [START auth_emulator_connect] const auth = firebase.auth(); - auth.useEmulator("http://localhost:9099"); + auth.useEmulator("http://127.0.0.1:9099"); // [END auth_emulator_connect] } diff --git a/database-next/emulator-suite.js b/database-next/emulator-suite.js index ab86bf9b..f94d3c89 100644 --- a/database-next/emulator-suite.js +++ b/database-next/emulator-suite.js @@ -8,7 +8,7 @@ function onDocumentReady() { const db = getDatabase(); if (location.hostname === "localhost") { // Point to the RTDB emulator running on localhost. - connectDatabaseEmulator(db, "localhost", 9000); + connectDatabaseEmulator(db, "127.0.0.1", 9000); } // [END rtdb_emulator_connect] } diff --git a/database/emulator-suite.js b/database/emulator-suite.js index 8fe739e4..8da23e25 100644 --- a/database/emulator-suite.js +++ b/database/emulator-suite.js @@ -10,7 +10,7 @@ function onDocumentReady() { var db = firebase.database(); if (location.hostname === "localhost") { // Point to the RTDB emulator running on localhost. - db.useEmulator("localhost", 9000); + db.useEmulator("127.0.0.1", 9000); } // [END rtdb_emulator_connect] } diff --git a/firestore-next/emulator-suite.js b/firestore-next/emulator-suite.js index 30ad24eb..edc900c1 100644 --- a/firestore-next/emulator-suite.js +++ b/firestore-next/emulator-suite.js @@ -7,6 +7,6 @@ function onDocumentReady() { // firebaseApps previously initialized using initializeApp() const db = getFirestore(); - connectFirestoreEmulator(db, 'localhost', 8080); + connectFirestoreEmulator(db, '127.0.0.1', 8080); // [END fs_emulator_connect] } diff --git a/firestore/emulator-suite.js b/firestore/emulator-suite.js index 714d38e7..03aef1e9 100644 --- a/firestore/emulator-suite.js +++ b/firestore/emulator-suite.js @@ -6,7 +6,7 @@ function onDocumentReady() { // Firebase previously initialized using firebase.initializeApp(). var db = firebase.firestore(); if (location.hostname === "localhost") { - db.useEmulator("localhost", 8080); + db.useEmulator("127.0.0.1", 8080); } // [END fs_emulator_connect] } diff --git a/functions-next/emulator-suite.js b/functions-next/emulator-suite.js index 7a750fc4..db7fd49d 100644 --- a/functions-next/emulator-suite.js +++ b/functions-next/emulator-suite.js @@ -15,7 +15,7 @@ export function emulatorSettings() { const { getFunctions, connectFunctionsEmulator } = require("firebase/functions"); const functions = getFunctions(getApp()); - connectFunctionsEmulator(functions, "localhost", 5001); + connectFunctionsEmulator(functions, "127.0.0.1", 5001); // [END fb_functions_emulator_connect] } diff --git a/functions/emulator-suite.js b/functions/emulator-suite.js index a9cdc7d7..e0413370 100644 --- a/functions/emulator-suite.js +++ b/functions/emulator-suite.js @@ -3,6 +3,6 @@ import "firebase/functions"; function emulatorSettings() { // [START fb_functions_emulator_connect] - firebase.functions().useEmulator("localhost", 5001); + firebase.functions().useEmulator("127.0.0.1", 5001); // [END fb_functions_emulator_connect] } diff --git a/snippets/auth-next/emulator-suite/auth_emulator_connect.js b/snippets/auth-next/emulator-suite/auth_emulator_connect.js index dd0b2e37..525a92b8 100644 --- a/snippets/auth-next/emulator-suite/auth_emulator_connect.js +++ b/snippets/auth-next/emulator-suite/auth_emulator_connect.js @@ -8,5 +8,5 @@ import { getAuth, connectAuthEmulator } from "firebase/auth"; const auth = getAuth(); -connectAuthEmulator(auth, "http://localhost:9099"); +connectAuthEmulator(auth, "http://127.0.0.1:9099"); // [END auth_emulator_connect_modular] \ No newline at end of file diff --git a/snippets/database-next/emulator-suite/rtdb_emulator_connect.js b/snippets/database-next/emulator-suite/rtdb_emulator_connect.js index 4cc268e7..0bd145f6 100644 --- a/snippets/database-next/emulator-suite/rtdb_emulator_connect.js +++ b/snippets/database-next/emulator-suite/rtdb_emulator_connect.js @@ -10,6 +10,6 @@ import { getDatabase, connectDatabaseEmulator } from "firebase/database"; const db = getDatabase(); if (location.hostname === "localhost") { // Point to the RTDB emulator running on localhost. - connectDatabaseEmulator(db, "localhost", 9000); + connectDatabaseEmulator(db, "127.0.0.1", 9000); } // [END rtdb_emulator_connect_modular] \ No newline at end of file diff --git a/snippets/firestore-next/emulator-suite/fs_emulator_connect.js b/snippets/firestore-next/emulator-suite/fs_emulator_connect.js index 7e31fcfd..d70fbb68 100644 --- a/snippets/firestore-next/emulator-suite/fs_emulator_connect.js +++ b/snippets/firestore-next/emulator-suite/fs_emulator_connect.js @@ -9,5 +9,5 @@ import { getFirestore, connectFirestoreEmulator } from "firebase/firestore"; // firebaseApps previously initialized using initializeApp() const db = getFirestore(); -connectFirestoreEmulator(db, 'localhost', 8080); +connectFirestoreEmulator(db, '127.0.0.1', 8080); // [END fs_emulator_connect_modular] \ No newline at end of file diff --git a/snippets/functions-next/emulator-suite/fb_functions_emulator_connect.js b/snippets/functions-next/emulator-suite/fb_functions_emulator_connect.js index 9b186fc2..835a2c60 100644 --- a/snippets/functions-next/emulator-suite/fb_functions_emulator_connect.js +++ b/snippets/functions-next/emulator-suite/fb_functions_emulator_connect.js @@ -9,5 +9,5 @@ import { getApp } from "firebase/app"; import { getFunctions, connectFunctionsEmulator } from "firebase/functions"; const functions = getFunctions(getApp()); -connectFunctionsEmulator(functions, "localhost", 5001); +connectFunctionsEmulator(functions, "127.0.0.1", 5001); // [END fb_functions_emulator_connect_modular] \ No newline at end of file diff --git a/snippets/storage-next/emulator-suite/storage_emulator_connect.js b/snippets/storage-next/emulator-suite/storage_emulator_connect.js index 5cdc1589..4b247d17 100644 --- a/snippets/storage-next/emulator-suite/storage_emulator_connect.js +++ b/snippets/storage-next/emulator-suite/storage_emulator_connect.js @@ -10,6 +10,6 @@ import { getStorage, connectStorageEmulator } from "firebase/storage"; const storage = getStorage(); if (location.hostname === "localhost") { // Point to the Storage emulator running on localhost. - connectStorageEmulator(storage, "localhost", 9199); + connectStorageEmulator(storage, "127.0.0.1", 9199); } // [END storage_emulator_connect_modular] \ No newline at end of file diff --git a/storage-next/emulator-suite.js b/storage-next/emulator-suite.js index b3038033..78891a4f 100644 --- a/storage-next/emulator-suite.js +++ b/storage-next/emulator-suite.js @@ -8,7 +8,7 @@ function onDocumentReady() { const storage = getStorage(); if (location.hostname === "localhost") { // Point to the Storage emulator running on localhost. - connectStorageEmulator(storage, "localhost", 9199); + connectStorageEmulator(storage, "127.0.0.1", 9199); } // [END storage_emulator_connect] } diff --git a/storage/emulator-suite.js b/storage/emulator-suite.js index 7f93e660..be1f2dd4 100644 --- a/storage/emulator-suite.js +++ b/storage/emulator-suite.js @@ -9,7 +9,7 @@ function onDocumentReady() { var storage = firebase.storage(); if (location.hostname === "localhost") { // Point to the Storage emulator running on localhost. - storage.useEmulator("localhost", 9199); + storage.useEmulator("127.0.0.1", 9199); } // [END storage_emulator_connect] } From 10cfebc889c92c7e41bfaec49dd3b777c88f9f53 Mon Sep 17 00:00:00 2001 From: DPEBot Date: Thu, 22 Jun 2023 15:19:27 -0700 Subject: [PATCH 26/38] Auto-update dependencies. (#311) --- analytics-next/package.json | 2 +- appcheck-next/package.json | 2 +- auth-next/package.json | 2 +- database-next/package.json | 2 +- firebaseapp-next/package.json | 2 +- firestore-next/package.json | 2 +- functions-next/package.json | 2 +- messaging-next/package.json | 2 +- perf-next/package.json | 2 +- remoteconfig-next/package.json | 2 +- storage-next/package.json | 2 +- 11 files changed, 11 insertions(+), 11 deletions(-) diff --git a/analytics-next/package.json b/analytics-next/package.json index 0fb07418..2483e0cd 100644 --- a/analytics-next/package.json +++ b/analytics-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/appcheck-next/package.json b/appcheck-next/package.json index ad78db9f..8af508c9 100644 --- a/appcheck-next/package.json +++ b/appcheck-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/auth-next/package.json b/auth-next/package.json index 48adc595..748ff657 100644 --- a/auth-next/package.json +++ b/auth-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/database-next/package.json b/database-next/package.json index be3cab88..6e7d6f69 100644 --- a/database-next/package.json +++ b/database-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/firebaseapp-next/package.json b/firebaseapp-next/package.json index d7b654df..1e40f536 100644 --- a/firebaseapp-next/package.json +++ b/firebaseapp-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/firestore-next/package.json b/firestore-next/package.json index 39b5c6a9..3ec379a7 100644 --- a/firestore-next/package.json +++ b/firestore-next/package.json @@ -6,7 +6,7 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1", + "firebase": "^9.22.2", "geofire-common": "^5.1.0" }, "devDependencies": { diff --git a/functions-next/package.json b/functions-next/package.json index 618ee0c5..81d6c2f4 100644 --- a/functions-next/package.json +++ b/functions-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/messaging-next/package.json b/messaging-next/package.json index 2eb86c54..7ba8ab2c 100644 --- a/messaging-next/package.json +++ b/messaging-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/perf-next/package.json b/perf-next/package.json index e05ef409..e5d27230 100644 --- a/perf-next/package.json +++ b/perf-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/remoteconfig-next/package.json b/remoteconfig-next/package.json index ffbd6c3e..d0482e46 100644 --- a/remoteconfig-next/package.json +++ b/remoteconfig-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } diff --git a/storage-next/package.json b/storage-next/package.json index a64d67b2..7098fd72 100644 --- a/storage-next/package.json +++ b/storage-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.12.1" + "firebase": "^9.22.2" } } From 7156e6c4c245ff85082c1aa54f16cbcf1a75a640 Mon Sep 17 00:00:00 2001 From: Juyoung Kim Date: Fri, 7 Jul 2023 22:29:12 +0900 Subject: [PATCH 27/38] chore: add missing whitespace & fix an incorrect snippet (#352) * chore: add missing whitespace * chore: fix an incorrect snippet (#324) --- auth-next/index.js | 2 +- database-next/read-and-write.js | 2 +- snippets/auth-next/index/auth_set_language_code.js | 2 +- .../read-and-write/rtdb_social_listen_star_count.js | 2 +- 4 files changed, 4 insertions(+), 4 deletions(-) diff --git a/auth-next/index.js b/auth-next/index.js index b741a6d7..04ac7d03 100644 --- a/auth-next/index.js +++ b/auth-next/index.js @@ -87,7 +87,7 @@ function setLanguageCode() { const auth = getAuth(); auth.languageCode = 'it'; // To apply the default browser preference instead of explicitly setting it. - // firebase.auth().useDeviceLanguage(); + // auth.useDeviceLanguage(); // [END auth_set_language_code] } diff --git a/database-next/read-and-write.js b/database-next/read-and-write.js index 4196c0d7..c06c66b4 100644 --- a/database-next/read-and-write.js +++ b/database-next/read-and-write.js @@ -44,7 +44,7 @@ function socialListenStarCount() { } // [START rtdb_social_listen_star_count] - const { getDatabase, ref, onValue} = require("firebase/database"); + const { getDatabase, ref, onValue } = require("firebase/database"); const db = getDatabase(); const starCountRef = ref(db, 'posts/' + postId + '/starCount'); diff --git a/snippets/auth-next/index/auth_set_language_code.js b/snippets/auth-next/index/auth_set_language_code.js index 47e78295..fe9a2025 100644 --- a/snippets/auth-next/index/auth_set_language_code.js +++ b/snippets/auth-next/index/auth_set_language_code.js @@ -10,5 +10,5 @@ import { getAuth } from "firebase/auth"; const auth = getAuth(); auth.languageCode = 'it'; // To apply the default browser preference instead of explicitly setting it. -// firebase.auth().useDeviceLanguage(); +// auth.useDeviceLanguage(); // [END auth_set_language_code_modular] \ No newline at end of file diff --git a/snippets/database-next/read-and-write/rtdb_social_listen_star_count.js b/snippets/database-next/read-and-write/rtdb_social_listen_star_count.js index ab520ce6..eb782894 100644 --- a/snippets/database-next/read-and-write/rtdb_social_listen_star_count.js +++ b/snippets/database-next/read-and-write/rtdb_social_listen_star_count.js @@ -5,7 +5,7 @@ // 'npm run snippets'. // [START rtdb_social_listen_star_count_modular] -import { getDatabase, ref, onValue} from "firebase/database"; +import { getDatabase, ref, onValue } from "firebase/database"; const db = getDatabase(); const starCountRef = ref(db, 'posts/' + postId + '/starCount'); From 99310330e9cf4836ca94fc9e92114ed58cbdf1b9 Mon Sep 17 00:00:00 2001 From: Chase Hartsell <51487099+ch5zzy@users.noreply.github.com> Date: Mon, 10 Jul 2023 11:58:34 -0700 Subject: [PATCH 28/38] Update phone auth snippets with RecaptchaVerifier parameter reordering (#348) * Update phone auth snippets with RecaptchaVerifier parameter reordering * Update auth-next dependency to v10 --- auth-next/package.json | 2 +- auth-next/phone-auth.js | 10 +++++----- .../auth_phone_recaptcha_verifier_invisible.js | 4 ++-- .../phone-auth/auth_phone_recaptcha_verifier_simple.js | 2 +- .../auth_phone_recaptcha_verifier_visible.js | 4 ++-- 5 files changed, 11 insertions(+), 11 deletions(-) diff --git a/auth-next/package.json b/auth-next/package.json index 748ff657..8d43bad1 100644 --- a/auth-next/package.json +++ b/auth-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/auth-next/phone-auth.js b/auth-next/phone-auth.js index cd894c64..99492f99 100644 --- a/auth-next/phone-auth.js +++ b/auth-next/phone-auth.js @@ -15,13 +15,13 @@ function recaptchaVerifierInvisible() { const { getAuth, RecaptchaVerifier } = require("firebase/auth"); const auth = getAuth(); - window.recaptchaVerifier = new RecaptchaVerifier('sign-in-button', { + window.recaptchaVerifier = new RecaptchaVerifier(auth, 'sign-in-button', { 'size': 'invisible', 'callback': (response) => { // reCAPTCHA solved, allow signInWithPhoneNumber. onSignInSubmit(); } - }, auth); + }); // [END auth_phone_recaptcha_verifier_invisible] } @@ -30,7 +30,7 @@ function recaptchaVerifierVisible() { const { getAuth, RecaptchaVerifier } = require("firebase/auth"); const auth = getAuth(); - window.recaptchaVerifier = new RecaptchaVerifier('recaptcha-container', { + window.recaptchaVerifier = new RecaptchaVerifier(auth, 'recaptcha-container', { 'size': 'normal', 'callback': (response) => { // reCAPTCHA solved, allow signInWithPhoneNumber. @@ -40,7 +40,7 @@ function recaptchaVerifierVisible() { // Response expired. Ask user to solve reCAPTCHA again. // ... } - }, auth); + }); // [END auth_phone_recaptcha_verifier_visible] } @@ -49,7 +49,7 @@ function recaptchaVerifierSimple() { const { getAuth, RecaptchaVerifier } = require("firebase/auth"); const auth = getAuth(); - window.recaptchaVerifier = new RecaptchaVerifier('recaptcha-container', {}, auth); + window.recaptchaVerifier = new RecaptchaVerifier(auth, 'recaptcha-container', {}); // [END auth_phone_recaptcha_verifier_simple] } diff --git a/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_invisible.js b/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_invisible.js index f6b6893f..7fd16eea 100644 --- a/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_invisible.js +++ b/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_invisible.js @@ -8,11 +8,11 @@ import { getAuth, RecaptchaVerifier } from "firebase/auth"; const auth = getAuth(); -window.recaptchaVerifier = new RecaptchaVerifier('sign-in-button', { +window.recaptchaVerifier = new RecaptchaVerifier(auth, 'sign-in-button', { 'size': 'invisible', 'callback': (response) => { // reCAPTCHA solved, allow signInWithPhoneNumber. onSignInSubmit(); } -}, auth); +}); // [END auth_phone_recaptcha_verifier_invisible_modular] \ No newline at end of file diff --git a/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_simple.js b/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_simple.js index ed56fe99..b57eb37b 100644 --- a/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_simple.js +++ b/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_simple.js @@ -8,5 +8,5 @@ import { getAuth, RecaptchaVerifier } from "firebase/auth"; const auth = getAuth(); -window.recaptchaVerifier = new RecaptchaVerifier('recaptcha-container', {}, auth); +window.recaptchaVerifier = new RecaptchaVerifier(auth, 'recaptcha-container', {}); // [END auth_phone_recaptcha_verifier_simple_modular] \ No newline at end of file diff --git a/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_visible.js b/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_visible.js index c91e6041..42ebbe69 100644 --- a/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_visible.js +++ b/snippets/auth-next/phone-auth/auth_phone_recaptcha_verifier_visible.js @@ -8,7 +8,7 @@ import { getAuth, RecaptchaVerifier } from "firebase/auth"; const auth = getAuth(); -window.recaptchaVerifier = new RecaptchaVerifier('recaptcha-container', { +window.recaptchaVerifier = new RecaptchaVerifier(auth, 'recaptcha-container', { 'size': 'normal', 'callback': (response) => { // reCAPTCHA solved, allow signInWithPhoneNumber. @@ -18,5 +18,5 @@ window.recaptchaVerifier = new RecaptchaVerifier('recaptcha-container', { // Response expired. Ask user to solve reCAPTCHA again. // ... } -}, auth); +}); // [END auth_phone_recaptcha_verifier_visible_modular] \ No newline at end of file From 88aa8eb8210c90263eef7fe1f454cd6477a5a252 Mon Sep 17 00:00:00 2001 From: DPEBot Date: Mon, 10 Jul 2023 12:23:45 -0700 Subject: [PATCH 29/38] Auto-update dependencies. (#350) --- analytics-next/package.json | 2 +- appcheck-next/package.json | 2 +- database-next/package.json | 2 +- firebaseapp-next/package.json | 2 +- firestore-next/package.json | 2 +- functions-next/package.json | 2 +- messaging-next/package.json | 2 +- perf-next/package.json | 2 +- remoteconfig-next/package.json | 2 +- storage-next/package.json | 2 +- 10 files changed, 10 insertions(+), 10 deletions(-) diff --git a/analytics-next/package.json b/analytics-next/package.json index 2483e0cd..ee4e36ff 100644 --- a/analytics-next/package.json +++ b/analytics-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/appcheck-next/package.json b/appcheck-next/package.json index 8af508c9..e863723e 100644 --- a/appcheck-next/package.json +++ b/appcheck-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/database-next/package.json b/database-next/package.json index 6e7d6f69..eb16e2d5 100644 --- a/database-next/package.json +++ b/database-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/firebaseapp-next/package.json b/firebaseapp-next/package.json index 1e40f536..13cc74cd 100644 --- a/firebaseapp-next/package.json +++ b/firebaseapp-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/firestore-next/package.json b/firestore-next/package.json index 3ec379a7..ef3b8708 100644 --- a/firestore-next/package.json +++ b/firestore-next/package.json @@ -6,7 +6,7 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2", + "firebase": "^10.0.0", "geofire-common": "^5.1.0" }, "devDependencies": { diff --git a/functions-next/package.json b/functions-next/package.json index 81d6c2f4..14f097ee 100644 --- a/functions-next/package.json +++ b/functions-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/messaging-next/package.json b/messaging-next/package.json index 7ba8ab2c..e4887a2a 100644 --- a/messaging-next/package.json +++ b/messaging-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/perf-next/package.json b/perf-next/package.json index e5d27230..688f6db0 100644 --- a/perf-next/package.json +++ b/perf-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/remoteconfig-next/package.json b/remoteconfig-next/package.json index d0482e46..952b1540 100644 --- a/remoteconfig-next/package.json +++ b/remoteconfig-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } diff --git a/storage-next/package.json b/storage-next/package.json index 7098fd72..b1c449ab 100644 --- a/storage-next/package.json +++ b/storage-next/package.json @@ -6,6 +6,6 @@ }, "license": "Apache-2.0", "dependencies": { - "firebase": "^9.22.2" + "firebase": "^10.0.0" } } From d781c67b528afe99fcdb7c7056104772463fa3ec Mon Sep 17 00:00:00 2001 From: Jonas Kaas Date: Fri, 29 Sep 2023 17:51:19 +0200 Subject: [PATCH 30/38] Fix comment for signup (#356) --- auth-next/email.js | 2 +- snippets/auth-next/email/auth_signup_password.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/auth-next/email.js b/auth-next/email.js index b00551c8..26391f81 100644 --- a/auth-next/email.js +++ b/auth-next/email.js @@ -32,7 +32,7 @@ function signUpWithEmailPassword() { const auth = getAuth(); createUserWithEmailAndPassword(auth, email, password) .then((userCredential) => { - // Signed in + // Signed up const user = userCredential.user; // ... }) diff --git a/snippets/auth-next/email/auth_signup_password.js b/snippets/auth-next/email/auth_signup_password.js index 00aa9bd5..936b64ce 100644 --- a/snippets/auth-next/email/auth_signup_password.js +++ b/snippets/auth-next/email/auth_signup_password.js @@ -10,7 +10,7 @@ import { getAuth, createUserWithEmailAndPassword } from "firebase/auth"; const auth = getAuth(); createUserWithEmailAndPassword(auth, email, password) .then((userCredential) => { - // Signed in + // Signed up const user = userCredential.user; // ... }) From 1f9e7978ed8f6805fad12b32f34b6216ab4556cb Mon Sep 17 00:00:00 2001 From: Morgan Chen Date: Thu, 9 Nov 2023 09:50:47 -0800 Subject: [PATCH 31/38] fix broken array-in snippets (#360) * fix broken array-in snippets * npm run snippets * revert array contians anay changes --- firestore-next/test.firestore.js | 2 +- firestore/test.firestore.js | 2 +- snippets/firestore-next/test-firestore/in_filter_with_array.js | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/firestore-next/test.firestore.js b/firestore-next/test.firestore.js index c961af9d..969c1654 100644 --- a/firestore-next/test.firestore.js +++ b/firestore-next/test.firestore.js @@ -920,7 +920,7 @@ describe("firestore", () => { // [START in_filter_with_array] const { query, where } = require("firebase/firestore"); - const q = query(citiesRef, where('regions', 'in', [['west_coast', 'east_coast']])); + const q = query(citiesRef, where('regions', 'in', [['west_coast'], ['east_coast']])); // [END in_filter_with_array] } }); diff --git a/firestore/test.firestore.js b/firestore/test.firestore.js index ec89172e..20032d36 100644 --- a/firestore/test.firestore.js +++ b/firestore/test.firestore.js @@ -893,7 +893,7 @@ describe("firestore", () => { // [START in_filter_with_array] citiesRef.where('regions', 'in', - [['west_coast', 'east_coast']]); + [['west_coast'], ['east_coast']]); // [END in_filter_with_array] }); diff --git a/snippets/firestore-next/test-firestore/in_filter_with_array.js b/snippets/firestore-next/test-firestore/in_filter_with_array.js index ebe6f18b..190e9dfe 100644 --- a/snippets/firestore-next/test-firestore/in_filter_with_array.js +++ b/snippets/firestore-next/test-firestore/in_filter_with_array.js @@ -7,5 +7,5 @@ // [START in_filter_with_array_modular] import { query, where } from "firebase/firestore"; -const q = query(citiesRef, where('regions', 'in', [['west_coast', 'east_coast']])); +const q = query(citiesRef, where('regions', 'in', [['west_coast'], ['east_coast']])); // [END in_filter_with_array_modular] \ No newline at end of file From e74e8fd9591f70007a44c58580ff0f1fcd1c7959 Mon Sep 17 00:00:00 2001 From: Kevin Sanders Date: Thu, 9 Nov 2023 21:07:49 -0500 Subject: [PATCH 32/38] Typo Fix (#361) --- auth-next/custom-email-handler.js | 4 ++-- .../custom-email-handler/auth_handle_mgmt_query_params.js | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/auth-next/custom-email-handler.js b/auth-next/custom-email-handler.js index 728baff8..5fcc1f71 100644 --- a/auth-next/custom-email-handler.js +++ b/auth-next/custom-email-handler.js @@ -28,8 +28,8 @@ function handleUserManagementQueryParams() { // Configure the Firebase SDK. // This is the minimum configuration required for the API to be used. const config = { - 'apiKey': "YOU_API_KEY" // Copy this key from the web initialization - // snippet found in the Firebase console. + 'apiKey': "YOUR_API_KEY" // Copy this key from the web initialization + // snippet found in the Firebase console. }; const app = initializeApp(config); const auth = getAuth(app); diff --git a/snippets/auth-next/custom-email-handler/auth_handle_mgmt_query_params.js b/snippets/auth-next/custom-email-handler/auth_handle_mgmt_query_params.js index 6dec3399..d0a22696 100644 --- a/snippets/auth-next/custom-email-handler/auth_handle_mgmt_query_params.js +++ b/snippets/auth-next/custom-email-handler/auth_handle_mgmt_query_params.js @@ -23,8 +23,8 @@ document.addEventListener('DOMContentLoaded', () => { // Configure the Firebase SDK. // This is the minimum configuration required for the API to be used. const config = { - 'apiKey': "YOU_API_KEY" // Copy this key from the web initialization - // snippet found in the Firebase console. + 'apiKey': "YOUR_API_KEY" // Copy this key from the web initialization + // snippet found in the Firebase console. }; const app = initializeApp(config); const auth = getAuth(app); From a9160f62f8ebff02285779974620ad3ff260f5ac Mon Sep 17 00:00:00 2001 From: James Daniels Date: Wed, 13 Mar 2024 16:22:44 -0400 Subject: [PATCH 33/38] FirebaseServerApp (#366) * First. * already snippets for that * cleanup * auth_svc_admin * Auth, not auth-next * Express stub should not be in snippet * Move import into snippet * Update firebaseserverapp.js --- auth/package.json | 1 + auth/service-worker-sessions.js | 43 +++++++++++++++++++++ firebaseserverapp-next/firebaseserverapp.js | 27 +++++++++++++ firebaseserverapp-next/package.json | 12 ++++++ 4 files changed, 83 insertions(+) create mode 100644 firebaseserverapp-next/firebaseserverapp.js create mode 100644 firebaseserverapp-next/package.json diff --git a/auth/package.json b/auth/package.json index a6827027..b4b13f01 100644 --- a/auth/package.json +++ b/auth/package.json @@ -7,6 +7,7 @@ "license": "Apache 2.0", "dependencies": { "firebase": "^8.10.0", + "firebase-admin": "^12.0.0", "firebaseui": "^5.0.0" } } diff --git a/auth/service-worker-sessions.js b/auth/service-worker-sessions.js index babbf91e..05791463 100644 --- a/auth/service-worker-sessions.js +++ b/auth/service-worker-sessions.js @@ -162,3 +162,46 @@ function svcSignInEmail(email, password) { }); // [END auth_svc_sign_in_email] } + +function svcRedirectAdmin() { + const app = { use: (a) => {} }; + + // [START auth_svc_admin] + // Server side code. + const admin = require('firebase-admin'); + + // The Firebase Admin SDK is used here to verify the ID token. + admin.initializeApp(); + + function getIdToken(req) { + // Parse the injected ID token from the request header. + const authorizationHeader = req.headers.authorization || ''; + const components = authorizationHeader.split(' '); + return components.length > 1 ? components[1] : ''; + } + + function checkIfSignedIn(url) { + return (req, res, next) => { + if (req.url == url) { + const idToken = getIdToken(req); + // Verify the ID token using the Firebase Admin SDK. + // User already logged in. Redirect to profile page. + admin.auth().verifyIdToken(idToken).then((decodedClaims) => { + // User is authenticated, user claims can be retrieved from + // decodedClaims. + // In this sample code, authenticated users are always redirected to + // the profile page. + res.redirect('/profile'); + }).catch((error) => { + next(); + }); + } else { + next(); + } + }; + } + + // If a user is signed in, redirect to profile page. + app.use(checkIfSignedIn('/')); + // [END auth_svc_admin] +} diff --git a/firebaseserverapp-next/firebaseserverapp.js b/firebaseserverapp-next/firebaseserverapp.js new file mode 100644 index 00000000..d0ab338c --- /dev/null +++ b/firebaseserverapp-next/firebaseserverapp.js @@ -0,0 +1,27 @@ +// @ts-nocheck +// [START serverapp_auth] +import { initializeServerApp } from 'firebase/app'; +import { getAuth } from 'firebase/auth'; +import { headers } from 'next/headers'; +import { redirect } from 'next/navigation'; + +export default function MyServerComponent() { + + // Get relevant request headers (in Next.JS) + const authIdToken = headers().get('Authorization')?.split('Bearer ')[1]; + + // Initialize the FirebaseServerApp instance. + const serverApp = initializeServerApp(firebaseConfig, { authIdToken }); + + // Initialize Firebase Authentication using the FirebaseServerApp instance. + const auth = getAuth(serverApp); + + if (auth.currentUser) { + redirect('/profile'); + } + + // ... +} +// [END serverapp_auth] + +const firebaseConfig = {}; diff --git a/firebaseserverapp-next/package.json b/firebaseserverapp-next/package.json new file mode 100644 index 00000000..0836b0b2 --- /dev/null +++ b/firebaseserverapp-next/package.json @@ -0,0 +1,12 @@ +{ + "name": "firebaseserverapp-next", + "version": "1.0.0", + "scripts": { + "compile": "cp ../tsconfig.json.template ./tsconfig.json && tsc" + }, + "license": "Apache-2.0", + "dependencies": { + "firebase": "^10.0.0", + "next": "^14.1.3" + } +} From 1abb6ce1a784ae5552946dff5f1f5aab7dcbda30 Mon Sep 17 00:00:00 2001 From: "Nhien (Ricky) Lam" <62775270+NhienLam@users.noreply.github.com> Date: Fri, 12 Apr 2024 16:24:45 -0700 Subject: [PATCH 34/38] =?UTF-8?q?Add=20snippets=20for=20Handling=20the=20a?= =?UTF-8?q?ccount-exists-with-different=E2=80=A6=20(#367)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Add v8 and v9 snippets for Handling the account-exists-with-different-credential error * Import auth functions * Add missing methods to param * Add missing methods to params for legacy snippets --- auth-next/link-multiple-accounts.js | 58 ++++++++++++++++++ auth/link-multiple-accounts.js | 56 +++++++++++++++++ .../account_exists_popup.js | 61 +++++++++++++++++++ 3 files changed, 175 insertions(+) create mode 100644 snippets/auth-next/link-multiple-accounts/account_exists_popup.js diff --git a/auth-next/link-multiple-accounts.js b/auth-next/link-multiple-accounts.js index 34c0db58..1938aafc 100644 --- a/auth-next/link-multiple-accounts.js +++ b/auth-next/link-multiple-accounts.js @@ -182,3 +182,61 @@ function unlink(providerId) { }); // [END auth_unlink_provider] } + +function accountExistsPopup(auth, facebookProvider, goToApp, promptUserForPassword, promptUserForSignInMethod, getProviderForProviderId) { + // [START account_exists_popup] + const { signInWithPopup, signInWithEmailAndPassword, linkWithCredential } = require("firebase/auth"); + + // User tries to sign in with Facebook. + signInWithPopup(auth, facebookProvider).catch((error) => { + // User's email already exists. + if (error.code === 'auth/account-exists-with-different-credential') { + // The pending Facebook credential. + const pendingCred = error.credential; + // The provider account's email address. + const email = error.customData.email; + + // Present the user with a list of providers they might have + // used to create the original account. + // Then, ask the user to sign in with the existing provider. + const method = promptUserForSignInMethod(); + + if (method === 'password') { + // TODO: Ask the user for their password. + // In real scenario, you should handle this asynchronously. + const password = promptUserForPassword(); + signInWithEmailAndPassword(auth, email, password).then((result) => { + return linkWithCredential(result.user, pendingCred); + }).then(() => { + // Facebook account successfully linked to the existing user. + goToApp(); + }); + return; + } + + // All other cases are external providers. + // Construct provider object for that provider. + // TODO: Implement getProviderForProviderId. + const provider = getProviderForProviderId(method); + // At this point, you should let the user know that they already have an + // account with a different provider, and validate they want to sign in + // with the new provider. + // Note: Browsers usually block popups triggered asynchronously, so in + // real app, you should ask the user to click on a "Continue" button + // that will trigger signInWithPopup(). + signInWithPopup(auth, provider).then((result) => { + // Note: Identity Platform doesn't control the provider's sign-in + // flow, so it's possible for the user to sign in with an account + // with a different email from the first one. + + // Link the Facebook credential. We have access to the pending + // credential, so we can directly call the link method. + linkWithCredential(result.user, pendingCred).then((userCred) => { + // Success. + goToApp(); + }); + }); + } +}); +// [END account_exists_popup] +} diff --git a/auth/link-multiple-accounts.js b/auth/link-multiple-accounts.js index 30f5a2ec..8eed77b8 100644 --- a/auth/link-multiple-accounts.js +++ b/auth/link-multiple-accounts.js @@ -166,3 +166,59 @@ function unlink(providerId) { }); // [END auth_unlink_provider] } + +function accountExistsPopup(facebookProvider, goToApp, promptUserForPassword, promptUserForSignInMethod, getProviderForProviderId) { + // [START account_exists_popup] + // User tries to sign in with Facebook. + auth.signInWithPopup(facebookProvider).catch((error) => { + // User's email already exists. + if (error.code === 'auth/account-exists-with-different-credential') { + // The pending Facebook credential. + const pendingCred = error.credential; + // The provider account's email address. + const email = error.email; + + // Present the user with a list of providers they might have + // used to create the original account. + // Then, ask the user to sign in with the existing provider. + const method = promptUserForSignInMethod(); + + if (method === 'password') { + // TODO: Ask the user for their password. + // In real scenario, you should handle this asynchronously. + const password = promptUserForPassword(); + auth.signInWithEmailAndPassword(email, password).then((result) => { + return result.user.linkWithCredential(pendingCred); + }).then(() => { + // Facebook account successfully linked to the existing user. + goToApp(); + }); + return; + } + + // All other cases are external providers. + // Construct provider object for that provider. + // TODO: Implement getProviderForProviderId. + const provider = getProviderForProviderId(method); + // At this point, you should let the user know that they already have an + // account with a different provider, and validate they want to sign in + // with the new provider. + // Note: Browsers usually block popups triggered asynchronously, so in + // real app, you should ask the user to click on a "Continue" button + // that will trigger signInWithPopup(). + auth.signInWithPopup(provider).then((result) => { + // Note: Identity Platform doesn't control the provider's sign-in + // flow, so it's possible for the user to sign in with an account + // with a different email from the first one. + + // Link the Facebook credential. We have access to the pending + // credential, so we can directly call the link method. + result.user.linkWithCredential(pendingCred).then((userCred) => { + // Success. + goToApp(); + }); + }); + } +}); +// [END account_exists_popup] +} diff --git a/snippets/auth-next/link-multiple-accounts/account_exists_popup.js b/snippets/auth-next/link-multiple-accounts/account_exists_popup.js new file mode 100644 index 00000000..2c667882 --- /dev/null +++ b/snippets/auth-next/link-multiple-accounts/account_exists_popup.js @@ -0,0 +1,61 @@ +// This snippet file was generated by processing the source file: +// ./auth-next/link-multiple-accounts.js +// +// To update the snippets in this file, edit the source and then run +// 'npm run snippets'. + + // [START account_exists_popup_modular] + import { signInWithPopup, signInWithEmailAndPassword, linkWithCredential } from "firebase/auth"; + + // User tries to sign in with Facebook. + signInWithPopup(auth, facebookProvider).catch((error) => { + // User's email already exists. + if (error.code === 'auth/account-exists-with-different-credential') { + // The pending Facebook credential. + const pendingCred = error.credential; + // The provider account's email address. + const email = error.customData.email; + + // Present the user with a list of providers they might have + // used to create the original account. + // Then, ask the user to sign in with the existing provider. + const method = promptUserForSignInMethod(); + + if (method === 'password') { + // TODO: Ask the user for their password. + // In real scenario, you should handle this asynchronously. + const password = promptUserForPassword(); + signInWithEmailAndPassword(auth, email, password).then((result) => { + return linkWithCredential(result.user, pendingCred); + }).then(() => { + // Facebook account successfully linked to the existing user. + goToApp(); + }); + return; + } + + // All other cases are external providers. + // Construct provider object for that provider. + // TODO: Implement getProviderForProviderId. + const provider = getProviderForProviderId(method); + // At this point, you should let the user know that they already have an + // account with a different provider, and validate they want to sign in + // with the new provider. + // Note: Browsers usually block popups triggered asynchronously, so in + // real app, you should ask the user to click on a "Continue" button + // that will trigger signInWithPopup(). + signInWithPopup(auth, provider).then((result) => { + // Note: Identity Platform doesn't control the provider's sign-in + // flow, so it's possible for the user to sign in with an account + // with a different email from the first one. + + // Link the Facebook credential. We have access to the pending + // credential, so we can directly call the link method. + linkWithCredential(result.user, pendingCred).then((userCred) => { + // Success. + goToApp(); + }); + }); + } +}); +// [END account_exists_popup_modular] \ No newline at end of file From 2117c619ce49b08d582f282e7d2ec798f5105c3d Mon Sep 17 00:00:00 2001 From: spider-hand Date: Wed, 29 May 2024 01:05:44 +0900 Subject: [PATCH 35/38] chore: update outdated comments (#370) --- auth-next/email-link-auth.js | 10 ++++++---- .../auth-next/email-link-auth/email_link_complete.js | 10 ++++++---- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/auth-next/email-link-auth.js b/auth-next/email-link-auth.js index 59ea2115..4748e699 100644 --- a/auth-next/email-link-auth.js +++ b/auth-next/email-link-auth.js @@ -68,11 +68,13 @@ function emailLinkComplete() { .then((result) => { // Clear email from storage. window.localStorage.removeItem('emailForSignIn'); - // You can access the new user via result.user - // Additional user info profile not available via: - // result.additionalUserInfo.profile == null + // You can access the new user by importing getAdditionalUserInfo + // and calling it with result: + // getAdditionalUserInfo(result) + // You can access the user's profile via: + // getAdditionalUserInfo(result)?.profile // You can check if the user is new or existing: - // result.additionalUserInfo.isNewUser + // getAdditionalUserInfo(result)?.isNewUser }) .catch((error) => { // Some error occurred, you can inspect the code: error.code diff --git a/snippets/auth-next/email-link-auth/email_link_complete.js b/snippets/auth-next/email-link-auth/email_link_complete.js index b42b9af9..dbe1143d 100644 --- a/snippets/auth-next/email-link-auth/email_link_complete.js +++ b/snippets/auth-next/email-link-auth/email_link_complete.js @@ -26,11 +26,13 @@ if (isSignInWithEmailLink(auth, window.location.href)) { .then((result) => { // Clear email from storage. window.localStorage.removeItem('emailForSignIn'); - // You can access the new user via result.user - // Additional user info profile not available via: - // result.additionalUserInfo.profile == null + // You can access the new user by importing getAdditionalUserInfo + // and calling it with result: + // getAdditionalUserInfo(result) + // You can access the user's profile via: + // getAdditionalUserInfo(result)?.profile // You can check if the user is new or existing: - // result.additionalUserInfo.isNewUser + // getAdditionalUserInfo(result)?.isNewUser }) .catch((error) => { // Some error occurred, you can inspect the code: error.code From 56d70627e2dc275f01cd0e55699794bf40faca80 Mon Sep 17 00:00:00 2001 From: Daniel La Rocque Date: Tue, 8 Oct 2024 15:17:01 -0400 Subject: [PATCH 36/38] Upgrade versions in FCM service worker (#382) * Upgrade versions in FCM service worker * Add comment telling users to use latest --- messaging/service-worker.js | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/messaging/service-worker.js b/messaging/service-worker.js index c0f875bb..1a202159 100644 --- a/messaging/service-worker.js +++ b/messaging/service-worker.js @@ -10,8 +10,9 @@ function initInSw() { // Give the service worker access to Firebase Messaging. // Note that you can only use Firebase Messaging here. Other Firebase libraries // are not available in the service worker. - importScripts('https://www.gstatic.com/firebasejs/8.10.1/firebase-app.js'); - importScripts('https://www.gstatic.com/firebasejs/8.10.1/firebase-messaging.js'); + // Replace 10.13.2 with latest version of the Firebase JS SDK. + importScripts('https://www.gstatic.com/firebasejs/10.13.2/firebase-app-compat.js'); + importScripts('https://www.gstatic.com/firebasejs/10.13.2/firebase-messaging-compat.js'); // Initialize the Firebase app in the service worker by passing in // your app's Firebase config object. From 3d04522869ad402c4da3ae74d6b30a4dbf8d1233 Mon Sep 17 00:00:00 2001 From: Athira M Date: Fri, 24 Jan 2025 12:17:10 +0530 Subject: [PATCH 37/38] RC doc update to provide default prod value for minimumFetchIntervalMillis (#389) * Add comment to highlight the default prod value for minimumFetchIntervalMillis. Issue addressed: https://github.com/firebase/firebase-js-sdk/issues/2841 * Update code snipped with default prod value for minimumFetchIntervalMillis. * Update code snipped with default prod value for minimumFetchIntervalMillis. * Update code snipped with default prod value for minimumFetchIntervalMillis. --------- Co-authored-by: Athira M --- remoteconfig-next/index.js | 1 + snippets/remoteconfig-next/index/rc_set_minimum_fetch_time.js | 1 + 2 files changed, 2 insertions(+) diff --git a/remoteconfig-next/index.js b/remoteconfig-next/index.js index aeeb263a..287f3c99 100644 --- a/remoteconfig-next/index.js +++ b/remoteconfig-next/index.js @@ -14,6 +14,7 @@ function getInstance() { function setMinimumFetchTime() { const remoteConfig = getInstance(); // [START rc_set_minimum_fetch_time] + // The default and recommended production fetch interval for Remote Config is 12 hours remoteConfig.settings.minimumFetchIntervalMillis = 3600000; // [END rc_set_minimum_fetch_time] } diff --git a/snippets/remoteconfig-next/index/rc_set_minimum_fetch_time.js b/snippets/remoteconfig-next/index/rc_set_minimum_fetch_time.js index 131976c5..77aa9f45 100644 --- a/snippets/remoteconfig-next/index/rc_set_minimum_fetch_time.js +++ b/snippets/remoteconfig-next/index/rc_set_minimum_fetch_time.js @@ -5,5 +5,6 @@ // 'npm run snippets'. // [START rc_set_minimum_fetch_time_modular] +// The default and recommended production fetch interval for Remote Config is 12 hours remoteConfig.settings.minimumFetchIntervalMillis = 3600000; // [END rc_set_minimum_fetch_time_modular] \ No newline at end of file From 467eaa165dcbd9b3ab15711e76fa52237ba37f8b Mon Sep 17 00:00:00 2001 From: "Nhien (Ricky) Lam" <62775270+NhienLam@users.noreply.github.com> Date: Thu, 6 Feb 2025 15:39:06 -0800 Subject: [PATCH 38/38] Update email link auth snippet to stop using deprecated `dynamicLinkDomain` (#390) * Update email link auth snippet to remove FDL * Update custom domain example --- auth-next/email-link-auth.js | 3 ++- .../email-link-auth/auth_email_link_actioncode_settings.js | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/auth-next/email-link-auth.js b/auth-next/email-link-auth.js index 4748e699..fde67663 100644 --- a/auth-next/email-link-auth.js +++ b/auth-next/email-link-auth.js @@ -19,7 +19,8 @@ function emailLinkActionCodeSettings() { installApp: true, minimumVersion: '12' }, - dynamicLinkDomain: 'example.page.link' + // The domain must be configured in Firebase Hosting and owned by the project. + linkDomain: 'custom-domain.com' }; // [END auth_email_link_actioncode_settings] } diff --git a/snippets/auth-next/email-link-auth/auth_email_link_actioncode_settings.js b/snippets/auth-next/email-link-auth/auth_email_link_actioncode_settings.js index a1480a11..010b5c09 100644 --- a/snippets/auth-next/email-link-auth/auth_email_link_actioncode_settings.js +++ b/snippets/auth-next/email-link-auth/auth_email_link_actioncode_settings.js @@ -19,6 +19,7 @@ const actionCodeSettings = { installApp: true, minimumVersion: '12' }, - dynamicLinkDomain: 'example.page.link' + // The domain must be configured in Firebase Hosting and owned by the project. + linkDomain: 'custom-domain.com' }; // [END auth_email_link_actioncode_settings_modular] \ No newline at end of file