修复侧边栏拖拽排序后无法保存的问题

This commit is contained in:
jingrow 2026-03-17 20:05:55 +08:00
parent 649ace7e19
commit 785c3bfa9b
3 changed files with 58 additions and 61 deletions

View File

@ -27,7 +27,6 @@
<draggable
v-model="editableWorkspaces"
item-key="id"
@end="handleSortEnd"
>
<template #item="{ element }">
<div class="menu-item-wrapper">
@ -130,6 +129,13 @@ watch(() => workspaceEditStore.isEditMode, (isEdit) => {
if (isEdit) syncEditableWorkspaces()
})
// Sync sorted workspaces to store when changed (for save)
watch(editableWorkspaces, (items) => {
if (workspaceEditStore.isEditMode) {
workspaceEditStore.updateSortedWorkspaces(items)
}
}, { deep: true })
function syncEditableWorkspaces() {
const workspaceItems = menuStore.items
.filter(item => item.type === 'workspace')
@ -176,65 +182,6 @@ function handleMenuAction(key: string, workspace: AppMenuItem) {
actions[key]?.()
}
async function handleSortEnd(evt: any) {
try {
// Get the dragged item to determine if it's public or private
const draggedItem = editableWorkspaces.value[evt.newIndex]
const isPrivateDragged = draggedItem?.isPrivate
// Helper function to get parent title from parentId (keep existing parent relationship)
const getParentTitle = (item: AppMenuItem) => {
if (!item.parentId) return ''
// Find parent workspace and return its label (title)
const parent = editableWorkspaces.value.find(w =>
w.id === item.parentId ||
w.workspaceName === item.parentId ||
w.label === item.parentId
)
return parent?.label || ''
}
// Align with legacy: only send the dragged type to backend
// Send empty array for the other type so backend won't update it
let publicItems: any[] = []
let privateItems: any[] = []
if (isPrivateDragged) {
// Only update private workspaces
privateItems = editableWorkspaces.value
.filter(item => item.isPrivate)
.map(item => ({
title: item.label, // Use label (page.title) for backend matching
parent_page: getParentTitle(item),
public: 0
}))
} else {
// Only update public workspaces
publicItems = editableWorkspaces.value
.filter(item => !item.isPrivate)
.map(item => ({
title: item.label, // Use label (page.title) for backend matching
parent_page: getParentTitle(item),
public: 1
}))
}
await api.call('jingrow.desk.pagetype.workspace.workspace.sort_pages', {
sb_public_items: JSON.stringify(publicItems),
sb_private_items: JSON.stringify(privateItems)
})
// Reload menu to sync the new order
await menuStore.loadFromBackend()
syncEditableWorkspaces()
message.success(t('Saved'))
} catch (error: any) {
message.error(error.message || t('Error'))
}
}
async function editWorkspace(workspace: AppMenuItem) {
await menuStore.loadFromBackend()
syncEditableWorkspaces()

View File

@ -1,5 +1,6 @@
import { defineStore } from 'pinia'
import { ref } from 'vue'
import type { AppMenuItem } from './menu'
/**
* Workspace Edit Mode Store
@ -9,6 +10,9 @@ export const useWorkspaceEditStore = defineStore('workspaceEdit', () => {
// Edit mode state
const isEditMode = ref(false)
// Sorted workspace items (updated when user drags in sidebar)
const sortedWorkspaces = ref<AppMenuItem[]>([])
// Enter edit mode
function enterEditMode() {
isEditMode.value = true
@ -24,10 +28,17 @@ export const useWorkspaceEditStore = defineStore('workspaceEdit', () => {
isEditMode.value = !isEditMode.value
}
// Update sorted workspaces
function updateSortedWorkspaces(items: AppMenuItem[]) {
sortedWorkspaces.value = items
}
return {
isEditMode,
sortedWorkspaces,
enterEditMode,
exitEditMode,
toggleEditMode
toggleEditMode,
updateSortedWorkspaces
}
})

View File

@ -949,6 +949,9 @@ async function saveChanges() {
)
if (success) {
// Also save sidebar workspace sort order
await saveSidebarSortOrder()
message.success(t('Saved successfully'))
workspaceEditStore.exitEditMode()
originalItems.value = JSON.parse(JSON.stringify(items.value))
@ -960,6 +963,42 @@ async function saveChanges() {
}
}
// Save sidebar workspace sort order
async function saveSidebarSortOrder() {
try {
// Use sorted workspaces from store (updated by sidebar drag)
const workspaceItems = workspaceEditStore.sortedWorkspaces
if (!workspaceItems || workspaceItems.length === 0) return
const publicItems = workspaceItems
.filter(item => !item.isPrivate)
.map(item => ({
title: item.label,
parent_page: item.parentId || '',
public: 1
}))
const privateItems = workspaceItems
.filter(item => item.isPrivate)
.map(item => ({
title: item.label,
parent_page: item.parentId || '',
public: 0
}))
if (publicItems.length > 0 || privateItems.length > 0) {
await api.call('jingrow.desk.pagetype.workspace.workspace.sort_pages', {
sb_public_items: JSON.stringify(publicItems),
sb_private_items: JSON.stringify(privateItems)
})
await menuStore.reloadFromBackend()
}
} catch (err) {
console.error('Failed to save sidebar sort order:', err)
}
}
function deleteBlock(index: number) {
items.value.splice(index, 1)
}