Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 0 additions & 15 deletions docs/openapi.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -5409,8 +5409,6 @@ paths:
$ref: "#/components/schemas/AccountApp/properties/clientType"
redirectURIs:
$ref: "#/components/schemas/AccountApp/properties/redirectURIs"
allowedOrigins:
$ref: "#/components/schemas/AccountApp/properties/allowedOrigins"
responses:
"201":
description: Account app created.
Expand Down Expand Up @@ -5489,8 +5487,6 @@ paths:
$ref: "#/components/schemas/AccountApp/properties/status"
redirectURIs:
$ref: "#/components/schemas/AccountApp/properties/redirectURIs"
allowedOrigins:
$ref: "#/components/schemas/AccountApp/properties/allowedOrigins"
responses:
"200":
description: Account app updated.
Expand Down Expand Up @@ -6667,7 +6663,6 @@ components:
- status
- redirectURIs
- redirectURIPatterns
- allowedOrigins
properties:
id:
$ref: "#/components/schemas/Model/properties/id"
Expand Down Expand Up @@ -6743,16 +6738,6 @@ components:
type: string
examples:
- - https://app-*.example.com/oauth/callback
allowedOrigins:
description: |
Allowed web origins.

Production web origins must use `https`, must not include path, query, or fragment, and must be matched
exactly by the server.
type: array
items:
type: string
format: uri

AccountAppSecret:
type: object
Expand Down
2 changes: 0 additions & 2 deletions spx-gui/src/apis/account/common.ts
Original file line number Diff line number Diff line change
Expand Up @@ -70,8 +70,6 @@ export type AccountApp = AccountModel & {
redirectURIs: string[]
/** Read-only allowed redirect URI patterns */
redirectURIPatterns: string[]
/** Allowed web origins */
allowedOrigins: string[]
}

export type AccountAppSecret = {
Expand Down
4 changes: 0 additions & 4 deletions spx-gui/src/apis/admin/account.ts
Original file line number Diff line number Diff line change
Expand Up @@ -194,8 +194,6 @@ export type CreateAccountAppParams = {
clientType: AccountAppClientType
/** Allowed redirect URIs */
redirectURIs: string[]
/** Allowed web origins */
allowedOrigins?: string[]
}

export function createAccountApp(params: CreateAccountAppParams) {
Expand All @@ -213,8 +211,6 @@ export type UpdateAccountAppParams = {
status?: AccountAppStatus
/** Allowed redirect URIs */
redirectURIs?: string[]
/** Allowed web origins */
allowedOrigins?: string[]
}

export function updateAccountApp(appID: string, params: UpdateAccountAppParams) {
Expand Down
34 changes: 9 additions & 25 deletions spx-gui/src/apps/xbuilder/pages/admin/app.vue
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ import CopyButton from '@/components/common/CopyButton.vue'
import UIIcon from '@/components/ui/icons/UIIcon.vue'
import * as accountAdminApis from '@/apis/admin/account'
import {
accountAppAllowedOriginsTip,
accountAppClientTypeLabels,
accountAppRedirectURIPatternsTip,
accountAppRedirectURIsTip,
Expand Down Expand Up @@ -52,11 +51,9 @@ usePageTitle(() =>
const displayName = ref('')
const status = ref<accountAdminApis.AccountApp['status']>('active')
const redirectURIs = ref('')
const allowedOrigins = ref('')
const savedDisplayName = ref('')
const savedStatus = ref<accountAdminApis.AccountApp['status']>('active')
const savedRedirectURIs = ref<string[]>([])
const savedAllowedOrigins = ref<string[]>([])
const appUpdatedAt = ref('')
const appFallbackText = computed(() => displayName.value.trim().charAt(0).toUpperCase() || '?')
const trimmedDisplayName = computed(() => displayName.value.trim())
Expand All @@ -68,28 +65,22 @@ watch(
displayName.value = value.displayName
status.value = value.status
redirectURIs.value = value.redirectURIs.join('\n')
allowedOrigins.value = value.allowedOrigins.join('\n')
savedDisplayName.value = value.displayName
savedStatus.value = value.status
savedRedirectURIs.value = value.redirectURIs
savedAllowedOrigins.value = value.allowedOrigins
appUpdatedAt.value = value.updatedAt
},
{ immediate: true }
)

const parsedRedirectURIs = computed(() => parseLines(redirectURIs.value))
const parsedAllowedOrigins = computed(() => parseLines(allowedOrigins.value))
const isActive = computed(() => status.value === 'active')
const isIdentityChanged = computed(
() => trimmedDisplayName.value !== '' && trimmedDisplayName.value !== savedDisplayName.value
)
const isStatusChanged = computed(() => status.value !== savedStatus.value)
const areEndpointsChanged = computed(
() =>
parsedRedirectURIs.value.length > 0 &&
(!areStringListsEqual(parsedRedirectURIs.value, savedRedirectURIs.value) ||
!areStringListsEqual(parsedAllowedOrigins.value, savedAllowedOrigins.value))
const areRedirectURIsChanged = computed(
() => parsedRedirectURIs.value.length > 0 && !areStringListsEqual(parsedRedirectURIs.value, savedRedirectURIs.value)
)

function areStringListsEqual(a: string[], b: string[]) {
Expand Down Expand Up @@ -123,14 +114,12 @@ const handleUpdateIdentity = useMessageHandle(
{ en: 'App identity updated', zh: '应用信息已更新' }
)

const handleUpdateEndpoints = useMessageHandle(
const handleUpdateRedirectURIs = useMessageHandle(
async () => {
const updated = await accountAdminApis.updateAccountApp(props.appID, {
redirectURIs: parsedRedirectURIs.value,
allowedOrigins: parsedAllowedOrigins.value
redirectURIs: parsedRedirectURIs.value
})
savedRedirectURIs.value = updated.redirectURIs
savedAllowedOrigins.value = updated.allowedOrigins
appUpdatedAt.value = updated.updatedAt
},
{ en: 'Failed to update OAuth endpoints', zh: '更新 OAuth 地址配置失败' },
Expand Down Expand Up @@ -339,13 +328,13 @@ function deleteSecret(secretID: string) {
<p class="m-0 mt-1 text-sm text-grey-800">
{{
$t({
en: 'Exact destinations and browser origins trusted by this app.',
zh: '此应用信任的精确回调地址和浏览器来源。'
en: 'Exact callback destinations trusted by this app.',
zh: '此应用信任的精确回调地址。'
})
}}
</p>
</div>
<form class="flex flex-col gap-5" @submit.prevent="handleUpdateEndpoints.fn">
<form class="flex flex-col gap-5" @submit.prevent="handleUpdateRedirectURIs.fn">
<label class="flex flex-col gap-1 text-sm text-grey-900">
{{ $t({ en: 'Redirect URIs', zh: '回调 URI' }) }}
<UITextInput v-model:value="redirectURIs" type="textarea" :rows="5" />
Expand All @@ -364,17 +353,12 @@ function deleteSecret(secretID: string) {
</div>
<span class="text-xs text-grey-700">{{ $t(accountAppRedirectURIPatternsTip) }}</span>
</div>
<label class="flex flex-col gap-1 text-sm text-grey-900">
{{ $t({ en: 'Allowed origins', zh: '允许的 Origin' }) }}
<UITextInput v-model:value="allowedOrigins" type="textarea" :rows="4" />
<span class="text-xs text-grey-700">{{ $t(accountAppAllowedOriginsTip) }}</span>
</label>
<div class="flex justify-end">
<UIButton
html-type="submit"
type="primary"
:disabled="!areEndpointsChanged"
:loading="handleUpdateEndpoints.isLoading.value"
:disabled="!areRedirectURIsChanged"
:loading="handleUpdateRedirectURIs.isLoading.value"
>
{{ $t({ en: 'Save endpoint settings', zh: '保存地址配置' }) }}
</UIButton>
Expand Down
13 changes: 2 additions & 11 deletions spx-gui/src/apps/xbuilder/pages/admin/apps.vue
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import { useSignedInStateQuery } from '@/stores/user'
import { UIButton, UIError, UILoading, UIPagination, UISelect, UISelectOption, UITextInput } from '@/components/ui'
import * as accountAdminApis from '@/apis/admin/account'
import {
accountAppAllowedOriginsTip,
accountAppClientTypeLabels,
accountAppRedirectURIsTip,
accountAppStatusLabels,
Expand All @@ -33,8 +32,7 @@ const createForm = reactive({
name: '',
displayName: '',
clientType: 'public' as accountAdminApis.AccountApp['clientType'],
redirectURIs: '',
allowedOrigins: ''
redirectURIs: ''
})

const appsQuery = useQuery(
Expand All @@ -60,8 +58,7 @@ const handleCreateApp = useMessageHandle(
name: createForm.name.trim(),
displayName: createForm.displayName.trim(),
clientType: createForm.clientType,
redirectURIs: parseLines(createForm.redirectURIs),
allowedOrigins: parseLines(createForm.allowedOrigins)
redirectURIs: parseLines(createForm.redirectURIs)
})
await router.push(`/admin/apps/${encodeURIComponent(app.id)}`)
},
Expand Down Expand Up @@ -110,17 +107,11 @@ const handleCreateApp = useMessageHandle(
<UISelectOption value="confidential">{{ $t(accountAppClientTypeLabels.confidential) }}</UISelectOption>
</UISelect>
</label>
<div class="hidden tablet:block"></div>
<label class="flex flex-col gap-1 text-sm text-grey-900">
{{ $t({ en: 'Redirect URIs', zh: '回调 URI' }) }}
<UITextInput v-model:value="createForm.redirectURIs" type="textarea" :rows="4" />
<span class="text-xs text-grey-700">{{ $t(accountAppRedirectURIsTip) }}</span>
</label>
<label class="flex flex-col gap-1 text-sm text-grey-900">
{{ $t({ en: 'Allowed origins', zh: '允许的 Origin' }) }}
<UITextInput v-model:value="createForm.allowedOrigins" type="textarea" :rows="4" />
<span class="text-xs text-grey-700">{{ $t(accountAppAllowedOriginsTip) }}</span>
</label>
</div>
<div class="mt-4 flex justify-end">
<UIButton html-type="submit" type="primary" :loading="handleCreateApp.isLoading.value">
Expand Down
5 changes: 0 additions & 5 deletions spx-gui/src/apps/xbuilder/pages/admin/common.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,11 +28,6 @@ export const accountAppRedirectURIPatternsTip: LocaleMessage = {
zh: '用于受控预览或非生产回调域名的只读通配模式。精确回调 URI 仍是主要 allowlist;这组模式不通过公开 Admin API 管理,也不能在这里修改。'
}

export const accountAppAllowedOriginsTip: LocaleMessage = {
en: 'Origins allowed to host Account Web and receive identity provider callbacks for this app. Enter one origin per line, such as https://account.example.com. Do not include a path, query, or fragment.',
zh: '允许承载 Account Web 并接收本应用第三方身份提供商回调的 Origin。每行一个,例如 https://account.example.com;不要包含路径、查询参数或 fragment。'
}

export function formatTime(value: string) {
return dayjs(value).format('YYYY-MM-DD HH:mm')
}
Expand Down