mirror of
https://github.com/nocodb/nocodb.git
synced 2026-05-02 00:47:11 +00:00
feat: sync fw (#10671)
* feat: sync table init * feat: sync table (WIP) * feat: oauth flow for github * feat: sync feature flag * feat: progress for sync * feat: revise sync status * feat: incremental support for sync * feat: disable insert & delete operations on synced tables * feat: handle synced & readonly on frontend * test: apply system column order (always initial) * test: change wrong index * fix: PR requested changes * test: overlapping variable names
This commit is contained in:
90
packages/nc-gui/components/nc/form-builder/input/OAuth.vue
Normal file
90
packages/nc-gui/components/nc/form-builder/input/OAuth.vue
Normal file
@@ -0,0 +1,90 @@
|
||||
<script lang="ts" setup>
|
||||
import type { FormBuilderElement } from 'nocodb-sdk'
|
||||
|
||||
const props = defineProps<{
|
||||
value: string
|
||||
element: FormBuilderElement
|
||||
haveValue?: boolean
|
||||
}>()
|
||||
|
||||
const emits = defineEmits(['update:value'])
|
||||
|
||||
const vModel = useVModel(props, 'value', emits)
|
||||
|
||||
const OAuthConfig = computed(() => {
|
||||
return props.element.oauthMeta!
|
||||
})
|
||||
|
||||
const generateState = () => {
|
||||
return Math.random().toString(36).substring(2, 15) + Math.random().toString(36).substring(2, 15)
|
||||
}
|
||||
|
||||
const openPopup = (url: string, name: string, state: string, width = 500, height = 600) => {
|
||||
const left = window.screenX + (window.outerWidth - width) / 2
|
||||
const top = window.screenY + (window.outerHeight - height) / 2.5
|
||||
|
||||
// add state to the URL
|
||||
url += `&state=${state}`
|
||||
|
||||
const popup = window.open(url, name, `width=${width},height=${height},left=${left},top=${top}`)
|
||||
if (!popup) throw new Error('Popup blocked')
|
||||
|
||||
return new Promise<string | null>((resolve, reject) => {
|
||||
const interval = setInterval(() => {
|
||||
try {
|
||||
if (popup.closed) {
|
||||
clearInterval(interval)
|
||||
reject(new Error('Popup closed by user'))
|
||||
}
|
||||
|
||||
const url = popup.location.href
|
||||
if (url.includes(OAuthConfig.value.redirectUri)) {
|
||||
const params = new URL(url).searchParams
|
||||
const code = params.get(OAuthConfig.value.codeKey || 'code')
|
||||
if (code) {
|
||||
clearInterval(interval)
|
||||
|
||||
if (params.get('state') !== state) {
|
||||
reject(new Error('Invalid state please try again'))
|
||||
}
|
||||
|
||||
popup.close()
|
||||
resolve(code)
|
||||
} else {
|
||||
reject(new Error('No code returned'))
|
||||
}
|
||||
}
|
||||
} catch {
|
||||
// Cross-origin frame access error is expected, ignore it
|
||||
}
|
||||
}, 500)
|
||||
})
|
||||
}
|
||||
|
||||
const handleOAuth = async () => {
|
||||
const url = OAuthConfig.value.authUri
|
||||
const code = await openPopup(url, `${OAuthConfig.value.provider} OAuth`, generateState(), 500, 600)
|
||||
|
||||
if (!code) {
|
||||
message.error('Failed to authenticate using OAuth')
|
||||
return
|
||||
}
|
||||
|
||||
vModel.value = code
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div>
|
||||
<NcButton type="primary" @click="handleOAuth">
|
||||
<div class="flex items-center gap-2">
|
||||
<div class="font-bold">Authenticate With {{ OAuthConfig.provider }}</div>
|
||||
<template v-if="haveValue">
|
||||
<GeneralIcon icon="circleCheckSolid" class="text-success w-6 h-6 bg-white-500" />
|
||||
</template>
|
||||
</div>
|
||||
</NcButton>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style></style>
|
||||
@@ -0,0 +1,22 @@
|
||||
<script lang="ts" setup>
|
||||
const props = defineProps<{
|
||||
value: string
|
||||
}>()
|
||||
|
||||
const emits = defineEmits(['update:value'])
|
||||
|
||||
const vModel = useVModel(props, 'value', emits)
|
||||
|
||||
const basesStore = useBases()
|
||||
|
||||
const baseOptions = computed(() => {
|
||||
return basesStore.basesList.map((base) => ({
|
||||
label: base.title,
|
||||
value: base.id,
|
||||
}))
|
||||
})
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<NcSelect v-model:value="vModel" :options="baseOptions" />
|
||||
</template>
|
||||
Reference in New Issue
Block a user