feat: load allowed login methods from .env (#3264)

Co-authored-by: Andrew Bastin <andrewbastin.k@gmail.com>
This commit is contained in:
Akash K
2023-08-18 21:23:56 +05:30
committed by GitHub
parent c626fb9241
commit ce7adf6da3

View File

@@ -9,27 +9,12 @@
<template #body> <template #body>
<div v-if="mode === 'sign-in'" class="flex flex-col space-y-2"> <div v-if="mode === 'sign-in'" class="flex flex-col space-y-2">
<HoppSmartItem <HoppSmartItem
:loading="signingInWithGitHub" v-for="provider in allowedAuthProviders"
:icon="IconGithub" :key="provider.id"
:label="`${t('auth.continue_with_github')}`" :loading="provider.isLoading.value"
@click="signInWithGithub" :icon="provider.icon"
/> :label="provider.label"
<HoppSmartItem @click="provider.action"
:loading="signingInWithGoogle"
:icon="IconGoogle"
:label="`${t('auth.continue_with_google')}`"
@click="signInWithGoogle"
/>
<HoppSmartItem
:loading="signingInWithMicrosoft"
:icon="IconMicrosoft"
:label="`${t('auth.continue_with_microsoft')}`"
@click="signInWithMicrosoft"
/>
<HoppSmartItem
:icon="IconEmail"
:label="`${t('auth.continue_with_email')}`"
@click="mode = 'email'"
/> />
<hr v-if="additonalLoginItems.length > 0" /> <hr v-if="additonalLoginItems.length > 0" />
@@ -123,76 +108,80 @@
</HoppSmartModal> </HoppSmartModal>
</template> </template>
<script lang="ts"> <script setup lang="ts">
import { defineComponent, computed } from "vue" import { Ref, computed, onMounted, ref } from "vue"
import { useStreamSubscriber } from "@composables/stream"
import { useToast } from "@composables/toast"
import { useI18n } from "@composables/i18n"
import { platform } from "~/platform" import { platform } from "~/platform"
import { setLocalConfig } from "~/newstore/localpersistence"
import IconGithub from "~icons/auth/github" import IconGithub from "~icons/auth/github"
import IconGoogle from "~icons/auth/google" import IconGoogle from "~icons/auth/google"
import IconEmail from "~icons/auth/email" import IconEmail from "~icons/auth/email"
import IconMicrosoft from "~icons/auth/microsoft" import IconMicrosoft from "~icons/auth/microsoft"
import IconArrowLeft from "~icons/lucide/arrow-left" import IconArrowLeft from "~icons/lucide/arrow-left"
import { setLocalConfig } from "~/newstore/localpersistence"
import { useStreamSubscriber } from "@composables/stream"
import { useToast } from "@composables/toast"
import { useI18n } from "@composables/i18n"
import { LoginItemDef } from "~/platform/auth" import { LoginItemDef } from "~/platform/auth"
export default defineComponent({ defineProps<{
props: { show: boolean
show: Boolean, }>()
},
emits: ["hide-modal"], const emit = defineEmits<{
setup() { (e: "hide-modal"): void
}>()
const { subscribeToStream } = useStreamSubscriber() const { subscribeToStream } = useStreamSubscriber()
const t = useI18n()
const toast = useToast()
const form = {
email: "",
}
const signingInWithGoogle = ref(false)
const signingInWithGitHub = ref(false)
const signingInWithMicrosoft = ref(false)
const signingInWithEmail = ref(false)
const mode = ref("sign-in")
const tosLink = import.meta.env.VITE_APP_TOS_LINK const tosLink = import.meta.env.VITE_APP_TOS_LINK
const privacyPolicyLink = import.meta.env.VITE_APP_PRIVACY_POLICY_LINK const privacyPolicyLink = import.meta.env.VITE_APP_PRIVACY_POLICY_LINK
return { type AuthProviderItem = {
subscribeToStream, id: string
t: useI18n(), icon: typeof IconGithub
additonalLoginItems: computed( label: string
action: (...args: any[]) => any
isLoading: Ref<boolean>
}
const additonalLoginItems = computed(
() => platform.auth.additionalLoginItems ?? [] () => platform.auth.additionalLoginItems ?? []
), )
toast: useToast(),
IconGithub, const doAdditionalLoginItemClickAction = async (item: LoginItemDef) => {
IconGoogle, await item.onClick()
IconEmail, emit("hide-modal")
IconMicrosoft,
IconArrowLeft,
tosLink,
privacyPolicyLink,
} }
},
data() { onMounted(() => {
return {
form: {
email: "",
},
signingInWithGoogle: false,
signingInWithGitHub: false,
signingInWithMicrosoft: false,
signingInWithEmail: false,
mode: "sign-in",
}
},
mounted() {
const currentUser$ = platform.auth.getCurrentUserStream() const currentUser$ = platform.auth.getCurrentUserStream()
this.subscribeToStream(currentUser$, (user) => { subscribeToStream(currentUser$, (user) => {
if (user) this.hideModal() if (user) hideModal()
}) })
}, })
methods: {
async doAdditionalLoginItemClickAction(item: LoginItemDef) { const showLoginSuccess = () => {
await item.onClick() toast.success(`${t("auth.login_success")}`)
this.$emit("hide-modal") }
},
showLoginSuccess() { const signInWithGoogle = async () => {
this.toast.success(`${this.t("auth.login_success")}`) signingInWithGoogle.value = true
},
async signInWithGoogle() {
this.signingInWithGoogle = true
try { try {
await platform.auth.signInUserWithGoogle() await platform.auth.signInUserWithGoogle()
@@ -202,32 +191,33 @@ export default defineComponent({
A auth/account-exists-with-different-credential Firebase error wont happen between Google and any other providers A auth/account-exists-with-different-credential Firebase error wont happen between Google and any other providers
Seems Google account overwrites accounts of other providers https://github.com/firebase/firebase-android-sdk/issues/25 Seems Google account overwrites accounts of other providers https://github.com/firebase/firebase-android-sdk/issues/25
*/ */
this.toast.error(`${this.t("error.something_went_wrong")}`) toast.error(`${t("error.something_went_wrong")}`)
} }
this.signingInWithGoogle = false signingInWithGoogle.value = false
}, }
async signInWithGithub() {
this.signingInWithGitHub = true const signInWithGithub = async () => {
signingInWithGitHub.value = true
const result = await platform.auth.signInUserWithGithub() const result = await platform.auth.signInUserWithGithub()
if (!result) { if (!result) {
this.signingInWithGitHub = false signingInWithGitHub.value = false
return return
} }
if (result.type === "success") { if (result.type === "success") {
// this.showLoginSuccess() // this.showLoginSuccess()
} else if (result.type === "account-exists-with-different-cred") { } else if (result.type === "account-exists-with-different-cred") {
this.toast.info(`${this.t("auth.account_exists")}`, { toast.info(`${t("auth.account_exists")}`, {
duration: 0, duration: 0,
closeOnSwipe: false, closeOnSwipe: false,
action: { action: {
text: `${this.t("action.yes")}`, text: `${t("action.yes")}`,
onClick: async (_, toastObject) => { onClick: async (_, toastObject) => {
await result.link() await result.link()
this.showLoginSuccess() showLoginSuccess()
toastObject.goAway(0) toastObject.goAway(0)
}, },
@@ -235,13 +225,14 @@ export default defineComponent({
}) })
} else { } else {
console.log("error logging into github", result.err) console.log("error logging into github", result.err)
this.toast.error(`${this.t("error.something_went_wrong")}`) toast.error(`${t("error.something_went_wrong")}`)
} }
this.signingInWithGitHub = false signingInWithGitHub.value = false
}, }
async signInWithMicrosoft() {
this.signingInWithMicrosoft = true const signInWithMicrosoft = async () => {
signingInWithMicrosoft.value = true
try { try {
await platform.auth.signInUserWithMicrosoft() await platform.auth.signInUserWithMicrosoft()
@@ -256,34 +247,82 @@ export default defineComponent({
@firebase/auth: Auth (9.6.11): INTERNAL ASSERTION FAILED: Pending promise was never set @firebase/auth: Auth (9.6.11): INTERNAL ASSERTION FAILED: Pending promise was never set
They may be related to https://github.com/firebase/firebaseui-web/issues/947 They may be related to https://github.com/firebase/firebaseui-web/issues/947
*/ */
this.toast.error(`${this.t("error.something_went_wrong")}`) toast.error(`${t("error.something_went_wrong")}`)
} }
this.signingInWithMicrosoft = false signingInWithMicrosoft.value = false
}, }
async signInWithEmail() {
this.signingInWithEmail = true const signInWithEmail = async () => {
signingInWithEmail.value = true
await platform.auth await platform.auth
.signInWithEmail(this.form.email) .signInWithEmail(form.email)
.then(() => { .then(() => {
this.mode = "email-sent" mode.value = "email-sent"
setLocalConfig("emailForSignIn", this.form.email) setLocalConfig("emailForSignIn", form.email)
}) })
.catch((e) => { .catch((e) => {
console.error(e) console.error(e)
this.toast.error(e.message) toast.error(e.message)
this.signingInWithEmail = false signingInWithEmail.value = false
}) })
.finally(() => { .finally(() => {
this.signingInWithEmail = false signingInWithEmail.value = false
}) })
}
const hideModal = () => {
mode.value = "sign-in"
toast.clear()
emit("hide-modal")
}
const authProviders: AuthProviderItem[] = [
{
id: "GITHUB",
icon: IconGithub,
label: t("auth.continue_with_github"),
action: signInWithGithub,
isLoading: signingInWithGitHub,
}, },
hideModal() { {
this.mode = "sign-in" id: "GOOGLE",
this.toast.clear() icon: IconGoogle,
this.$emit("hide-modal") label: t("auth.continue_with_google"),
action: signInWithGoogle,
isLoading: signingInWithGoogle,
}, },
{
id: "MICROSOFT",
icon: IconMicrosoft,
label: t("auth.continue_with_microsoft"),
action: signInWithMicrosoft,
isLoading: signingInWithMicrosoft,
}, },
}) {
id: "EMAIL",
icon: IconEmail,
label: t("auth.continue_with_email"),
action: () => {
mode.value = "email"
},
isLoading: signingInWithEmail,
},
]
const allowedAuthProvidersIDsString: string | undefined = import.meta.env
.VITE_ALLOWED_AUTH_PROVIDERS
const allowedAuthProvidersIDs = allowedAuthProvidersIDsString
? allowedAuthProvidersIDsString.split(",")
: []
const allowedAuthProviders =
allowedAuthProvidersIDs.length > 0
? authProviders.filter((provider) =>
allowedAuthProvidersIDs.includes(provider.id)
)
: authProviders
</script> </script>