fix: 修复素材库批量删除后白屏崩溃 #509
Regular → Executable
+23
-4
@@ -390,6 +390,25 @@ export interface BatchOperationResult {
|
||||
failure_count: number;
|
||||
}
|
||||
|
||||
/** 统一批量操作结果归一化,防御后端字段缺失或格式不一致 */
|
||||
const normalizeBatchResult = (
|
||||
raw: Record<string, unknown>,
|
||||
): BatchOperationResult => {
|
||||
const succeeded = Array.isArray(raw.succeeded)
|
||||
? (raw.succeeded as string[])
|
||||
: [];
|
||||
const failed = Array.isArray(raw.failed) ? (raw.failed as string[]) : [];
|
||||
const success_count =
|
||||
typeof raw.success_count === "number"
|
||||
? raw.success_count
|
||||
: succeeded.length;
|
||||
const failure_count =
|
||||
typeof raw.failure_count === "number" ? raw.failure_count : failed.length;
|
||||
const total =
|
||||
typeof raw.total === "number" ? raw.total : success_count + failure_count;
|
||||
return { succeeded, failed, total, success_count, failure_count };
|
||||
};
|
||||
|
||||
/** 批量删除素材 */
|
||||
export const batchDeleteAssets = async (
|
||||
assetIds: string[],
|
||||
@@ -397,7 +416,7 @@ export const batchDeleteAssets = async (
|
||||
const response = await apiClient.post("/assets/batch-delete", {
|
||||
asset_ids: assetIds,
|
||||
});
|
||||
return response.data;
|
||||
return normalizeBatchResult((response.data || {}) as Record<string, unknown>);
|
||||
};
|
||||
|
||||
/** 批量打标签 */
|
||||
@@ -407,7 +426,7 @@ export const batchTagAssets = async (data: {
|
||||
mode: "add" | "replace";
|
||||
}): Promise<BatchOperationResult> => {
|
||||
const response = await apiClient.post("/assets/batch-tag", data);
|
||||
return response.data;
|
||||
return normalizeBatchResult((response.data || {}) as Record<string, unknown>);
|
||||
};
|
||||
|
||||
/** 批量改分类 */
|
||||
@@ -416,7 +435,7 @@ export const batchClassifyAssets = async (data: {
|
||||
category: string;
|
||||
}): Promise<BatchOperationResult> => {
|
||||
const response = await apiClient.post("/assets/batch-classify", data);
|
||||
return response.data;
|
||||
return normalizeBatchResult((response.data || {}) as Record<string, unknown>);
|
||||
};
|
||||
|
||||
/** 批量智能标记 */
|
||||
@@ -425,5 +444,5 @@ export const batchMarkAssets = async (data: {
|
||||
smart_view: "recommended" | "caution" | "high_risk";
|
||||
}): Promise<BatchOperationResult> => {
|
||||
const response = await apiClient.post("/assets/batch-mark", data);
|
||||
return response.data;
|
||||
return normalizeBatchResult((response.data || {}) as Record<string, unknown>);
|
||||
};
|
||||
|
||||
Regular → Executable
+8
-2
@@ -355,7 +355,10 @@ const AssetLibrary: React.FC = () => {
|
||||
staleTime: 60_000,
|
||||
});
|
||||
|
||||
const libraries = useMemo(() => apiLibraries.map(mapLibrary), [apiLibraries]);
|
||||
const libraries = useMemo(
|
||||
() => (Array.isArray(apiLibraries) ? apiLibraries : []).map(mapLibrary),
|
||||
[apiLibraries],
|
||||
);
|
||||
|
||||
/* ── 当前选中的素材库 ── */
|
||||
const [activeLibId, setActiveLibId] = useState<string>("");
|
||||
@@ -377,7 +380,10 @@ const AssetLibrary: React.FC = () => {
|
||||
staleTime: 30_000,
|
||||
});
|
||||
|
||||
const assets = useMemo(() => apiAssets.map(mapAsset), [apiAssets]);
|
||||
const assets = useMemo(
|
||||
() => (Array.isArray(apiAssets) ? apiAssets : []).map(mapAsset),
|
||||
[apiAssets],
|
||||
);
|
||||
|
||||
/* ── Mutations ── */
|
||||
const createLibMutation = useMutation({
|
||||
|
||||
Reference in New Issue
Block a user