mirror of
https://gitee.com/mateos/mateclaw.git
synced 2026-09-15 20:08:18 +08:00
fix(workspace): keep workspace ids as strings so a switch survives reload
This commit is contained in:
parent
651d53050e
commit
92d35a3d3d
@ -87,7 +87,7 @@ export const authApi = {
|
|||||||
http.post('/auth/login', data),
|
http.post('/auth/login', data),
|
||||||
listUsers: () => http.get('/auth/users'),
|
listUsers: () => http.get('/auth/users'),
|
||||||
createUser: (data: any) => http.post('/auth/users', data),
|
createUser: (data: any) => http.post('/auth/users', data),
|
||||||
changePassword: (id: number, oldPassword: string, newPassword: string) =>
|
changePassword: (id: string | number, oldPassword: string, newPassword: string) =>
|
||||||
http.put(`/auth/users/${id}/password`, null, { params: { oldPassword, newPassword } }),
|
http.put(`/auth/users/${id}/password`, null, { params: { oldPassword, newPassword } }),
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -953,7 +953,7 @@ export const hotCacheApi = {
|
|||||||
|
|
||||||
export interface WorkflowSummary {
|
export interface WorkflowSummary {
|
||||||
id: number
|
id: number
|
||||||
workspaceId: number
|
workspaceId: string | number
|
||||||
name: string
|
name: string
|
||||||
description?: string
|
description?: string
|
||||||
enabled: boolean
|
enabled: boolean
|
||||||
@ -985,7 +985,7 @@ export interface WorkflowRun {
|
|||||||
id: number
|
id: number
|
||||||
workflowId: number
|
workflowId: number
|
||||||
revisionId: number
|
revisionId: number
|
||||||
workspaceId: number
|
workspaceId: string | number
|
||||||
state: string
|
state: string
|
||||||
triggeredBy?: string
|
triggeredBy?: string
|
||||||
initialInputRef?: string
|
initialInputRef?: string
|
||||||
@ -1048,7 +1048,7 @@ export interface ResumeResponse {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export const workflowApi = {
|
export const workflowApi = {
|
||||||
list: (workspaceId: number) =>
|
list: (workspaceId: string | number) =>
|
||||||
http.get<WorkflowSummary[]>('/workflows', { params: { workspaceId } }),
|
http.get<WorkflowSummary[]>('/workflows', { params: { workspaceId } }),
|
||||||
get: (id: number) => http.get<WorkflowSummary>(`/workflows/${id}`),
|
get: (id: number) => http.get<WorkflowSummary>(`/workflows/${id}`),
|
||||||
create: (data: Partial<WorkflowSummary>) =>
|
create: (data: Partial<WorkflowSummary>) =>
|
||||||
@ -1119,7 +1119,7 @@ export interface WorkflowDraftTemplate {
|
|||||||
|
|
||||||
export interface TriggerSummary {
|
export interface TriggerSummary {
|
||||||
id: number
|
id: number
|
||||||
workspaceId: number
|
workspaceId: string | number
|
||||||
name?: string
|
name?: string
|
||||||
patternType: string
|
patternType: string
|
||||||
patternJson: string
|
patternJson: string
|
||||||
@ -1149,7 +1149,7 @@ export interface TriggerSummary {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export const triggerApi = {
|
export const triggerApi = {
|
||||||
list: (workspaceId: number) =>
|
list: (workspaceId: string | number) =>
|
||||||
http.get<TriggerSummary[]>('/triggers', { params: { workspaceId } }),
|
http.get<TriggerSummary[]>('/triggers', { params: { workspaceId } }),
|
||||||
get: (id: number) => http.get<TriggerSummary>(`/triggers/${id}`),
|
get: (id: number) => http.get<TriggerSummary>(`/triggers/${id}`),
|
||||||
create: (data: Partial<TriggerSummary>) =>
|
create: (data: Partial<TriggerSummary>) =>
|
||||||
@ -1158,7 +1158,7 @@ export const triggerApi = {
|
|||||||
http.put<TriggerSummary>(`/triggers/${id}`, data),
|
http.put<TriggerSummary>(`/triggers/${id}`, data),
|
||||||
delete: (id: number) => http.delete(`/triggers/${id}`),
|
delete: (id: number) => http.delete(`/triggers/${id}`),
|
||||||
ingestEvent: (envelope: {
|
ingestEvent: (envelope: {
|
||||||
workspaceId: number
|
workspaceId: string | number
|
||||||
patternType: string
|
patternType: string
|
||||||
eventId?: string
|
eventId?: string
|
||||||
senderId?: string
|
senderId?: string
|
||||||
|
|||||||
@ -107,7 +107,7 @@ async function handleSubmit() {
|
|||||||
}
|
}
|
||||||
submitting.value = true
|
submitting.value = true
|
||||||
try {
|
try {
|
||||||
const userId = Number(localStorage.getItem('userId') || '1')
|
const userId = localStorage.getItem('userId') || '1'
|
||||||
await authApi.changePassword(userId, form.oldPassword, form.newPassword)
|
await authApi.changePassword(userId, form.oldPassword, form.newPassword)
|
||||||
mcToast.success(t('auth.passwordChanged'))
|
mcToast.success(t('auth.passwordChanged'))
|
||||||
close()
|
close()
|
||||||
|
|||||||
@ -397,7 +397,7 @@ function hasUnread(conv: Conversation): boolean {
|
|||||||
if (!Number.isFinite(lastActive)) return false
|
if (!Number.isFinite(lastActive)) return false
|
||||||
let viewed = 0
|
let viewed = 0
|
||||||
try {
|
try {
|
||||||
viewed = Number(localStorage.getItem(VIEWED_KEY_PREFIX + conv.conversationId) || '0')
|
viewed = Number(localStorage.getItem(VIEWED_KEY_PREFIX + conv.conversationId) || '0') // snowflake-precision-ok: stored value is a last-viewed epoch-ms timestamp, not an id
|
||||||
} catch {
|
} catch {
|
||||||
// Treat as never-viewed when storage is unavailable.
|
// Treat as never-viewed when storage is unavailable.
|
||||||
}
|
}
|
||||||
|
|||||||
@ -127,7 +127,7 @@ onMounted(() => {
|
|||||||
store.fetchWorkspaces()
|
store.fetchWorkspaces()
|
||||||
})
|
})
|
||||||
|
|
||||||
function onSelect(id: number) {
|
function onSelect(id: string) {
|
||||||
open.value = false
|
open.value = false
|
||||||
if (id !== currentWorkspaceId.value) {
|
if (id !== currentWorkspaceId.value) {
|
||||||
store.switchWorkspace(id)
|
store.switchWorkspace(id)
|
||||||
|
|||||||
@ -5,12 +5,14 @@ import type { Capability, WorkspaceRole } from '@/composables/capabilities'
|
|||||||
import { ROLE_LEVEL } from '@/composables/capabilities'
|
import { ROLE_LEVEL } from '@/composables/capabilities'
|
||||||
|
|
||||||
export interface Workspace {
|
export interface Workspace {
|
||||||
id: number
|
// Backend-issued Snowflake id — kept as a string for its whole lifecycle so a
|
||||||
|
// Number() round-trip never truncates the 19-digit value (see CLAUDE.md).
|
||||||
|
id: string
|
||||||
name: string
|
name: string
|
||||||
slug: string
|
slug: string
|
||||||
description?: string
|
description?: string
|
||||||
basePath?: string
|
basePath?: string
|
||||||
ownerId?: number
|
ownerId?: string
|
||||||
settingsJson?: string
|
settingsJson?: string
|
||||||
createTime?: string
|
createTime?: string
|
||||||
updateTime?: string
|
updateTime?: string
|
||||||
@ -24,8 +26,11 @@ export interface Workspace {
|
|||||||
|
|
||||||
export const useWorkspaceStore = defineStore('workspace', () => {
|
export const useWorkspaceStore = defineStore('workspace', () => {
|
||||||
const workspaces = ref<Workspace[]>([])
|
const workspaces = ref<Workspace[]>([])
|
||||||
const currentWorkspaceId = ref<number | null>(
|
// Stored as a string: the workspace id is a 19-digit Snowflake, so a Number()
|
||||||
Number(localStorage.getItem('mc-workspace-id')) || null
|
// coercion here would corrupt every non-default workspace id and the reloaded
|
||||||
|
// value would match no workspace, silently snapping back to Default.
|
||||||
|
const currentWorkspaceId = ref<string | null>(
|
||||||
|
localStorage.getItem('mc-workspace-id') || null
|
||||||
)
|
)
|
||||||
const loading = ref(false)
|
const loading = ref(false)
|
||||||
|
|
||||||
@ -102,9 +107,9 @@ export const useWorkspaceStore = defineStore('workspace', () => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async function switchWorkspace(id: number) {
|
async function switchWorkspace(id: string) {
|
||||||
currentWorkspaceId.value = id
|
currentWorkspaceId.value = id
|
||||||
localStorage.setItem('mc-workspace-id', String(id))
|
localStorage.setItem('mc-workspace-id', id)
|
||||||
accessLoaded.value = false
|
accessLoaded.value = false
|
||||||
currentCapabilities.value = new Set()
|
currentCapabilities.value = new Set()
|
||||||
await refreshAccess()
|
await refreshAccess()
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user