@tuturuuu/ui 0.2.0 → 0.3.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +60 -0
- package/package.json +79 -67
- package/src/components/ui/__tests__/avatar.test.tsx +8 -5
- package/src/components/ui/calendar-app/components/calendar-connections-compact.tsx +414 -0
- package/src/components/ui/calendar-app/components/calendar-connections-manager.tsx +5 -1
- package/src/components/ui/calendar-app/components/calendar-connections-settings-content.tsx +529 -0
- package/src/components/ui/calendar-app/components/calendar-connections-unified.tsx +26 -1429
- package/src/components/ui/calendar-app/components/use-calendar-connections-manager.ts +711 -0
- package/src/components/ui/chart.test.tsx +29 -0
- package/src/components/ui/chart.tsx +12 -3
- package/src/components/ui/chat/chat-agent-details-operations-panel.test.tsx +396 -2
- package/src/components/ui/chat/chat-agent-details-operations-panel.tsx +36 -8
- package/src/components/ui/chat/chat-agent-details-setup-panel.tsx +14 -0
- package/src/components/ui/chat/chat-agent-details-sidebar.test.tsx +5 -0
- package/src/components/ui/chat/chat-agent-details-sidebar.tsx +21 -7
- package/src/components/ui/chat/chat-agent-details-utils.test.ts +73 -0
- package/src/components/ui/chat/chat-agent-details-utils.tsx +100 -26
- package/src/components/ui/chat/chat-agent-details-zalo-personal-panel.tsx +517 -0
- package/src/components/ui/chat/chat-workspace.tsx +31 -1
- package/src/components/ui/chat/hooks-messages.test.tsx +45 -1
- package/src/components/ui/chat/hooks-messages.ts +1 -1
- package/src/components/ui/chat/hooks-realtime.ts +13 -16
- package/src/components/ui/custom/__tests__/settings-dialog-shell.test.tsx +24 -1
- package/src/components/ui/custom/__tests__/tuturuuu-logo.test.ts +12 -3
- package/src/components/ui/custom/__tests__/workspace-select-helpers.test.ts +39 -0
- package/src/components/ui/custom/common-footer.tsx +16 -1
- package/src/components/ui/custom/production-indicator.tsx +1 -1
- package/src/components/ui/custom/settings/sidebar-settings.tsx +1 -1
- package/src/components/ui/custom/settings/task-settings.tsx +18 -0
- package/src/components/ui/custom/settings-dialog-shell.tsx +38 -23
- package/src/components/ui/custom/sidebar-context-compile-graph.test.ts +60 -0
- package/src/components/ui/custom/sidebar-context.tsx +61 -61
- package/src/components/ui/custom/sidebar-remote-behavior-bridge.tsx +123 -0
- package/src/components/ui/custom/tuturuuu-logo-urls.ts +6 -0
- package/src/components/ui/custom/tuturuuu-logo.tsx +25 -7
- package/src/components/ui/custom/workspace-select-helpers.ts +20 -0
- package/src/components/ui/custom/workspace-select.tsx +33 -12
- package/src/components/ui/finance/invoices/components/invoice-checkout-summary.tsx +7 -1
- package/src/components/ui/finance/invoices/components/invoice-payment-settings.tsx +3 -0
- package/src/components/ui/finance/invoices/components/invoice-products-permission-warning.tsx +58 -0
- package/src/components/ui/finance/invoices/components/subscription-group-selector.tsx +12 -20
- package/src/components/ui/finance/invoices/hooks/use-subscription-auto-selection.ts +10 -9
- package/src/components/ui/finance/invoices/hooks/use-subscription-invoice-content.ts +10 -5
- package/src/components/ui/finance/invoices/hooks.ts +75 -20
- package/src/components/ui/finance/invoices/new-invoice-page.test.tsx +137 -0
- package/src/components/ui/finance/invoices/new-invoice-page.tsx +86 -37
- package/src/components/ui/finance/invoices/product-selection.test.tsx +8 -26
- package/src/components/ui/finance/invoices/product-selection.tsx +2 -10
- package/src/components/ui/finance/invoices/standard-invoice.tsx +88 -26
- package/src/components/ui/finance/invoices/subscription-invoice.tsx +154 -46
- package/src/components/ui/finance/invoices/utils.test.ts +50 -0
- package/src/components/ui/finance/invoices/utils.ts +75 -17
- package/src/components/ui/finance/shared/finance-display-amount.tsx +3 -1
- package/src/components/ui/finance/shared/finance-permission-warning-dialog.test.tsx +34 -0
- package/src/components/ui/finance/shared/finance-permission-warning-dialog.tsx +157 -0
- package/src/components/ui/finance/transactions/form-basic-tab.tsx +8 -0
- package/src/components/ui/finance/transactions/form-more-tab.tsx +8 -0
- package/src/components/ui/finance/transactions/form-types.ts +2 -0
- package/src/components/ui/finance/transactions/form.test.tsx +43 -0
- package/src/components/ui/finance/transactions/form.tsx +60 -0
- package/src/components/ui/finance/transactions/infinite-transactions-list.tsx +27 -0
- package/src/components/ui/finance/transactions/transactions-create-summary.tsx +13 -1
- package/src/components/ui/finance/transactions/transactions-infinite-page.tsx +4 -0
- package/src/components/ui/finance/transactions/transactions-page.tsx +23 -1
- package/src/components/ui/finance/wallets/walletId/wallet-details-actions.tsx +4 -0
- package/src/components/ui/finance/wallets/walletId/wallet-details-page.tsx +5 -0
- package/src/components/ui/legacy/calendar/calendar-content.tsx +9 -1
- package/src/components/ui/legacy/calendar/event-modal.tsx +146 -2
- package/src/components/ui/legacy/calendar/event-preview-popover.tsx +200 -0
- package/src/components/ui/legacy/calendar/smart-calendar.test.tsx +76 -0
- package/src/components/ui/legacy/calendar/smart-calendar.tsx +13 -1
- package/src/components/ui/legacy/meet/page.test.ts +180 -0
- package/src/components/ui/legacy/meet/page.tsx +87 -39
- package/src/components/ui/tu-do/boards/boardId/board-column.tsx +79 -25
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/__tests__/bulk-mutations-external-workspaces.test.tsx +392 -0
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-actions-island.test.tsx +57 -0
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-actions-island.tsx +106 -0
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-mutations-clear-delete.ts +106 -161
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-mutations-relations-assignees.ts +96 -150
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-mutations-relations-labels.ts +63 -79
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-mutations-relations-projects.ts +64 -83
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-mutations-updates.ts +115 -155
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-operation-utils.ts +319 -2
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-operations.ts +8 -1
- package/src/components/ui/tu-do/boards/boardId/kanban/dnd/use-kanban-dnd.ts +63 -37
- package/src/components/ui/tu-do/boards/boardId/kanban/kanban-column-collapse.ts +16 -0
- package/src/components/ui/tu-do/boards/boardId/kanban/rendering/kanban-columns.test.tsx +46 -0
- package/src/components/ui/tu-do/boards/boardId/kanban/rendering/kanban-columns.tsx +5 -3
- package/src/components/ui/tu-do/boards/boardId/kanban.tsx +19 -7
- package/src/components/ui/tu-do/boards/boardId/menus/__tests__/task-menus.test.tsx +181 -2
- package/src/components/ui/tu-do/boards/boardId/menus/index.ts +1 -0
- package/src/components/ui/tu-do/boards/boardId/menus/task-scheduling-menu.tsx +463 -0
- package/src/components/ui/tu-do/boards/boardId/menus/task-scheduling-utils.ts +109 -0
- package/src/components/ui/tu-do/boards/boardId/task-board-server-page.tsx +4 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/TaskCardCheckbox.tsx +6 -3
- package/src/components/ui/tu-do/boards/boardId/task-card/TaskCardDates.tsx +26 -9
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card-checkbox-style.ts +39 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card-comparator.test.ts +43 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card-comparator.ts +33 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card-completion-checkbox-visibility.test.ts +31 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card-completion-checkbox-visibility.ts +9 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card-identifier-row.test.tsx +124 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card-identifier-row.tsx +88 -0
- package/src/components/ui/tu-do/boards/boardId/task-card/task-card.tsx +151 -76
- package/src/components/ui/tu-do/boards/boardId/task-card/task-scheduling-badge.tsx +174 -0
- package/src/components/ui/tu-do/providers/task-dialog-provider.tsx +34 -13
- package/src/components/ui/tu-do/shared/__tests__/board-client.test.tsx +54 -1
- package/src/components/ui/tu-do/shared/__tests__/board-views.test.tsx +158 -0
- package/src/components/ui/tu-do/shared/__tests__/task-dialog-manager.test.tsx +5 -2
- package/src/components/ui/tu-do/shared/board-client.tsx +12 -2
- package/src/components/ui/tu-do/shared/board-views.tsx +195 -328
- package/src/components/ui/tu-do/shared/list-view.tsx +18 -8
- package/src/components/ui/tu-do/shared/task-due-date-visibility.test.ts +72 -0
- package/src/components/ui/tu-do/shared/task-due-date-visibility.ts +38 -0
- package/src/components/ui/tu-do/shared/task-edit-dialog/hooks/use-task-mutations.ts +6 -3
- package/src/components/ui/tu-do/shared/task-edit-dialog/hooks/use-task-save.ts +2 -2
- package/src/components/ui/tu-do/shared/task-row-actions-menu.tsx +33 -0
- package/src/hooks/__tests__/use-calendar-readonly.test.tsx +74 -3
- package/src/hooks/__tests__/use-task-actions.test.tsx +118 -0
- package/src/hooks/__tests__/use-user-config.test.tsx +65 -0
- package/src/hooks/__tests__/use-workspace-presence.test.tsx +1 -1
- package/src/hooks/use-calendar-sync.tsx +22 -277
- package/src/hooks/use-calendar.tsx +95 -525
- package/src/hooks/use-semantic-task-search.ts +10 -33
- package/src/hooks/use-task-actions.ts +43 -117
- package/src/hooks/use-user-config.ts +1 -1
- package/src/hooks/use-workspace-config.ts +6 -2
- package/src/hooks/use-workspace-presence.ts +1 -1
- package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-actions-bar.tsx +0 -94
package/src/components/ui/tu-do/boards/boardId/kanban/bulk/bulk-mutations-relations-projects.ts
CHANGED
|
@@ -2,12 +2,17 @@
|
|
|
2
2
|
|
|
3
3
|
import { type QueryClient, useMutation } from '@tanstack/react-query';
|
|
4
4
|
import { bulkWorkspaceTasks } from '@tuturuuu/internal-api/tasks';
|
|
5
|
-
import type { Task } from '@tuturuuu/types/primitives/Task';
|
|
6
5
|
import { toast } from '@tuturuuu/ui/sonner';
|
|
7
6
|
import type { BoardBroadcastFn } from '../../../../shared/board-broadcast-context';
|
|
8
7
|
import type { BulkOperationI18n } from './bulk-operation-i18n';
|
|
9
8
|
import type { WorkspaceProject } from './bulk-operation-types';
|
|
10
|
-
import {
|
|
9
|
+
import {
|
|
10
|
+
getInternalApiOptions,
|
|
11
|
+
restoreBoardTaskCaches,
|
|
12
|
+
restoreFailedBoardTasks,
|
|
13
|
+
snapshotBoardTaskCaches,
|
|
14
|
+
updateBoardTaskCaches,
|
|
15
|
+
} from './bulk-operation-utils';
|
|
11
16
|
|
|
12
17
|
export function useBulkAddProject(
|
|
13
18
|
queryClient: QueryClient,
|
|
@@ -52,8 +57,9 @@ export function useBulkAddProject(
|
|
|
52
57
|
},
|
|
53
58
|
onMutate: async ({ projectId, taskIds }) => {
|
|
54
59
|
await queryClient.cancelQueries({ queryKey: ['tasks', boardId] });
|
|
55
|
-
|
|
56
|
-
const
|
|
60
|
+
await queryClient.cancelQueries({ queryKey: ['tasks-full', boardId] });
|
|
61
|
+
const cacheSnapshot = snapshotBoardTaskCaches(queryClient, boardId);
|
|
62
|
+
const current = cacheSnapshot.previousTasks || [];
|
|
57
63
|
const projectMeta = workspaceProjects.find((p) => p.id === projectId);
|
|
58
64
|
|
|
59
65
|
const missingTaskIds = taskIds.filter((id) => {
|
|
@@ -61,35 +67,30 @@ export function useBulkAddProject(
|
|
|
61
67
|
return !task?.projects?.some((p) => p.id === projectId);
|
|
62
68
|
});
|
|
63
69
|
|
|
64
|
-
queryClient
|
|
65
|
-
|
|
66
|
-
(
|
|
67
|
-
if (!
|
|
68
|
-
return
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
...task,
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
],
|
|
83
|
-
};
|
|
84
|
-
});
|
|
85
|
-
}
|
|
86
|
-
);
|
|
70
|
+
updateBoardTaskCaches(queryClient, boardId, (old) => {
|
|
71
|
+
if (!old) return old;
|
|
72
|
+
return old.map((task) => {
|
|
73
|
+
if (!missingTaskIds.includes(task.id)) return task;
|
|
74
|
+
return {
|
|
75
|
+
...task,
|
|
76
|
+
projects: [
|
|
77
|
+
...(task.projects || []),
|
|
78
|
+
{
|
|
79
|
+
id: projectId,
|
|
80
|
+
name:
|
|
81
|
+
projectMeta?.name || i18n?.defaultProjectName() || 'Project',
|
|
82
|
+
status: projectMeta?.status ?? 'unknown',
|
|
83
|
+
},
|
|
84
|
+
],
|
|
85
|
+
};
|
|
86
|
+
});
|
|
87
|
+
});
|
|
87
88
|
|
|
88
|
-
return {
|
|
89
|
+
return { ...cacheSnapshot, modifiedTaskIds: missingTaskIds };
|
|
89
90
|
},
|
|
90
91
|
onError: (error, _, context) => {
|
|
91
|
-
if (context
|
|
92
|
-
queryClient
|
|
92
|
+
if (context) {
|
|
93
|
+
restoreBoardTaskCaches(queryClient, boardId, context);
|
|
93
94
|
}
|
|
94
95
|
console.error('Bulk add project failed', error);
|
|
95
96
|
toast.error(
|
|
@@ -101,22 +102,13 @@ export function useBulkAddProject(
|
|
|
101
102
|
data.failures.map((failure) => failure.taskId)
|
|
102
103
|
);
|
|
103
104
|
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
(old: Task[] | undefined) => {
|
|
112
|
-
if (!old) return old;
|
|
113
|
-
return old.map((task) => {
|
|
114
|
-
if (!failedTaskIds.has(task.id)) return task;
|
|
115
|
-
return previousTaskMap.get(task.id) ?? task;
|
|
116
|
-
});
|
|
117
|
-
}
|
|
118
|
-
);
|
|
119
|
-
}
|
|
105
|
+
restoreFailedBoardTasks({
|
|
106
|
+
queryClient,
|
|
107
|
+
boardId,
|
|
108
|
+
previousTasks: context?.previousTasks,
|
|
109
|
+
previousFullTasks: context?.previousFullTasks,
|
|
110
|
+
failedTaskIds,
|
|
111
|
+
});
|
|
120
112
|
|
|
121
113
|
const modifiedTaskIds = context?.modifiedTaskIds ?? data.taskIds;
|
|
122
114
|
const succeededModifiedTaskIds = modifiedTaskIds.filter(
|
|
@@ -211,8 +203,9 @@ export function useBulkRemoveProject(
|
|
|
211
203
|
},
|
|
212
204
|
onMutate: async ({ projectId, taskIds }) => {
|
|
213
205
|
await queryClient.cancelQueries({ queryKey: ['tasks', boardId] });
|
|
214
|
-
|
|
215
|
-
const
|
|
206
|
+
await queryClient.cancelQueries({ queryKey: ['tasks-full', boardId] });
|
|
207
|
+
const cacheSnapshot = snapshotBoardTaskCaches(queryClient, boardId);
|
|
208
|
+
const current = cacheSnapshot.previousTasks || [];
|
|
216
209
|
const modifiedTaskIds = taskIds.filter((id) => {
|
|
217
210
|
const task = current.find((ct) => ct.id === id);
|
|
218
211
|
if (!task) {
|
|
@@ -223,28 +216,25 @@ export function useBulkRemoveProject(
|
|
|
223
216
|
});
|
|
224
217
|
const taskIdSet = new Set(taskIds);
|
|
225
218
|
|
|
226
|
-
queryClient
|
|
227
|
-
|
|
228
|
-
(
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
);
|
|
240
|
-
}
|
|
241
|
-
);
|
|
219
|
+
updateBoardTaskCaches(queryClient, boardId, (old) => {
|
|
220
|
+
if (!old) return old;
|
|
221
|
+
return old.map((task) =>
|
|
222
|
+
taskIdSet.has(task.id)
|
|
223
|
+
? {
|
|
224
|
+
...task,
|
|
225
|
+
projects: (task.projects || []).filter(
|
|
226
|
+
(p) => p.id !== projectId
|
|
227
|
+
),
|
|
228
|
+
}
|
|
229
|
+
: task
|
|
230
|
+
);
|
|
231
|
+
});
|
|
242
232
|
|
|
243
|
-
return {
|
|
233
|
+
return { ...cacheSnapshot, modifiedTaskIds };
|
|
244
234
|
},
|
|
245
235
|
onError: (error, _, context) => {
|
|
246
|
-
if (context
|
|
247
|
-
queryClient
|
|
236
|
+
if (context) {
|
|
237
|
+
restoreBoardTaskCaches(queryClient, boardId, context);
|
|
248
238
|
}
|
|
249
239
|
console.error('Bulk remove project failed', error);
|
|
250
240
|
toast.error(
|
|
@@ -257,22 +247,13 @@ export function useBulkRemoveProject(
|
|
|
257
247
|
data.failures.map((failure) => failure.taskId)
|
|
258
248
|
);
|
|
259
249
|
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
(old: Task[] | undefined) => {
|
|
268
|
-
if (!old) return old;
|
|
269
|
-
return old.map((task) => {
|
|
270
|
-
if (!failedTaskIds.has(task.id)) return task;
|
|
271
|
-
return previousTaskMap.get(task.id) ?? task;
|
|
272
|
-
});
|
|
273
|
-
}
|
|
274
|
-
);
|
|
275
|
-
}
|
|
250
|
+
restoreFailedBoardTasks({
|
|
251
|
+
queryClient,
|
|
252
|
+
boardId,
|
|
253
|
+
previousTasks: context?.previousTasks,
|
|
254
|
+
previousFullTasks: context?.previousFullTasks,
|
|
255
|
+
failedTaskIds,
|
|
256
|
+
});
|
|
276
257
|
|
|
277
258
|
const modifiedTaskIds = context?.modifiedTaskIds ?? data.succeededTaskIds;
|
|
278
259
|
const modifiedTaskIdSet = new Set(modifiedTaskIds);
|
|
@@ -1,14 +1,18 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
3
|
import { type QueryClient, useMutation } from '@tanstack/react-query';
|
|
4
|
-
import { bulkWorkspaceTasks } from '@tuturuuu/internal-api/tasks';
|
|
5
4
|
import type { Task } from '@tuturuuu/types/primitives/Task';
|
|
6
5
|
import { toast } from '@tuturuuu/ui/sonner';
|
|
7
6
|
import type { BoardBroadcastFn } from '../../../../shared/board-broadcast-context';
|
|
8
7
|
import type { BulkOperationI18n } from './bulk-operation-i18n';
|
|
9
8
|
import {
|
|
9
|
+
bulkWorkspaceTasksByEffectiveWorkspace,
|
|
10
10
|
getInternalApiOptions,
|
|
11
11
|
resolveDueDatePreset,
|
|
12
|
+
restoreBoardTaskCaches,
|
|
13
|
+
restoreFailedBoardTasks,
|
|
14
|
+
snapshotBoardTaskCaches,
|
|
15
|
+
updateBoardTaskCaches,
|
|
12
16
|
} from './bulk-operation-utils';
|
|
13
17
|
|
|
14
18
|
export function useBulkUpdatePriority(
|
|
@@ -28,17 +32,17 @@ export function useBulkUpdatePriority(
|
|
|
28
32
|
}) => {
|
|
29
33
|
const apiOptions = getInternalApiOptions();
|
|
30
34
|
|
|
31
|
-
const result = await
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
},
|
|
35
|
+
const result = await bulkWorkspaceTasksByEffectiveWorkspace({
|
|
36
|
+
queryClient,
|
|
37
|
+
boardId,
|
|
38
|
+
defaultWorkspaceId: wsId,
|
|
39
|
+
taskIds,
|
|
40
|
+
operation: {
|
|
41
|
+
type: 'update_fields',
|
|
42
|
+
updates: { priority },
|
|
39
43
|
},
|
|
40
|
-
apiOptions
|
|
41
|
-
);
|
|
44
|
+
options: apiOptions,
|
|
45
|
+
});
|
|
42
46
|
|
|
43
47
|
if (result.successCount === 0) {
|
|
44
48
|
throw new Error(
|
|
@@ -56,22 +60,20 @@ export function useBulkUpdatePriority(
|
|
|
56
60
|
},
|
|
57
61
|
onMutate: async ({ priority, taskIds }) => {
|
|
58
62
|
await queryClient.cancelQueries({ queryKey: ['tasks', boardId] });
|
|
59
|
-
|
|
63
|
+
await queryClient.cancelQueries({ queryKey: ['tasks-full', boardId] });
|
|
64
|
+
const cacheSnapshot = snapshotBoardTaskCaches(queryClient, boardId);
|
|
60
65
|
const taskIdSet = new Set(taskIds);
|
|
61
66
|
|
|
62
|
-
queryClient
|
|
63
|
-
|
|
64
|
-
(
|
|
65
|
-
|
|
66
|
-
return old.map((t) => (taskIdSet.has(t.id) ? { ...t, priority } : t));
|
|
67
|
-
}
|
|
68
|
-
);
|
|
67
|
+
updateBoardTaskCaches(queryClient, boardId, (old) => {
|
|
68
|
+
if (!old) return old;
|
|
69
|
+
return old.map((t) => (taskIdSet.has(t.id) ? { ...t, priority } : t));
|
|
70
|
+
});
|
|
69
71
|
|
|
70
|
-
return
|
|
72
|
+
return cacheSnapshot;
|
|
71
73
|
},
|
|
72
74
|
onError: (error, _, context) => {
|
|
73
|
-
if (context
|
|
74
|
-
queryClient
|
|
75
|
+
if (context) {
|
|
76
|
+
restoreBoardTaskCaches(queryClient, boardId, context);
|
|
75
77
|
}
|
|
76
78
|
console.error('Bulk priority update failed', error);
|
|
77
79
|
toast.error(
|
|
@@ -84,22 +86,13 @@ export function useBulkUpdatePriority(
|
|
|
84
86
|
data.failures.map((failure) => failure.taskId)
|
|
85
87
|
);
|
|
86
88
|
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
(old: Task[] | undefined) => {
|
|
95
|
-
if (!old) return old;
|
|
96
|
-
return old.map((task) => {
|
|
97
|
-
if (!failedTaskIds.has(task.id)) return task;
|
|
98
|
-
return previousTaskMap.get(task.id) ?? task;
|
|
99
|
-
});
|
|
100
|
-
}
|
|
101
|
-
);
|
|
102
|
-
}
|
|
89
|
+
restoreFailedBoardTasks({
|
|
90
|
+
queryClient,
|
|
91
|
+
boardId,
|
|
92
|
+
previousTasks: context?.previousTasks,
|
|
93
|
+
previousFullTasks: context?.previousFullTasks,
|
|
94
|
+
failedTaskIds,
|
|
95
|
+
});
|
|
103
96
|
|
|
104
97
|
for (const tid of data.succeededTaskIds) {
|
|
105
98
|
broadcast?.('task:upsert', {
|
|
@@ -147,17 +140,17 @@ export function useBulkUpdateEstimation(
|
|
|
147
140
|
}) => {
|
|
148
141
|
const apiOptions = getInternalApiOptions();
|
|
149
142
|
|
|
150
|
-
const result = await
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
},
|
|
143
|
+
const result = await bulkWorkspaceTasksByEffectiveWorkspace({
|
|
144
|
+
queryClient,
|
|
145
|
+
boardId,
|
|
146
|
+
defaultWorkspaceId: wsId,
|
|
147
|
+
taskIds,
|
|
148
|
+
operation: {
|
|
149
|
+
type: 'update_fields',
|
|
150
|
+
updates: { estimation_points: points },
|
|
158
151
|
},
|
|
159
|
-
apiOptions
|
|
160
|
-
);
|
|
152
|
+
options: apiOptions,
|
|
153
|
+
});
|
|
161
154
|
|
|
162
155
|
if (result.successCount === 0) {
|
|
163
156
|
throw new Error(
|
|
@@ -175,24 +168,22 @@ export function useBulkUpdateEstimation(
|
|
|
175
168
|
},
|
|
176
169
|
onMutate: async ({ points, taskIds }) => {
|
|
177
170
|
await queryClient.cancelQueries({ queryKey: ['tasks', boardId] });
|
|
178
|
-
|
|
171
|
+
await queryClient.cancelQueries({ queryKey: ['tasks-full', boardId] });
|
|
172
|
+
const cacheSnapshot = snapshotBoardTaskCaches(queryClient, boardId);
|
|
179
173
|
const taskIdSet = new Set(taskIds);
|
|
180
174
|
|
|
181
|
-
queryClient
|
|
182
|
-
|
|
183
|
-
(
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
);
|
|
188
|
-
}
|
|
189
|
-
);
|
|
175
|
+
updateBoardTaskCaches(queryClient, boardId, (old) => {
|
|
176
|
+
if (!old) return old;
|
|
177
|
+
return old.map((t) =>
|
|
178
|
+
taskIdSet.has(t.id) ? { ...t, estimation_points: points } : t
|
|
179
|
+
);
|
|
180
|
+
});
|
|
190
181
|
|
|
191
|
-
return
|
|
182
|
+
return cacheSnapshot;
|
|
192
183
|
},
|
|
193
184
|
onError: (error, _, context) => {
|
|
194
|
-
if (context
|
|
195
|
-
queryClient
|
|
185
|
+
if (context) {
|
|
186
|
+
restoreBoardTaskCaches(queryClient, boardId, context);
|
|
196
187
|
}
|
|
197
188
|
console.error('Bulk estimation update failed', error);
|
|
198
189
|
toast.error(
|
|
@@ -205,22 +196,13 @@ export function useBulkUpdateEstimation(
|
|
|
205
196
|
data.failures.map((failure) => failure.taskId)
|
|
206
197
|
);
|
|
207
198
|
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
(old: Task[] | undefined) => {
|
|
216
|
-
if (!old) return old;
|
|
217
|
-
return old.map((task) => {
|
|
218
|
-
if (!failedTaskIds.has(task.id)) return task;
|
|
219
|
-
return previousTaskMap.get(task.id) ?? task;
|
|
220
|
-
});
|
|
221
|
-
}
|
|
222
|
-
);
|
|
223
|
-
}
|
|
199
|
+
restoreFailedBoardTasks({
|
|
200
|
+
queryClient,
|
|
201
|
+
boardId,
|
|
202
|
+
previousTasks: context?.previousTasks,
|
|
203
|
+
previousFullTasks: context?.previousFullTasks,
|
|
204
|
+
failedTaskIds,
|
|
205
|
+
});
|
|
224
206
|
|
|
225
207
|
for (const tid of data.succeededTaskIds) {
|
|
226
208
|
broadcast?.('task:upsert', {
|
|
@@ -270,17 +252,17 @@ export function useBulkUpdateDueDate(
|
|
|
270
252
|
const newDate = resolveDueDatePreset(preset, weekStartsOn);
|
|
271
253
|
const apiOptions = getInternalApiOptions();
|
|
272
254
|
|
|
273
|
-
const result = await
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
},
|
|
255
|
+
const result = await bulkWorkspaceTasksByEffectiveWorkspace({
|
|
256
|
+
queryClient,
|
|
257
|
+
boardId,
|
|
258
|
+
defaultWorkspaceId: wsId,
|
|
259
|
+
taskIds,
|
|
260
|
+
operation: {
|
|
261
|
+
type: 'update_fields',
|
|
262
|
+
updates: { end_date: newDate },
|
|
281
263
|
},
|
|
282
|
-
apiOptions
|
|
283
|
-
);
|
|
264
|
+
options: apiOptions,
|
|
265
|
+
});
|
|
284
266
|
|
|
285
267
|
if (result.successCount === 0) {
|
|
286
268
|
throw new Error(
|
|
@@ -298,25 +280,23 @@ export function useBulkUpdateDueDate(
|
|
|
298
280
|
},
|
|
299
281
|
onMutate: async ({ preset, taskIds }) => {
|
|
300
282
|
await queryClient.cancelQueries({ queryKey: ['tasks', boardId] });
|
|
301
|
-
|
|
283
|
+
await queryClient.cancelQueries({ queryKey: ['tasks-full', boardId] });
|
|
284
|
+
const cacheSnapshot = snapshotBoardTaskCaches(queryClient, boardId);
|
|
302
285
|
const newDate = resolveDueDatePreset(preset, weekStartsOn);
|
|
303
286
|
const taskIdSet = new Set(taskIds);
|
|
304
287
|
|
|
305
|
-
queryClient
|
|
306
|
-
|
|
307
|
-
(
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
);
|
|
312
|
-
}
|
|
313
|
-
);
|
|
288
|
+
updateBoardTaskCaches(queryClient, boardId, (old) => {
|
|
289
|
+
if (!old) return old;
|
|
290
|
+
return old.map((t) =>
|
|
291
|
+
taskIdSet.has(t.id) ? { ...t, end_date: newDate } : t
|
|
292
|
+
);
|
|
293
|
+
});
|
|
314
294
|
|
|
315
|
-
return
|
|
295
|
+
return cacheSnapshot;
|
|
316
296
|
},
|
|
317
297
|
onError: (error, _, context) => {
|
|
318
|
-
if (context
|
|
319
|
-
queryClient
|
|
298
|
+
if (context) {
|
|
299
|
+
restoreBoardTaskCaches(queryClient, boardId, context);
|
|
320
300
|
}
|
|
321
301
|
console.error('Bulk due date update failed', error);
|
|
322
302
|
toast.error(
|
|
@@ -329,22 +309,13 @@ export function useBulkUpdateDueDate(
|
|
|
329
309
|
data.failures.map((failure) => failure.taskId)
|
|
330
310
|
);
|
|
331
311
|
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
(old: Task[] | undefined) => {
|
|
340
|
-
if (!old) return old;
|
|
341
|
-
return old.map((task) => {
|
|
342
|
-
if (!failedTaskIds.has(task.id)) return task;
|
|
343
|
-
return previousTaskMap.get(task.id) ?? task;
|
|
344
|
-
});
|
|
345
|
-
}
|
|
346
|
-
);
|
|
347
|
-
}
|
|
312
|
+
restoreFailedBoardTasks({
|
|
313
|
+
queryClient,
|
|
314
|
+
boardId,
|
|
315
|
+
previousTasks: context?.previousTasks,
|
|
316
|
+
previousFullTasks: context?.previousFullTasks,
|
|
317
|
+
failedTaskIds,
|
|
318
|
+
});
|
|
348
319
|
|
|
349
320
|
for (const tid of data.succeededTaskIds) {
|
|
350
321
|
broadcast?.('task:upsert', {
|
|
@@ -393,17 +364,17 @@ export function useBulkUpdateCustomDueDate(
|
|
|
393
364
|
const newDate = date ? date.toISOString() : null;
|
|
394
365
|
const apiOptions = getInternalApiOptions();
|
|
395
366
|
|
|
396
|
-
const result = await
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
},
|
|
367
|
+
const result = await bulkWorkspaceTasksByEffectiveWorkspace({
|
|
368
|
+
queryClient,
|
|
369
|
+
boardId,
|
|
370
|
+
defaultWorkspaceId: wsId,
|
|
371
|
+
taskIds,
|
|
372
|
+
operation: {
|
|
373
|
+
type: 'update_fields',
|
|
374
|
+
updates: { end_date: newDate },
|
|
404
375
|
},
|
|
405
|
-
apiOptions
|
|
406
|
-
);
|
|
376
|
+
options: apiOptions,
|
|
377
|
+
});
|
|
407
378
|
|
|
408
379
|
if (result.successCount === 0) {
|
|
409
380
|
throw new Error(
|
|
@@ -421,25 +392,23 @@ export function useBulkUpdateCustomDueDate(
|
|
|
421
392
|
},
|
|
422
393
|
onMutate: async ({ date, taskIds }) => {
|
|
423
394
|
await queryClient.cancelQueries({ queryKey: ['tasks', boardId] });
|
|
424
|
-
|
|
395
|
+
await queryClient.cancelQueries({ queryKey: ['tasks-full', boardId] });
|
|
396
|
+
const cacheSnapshot = snapshotBoardTaskCaches(queryClient, boardId);
|
|
425
397
|
const newDate = date ? date.toISOString() : null;
|
|
426
398
|
const taskIdSet = new Set(taskIds);
|
|
427
399
|
|
|
428
|
-
queryClient
|
|
429
|
-
|
|
430
|
-
(
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
434
|
-
);
|
|
435
|
-
}
|
|
436
|
-
);
|
|
400
|
+
updateBoardTaskCaches(queryClient, boardId, (old) => {
|
|
401
|
+
if (!old) return old;
|
|
402
|
+
return old.map((t) =>
|
|
403
|
+
taskIdSet.has(t.id) ? { ...t, end_date: newDate } : t
|
|
404
|
+
);
|
|
405
|
+
});
|
|
437
406
|
|
|
438
|
-
return
|
|
407
|
+
return cacheSnapshot;
|
|
439
408
|
},
|
|
440
409
|
onError: (error, _, context) => {
|
|
441
|
-
if (context
|
|
442
|
-
queryClient
|
|
410
|
+
if (context) {
|
|
411
|
+
restoreBoardTaskCaches(queryClient, boardId, context);
|
|
443
412
|
}
|
|
444
413
|
console.error('Bulk custom due date update failed', error);
|
|
445
414
|
toast.error(
|
|
@@ -452,22 +421,13 @@ export function useBulkUpdateCustomDueDate(
|
|
|
452
421
|
data.failures.map((failure) => failure.taskId)
|
|
453
422
|
);
|
|
454
423
|
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
(old: Task[] | undefined) => {
|
|
463
|
-
if (!old) return old;
|
|
464
|
-
return old.map((task) => {
|
|
465
|
-
if (!failedTaskIds.has(task.id)) return task;
|
|
466
|
-
return previousTaskMap.get(task.id) ?? task;
|
|
467
|
-
});
|
|
468
|
-
}
|
|
469
|
-
);
|
|
470
|
-
}
|
|
424
|
+
restoreFailedBoardTasks({
|
|
425
|
+
queryClient,
|
|
426
|
+
boardId,
|
|
427
|
+
previousTasks: context?.previousTasks,
|
|
428
|
+
previousFullTasks: context?.previousFullTasks,
|
|
429
|
+
failedTaskIds,
|
|
430
|
+
});
|
|
471
431
|
|
|
472
432
|
for (const tid of data.succeededTaskIds) {
|
|
473
433
|
broadcast?.('task:upsert', {
|