refactor(data): 收口关系表运行时数据源
Some checks failed
Deploy Production / Build, push, deploy, verify (push) Has been cancelled

- 移除已迁移业务 AppData 运行时 fallback,改走领域 API 和关系表快读
- 补齐需求产品负责人、版本计划任务 JSON 和成员 username 回填迁移
- 统一治理字典入口,并补充 AI provider、数据源契约和领域服务测试

Co-Authored-By: Codex GPT-5 <codex@openai.com>
This commit is contained in:
2026-07-09 14:59:49 +08:00
parent 1e6fb0c7aa
commit 2e595c7e72
98 changed files with 2938 additions and 1441 deletions

View File

@@ -1,6 +1,6 @@
'use client';
import { useEffect, useMemo, useState } from 'react';
import { useCallback, useEffect, useMemo, useState } from 'react';
import { useProductStore } from '@/stores/useProductStore';
import { useVersionPlanStore } from '@/stores/useVersionPlanStore';
import { useRequirementStore } from '@/stores/useRequirementStore';
@@ -31,6 +31,17 @@ export function useWorkspaceWorkItems({ autoFetch = true }: { autoFetch?: boolea
const userName = user?.name ?? '';
const workspaceUserKey = userId || userName;
const workspaceUserRefs = useMemo(() => [userName, userId].filter(Boolean), [userId, userName]);
const allVersions = useMemo(() => flattenVersions(overview), [overview]);
const hydrateWorkspaceStoreFallback = useCallback(() => {
for (const version of allVersions) {
void fetchRequirements({ productId: version.productId, versionId: version.id });
void fetchPlans({ versionId: version.id });
void fetchTasks({ versionId: version.id });
void fetchTestCases({ versionId: version.id });
void fetchBugs({ versionId: version.id });
}
}, [allVersions, fetchBugs, fetchPlans, fetchRequirements, fetchTasks, fetchTestCases]);
useEffect(() => {
if (!autoFetch || !workspaceUserKey.trim()) {
setV22WorkspaceData(null);
@@ -61,30 +72,21 @@ export function useWorkspaceWorkItems({ autoFetch = true }: { autoFetch?: boolea
useEffect(() => {
if (!autoFetch || !workspaceUserKey.trim() || !v22WorkspaceFailed) return;
void fetchPlans();
void fetchRequirements();
void fetchTasks();
void fetchTestCases();
void fetchBugs();
hydrateWorkspaceStoreFallback();
}, [
autoFetch,
fetchBugs,
fetchPlans,
fetchRequirements,
fetchTasks,
fetchTestCases,
hydrateWorkspaceStoreFallback,
v22WorkspaceFailed,
workspaceUserKey,
]);
const allVersions = useMemo(() => flattenVersions(overview), [overview]);
const versionMap = useMemo(() => {
const map = new Map<string, { id: string; name: string; productName: string; projectName: string }>();
const map = new Map<string, { id: string; name: string; productId: string; productName: string; projectName: string }>();
allVersions.forEach((version) => {
map.set(version.id, {
id: version.id,
name: version.name,
productId: version.productId,
productName: version.productName,
projectName: version.projectName,
});
@@ -105,7 +107,7 @@ export function useWorkspaceWorkItems({ autoFetch = true }: { autoFetch?: boolea
v22Loaded: v22WorkspaceLoaded,
v22Failed: v22WorkspaceFailed,
v22Data: v22WorkspaceData,
appData: { plans, devTasks, testCases, bugs },
storeData: { plans, devTasks, testCases, bugs },
}),
[bugs, devTasks, plans, testCases, v22WorkspaceData, v22WorkspaceFailed, v22WorkspaceLoaded],
);

View File

@@ -1,6 +1,6 @@
'use client';
import { useEffect, useMemo, useState } from 'react';
import { useCallback, useEffect, useMemo, useState } from 'react';
import { useHasPermission } from '@/components/auth/Guard';
import { useAuthStore } from '@/stores/useAuthStore';
import { useBugStore } from '@/stores/useBugStore';
@@ -20,7 +20,7 @@ import {
collectV22XiaobaoLatestInsights,
filterV22XiaobaoSummariesForVisibleVersions,
mergeV22XiaobaoLatestInsights,
shouldLoadXiaobaoAppDataFallback,
shouldLoadXiaobaoStoreFallback,
type V22XiaobaoSummaryLoadState,
} from '@/lib/xiaobao-v22-summary';
import { calcXiaobaoVersionRisk } from '@/lib/xiaobao-risk';
@@ -55,12 +55,26 @@ export function useXiaobaoWarningRisks({ loadRiskCache = false }: { loadRiskCach
const [v22Summaries, setV22Summaries] = useState<V22XiaobaoWarningSummary[]>([]);
const today = useMemo(() => new Date().toISOString().slice(0, 10), []);
const v22UserId = user?.name || user?.id || '';
const shouldLoadFallback = shouldLoadXiaobaoAppDataFallback(v22SummaryState);
const shouldLoadFallback = shouldLoadXiaobaoStoreFallback(v22SummaryState);
const relationInsights = useMemo(() => collectV22XiaobaoLatestInsights(v22Summaries), [v22Summaries]);
const mergedInsights = useMemo(
() => mergeV22XiaobaoLatestInsights(relationInsights, insights),
[insights, relationInsights],
);
const allVersions = useMemo(() => flattenVersions(overview), [overview]);
const visibleVersions = useMemo(
() => filterXiaobaoWarningVersions(allVersions, { canManage, userName: user?.name }),
[allVersions, canManage, user?.name],
);
const hydrateXiaobaoStoreFallback = useCallback(() => {
for (const version of visibleVersions) {
void fetchRequirements({ productId: version.productId, versionId: version.id });
void fetchPlans({ versionId: version.id });
void fetchTasks({ versionId: version.id });
void fetchTestCases({ versionId: version.id });
void fetchBugs({ versionId: version.id });
}
}, [fetchBugs, fetchPlans, fetchRequirements, fetchTasks, fetchTestCases, visibleVersions]);
useEffect(() => { fetchOverview(); }, [fetchOverview]);
useEffect(() => {
@@ -89,23 +103,15 @@ export function useXiaobaoWarningRisks({ loadRiskCache = false }: { loadRiskCach
ignore = true;
};
}, [canManage, v22UserId]);
useEffect(() => { if (shouldLoadFallback) fetchPlans(); }, [fetchPlans, shouldLoadFallback]);
useEffect(() => { if (shouldLoadFallback) fetchRequirements(); }, [fetchRequirements, shouldLoadFallback]);
useEffect(() => { if (shouldLoadFallback) fetchTasks(); }, [fetchTasks, shouldLoadFallback]);
useEffect(() => { if (shouldLoadFallback) fetchTestCases(); }, [fetchTestCases, shouldLoadFallback]);
useEffect(() => { if (shouldLoadFallback) fetchBugs(); }, [fetchBugs, shouldLoadFallback]);
useEffect(() => {
if (shouldLoadFallback) hydrateXiaobaoStoreFallback();
}, [hydrateXiaobaoStoreFallback, shouldLoadFallback]);
useEffect(() => { if (shouldLoadFallback) fetchActivities(); }, [fetchActivities, shouldLoadFallback]);
useEffect(() => { if (shouldLoadFallback) fetchWorklogs(); }, [fetchWorklogs, shouldLoadFallback]);
useEffect(() => {
if (loadRiskCache) fetchRiskData();
}, [fetchRiskData, loadRiskCache]);
const allVersions = useMemo(() => flattenVersions(overview), [overview]);
const visibleVersions = useMemo(
() => filterXiaobaoWarningVersions(allVersions, { canManage, userName: user?.name }),
[allVersions, canManage, user?.name],
);
const visibleVersionScopeMap = useMemo(() => buildVersionDataScopeMap({
versionIds: visibleVersions.map((version) => version.id),
plans,