- 上下文清单、任务列表与详情、恢复控制、运行观察、创作对话与消息流、正式变更决策面板、正文写作与候选审阅、资料研究等页面同步本轮后端能力。 - 事件标签表补齐后端事件类型;查询键与生成客户端随 HTTP 契约重新生成。 - 依赖调整后 lockfile 同步;交互用例与浏览器旅程 spec 一并更新。 - 证据:make 前端检查(lint + typecheck + Pi 工具桥 tsc)exit 0;make 前端测试 37 文件 / 120 用例通过。
138 lines
5.1 KiB
TypeScript
138 lines
5.1 KiB
TypeScript
/** 界面替身只验证确认与版本绑定,实际S02/PG证据另由集成用例提供。 */
|
||
import { afterEach, beforeEach, expect, it, vi } from "vitest";
|
||
import {
|
||
cleanup,
|
||
fireEvent,
|
||
render,
|
||
screen,
|
||
waitFor,
|
||
} from "@testing-library/react";
|
||
import { Ui方法详情 } from "../../src/功能/知识方法/方法详情";
|
||
|
||
const mocks = vi.hoisted(() => ({
|
||
get: vi.fn(),
|
||
post: vi.fn(),
|
||
refetch: vi.fn(),
|
||
}));
|
||
vi.mock("../../src/接口/生成/客户端", () => ({
|
||
客户端: { GET: mocks.get, POST: mocks.post },
|
||
}));
|
||
vi.mock("../../src/应用/作者会话", () => ({
|
||
useMuse作者会话: () => ({ data: {} }),
|
||
}));
|
||
vi.mock("../../src/功能/知识方法/数据", () => ({
|
||
useMuse方法类型: () => ({ data: [] }),
|
||
useMuse方法详情: () => ({
|
||
data: {
|
||
title: "动作表现迟疑",
|
||
state: "confirmed",
|
||
current_version: 3,
|
||
type_id: "craft",
|
||
owner: "synthetic",
|
||
versions: [],
|
||
evidence: { sources: [], counters: [], static_refs: [] },
|
||
},
|
||
isPending: false,
|
||
refetch: mocks.refetch,
|
||
}),
|
||
}));
|
||
beforeEach(() => {
|
||
vi.clearAllMocks();
|
||
mocks.get.mockResolvedValue({
|
||
data: {
|
||
payload: {
|
||
target: { version: "3" },
|
||
valid_until: "2030-01-01T00:00:00Z",
|
||
},
|
||
},
|
||
});
|
||
mocks.post.mockResolvedValue({ data: { receipt_id: "receipt" } });
|
||
mocks.refetch.mockResolvedValue({});
|
||
});
|
||
afterEach(cleanup);
|
||
|
||
// @muse-case {"case_id":"NC-ui-method-enable","environment":"离线组件与传输替身","given":"确切方法确认版本和明确作者身份","when":"核对启用凭据并执行当前目标的作者状态操作","then":["核对具体凭据后由作者启用当前版本"],"contract":"docs/系统架构/新版设计/模块设计/B10-效果评测.md"}
|
||
it("NC-ui-method-enable:核对具体凭据后由作者启用当前版本", async () => {
|
||
render(<Ui方法详情 methodId="method-a" />);
|
||
const enable = screen.getByRole("button", {
|
||
name: "确认启用写手用途",
|
||
}) as HTMLButtonElement;
|
||
expect(enable.disabled).toBe(true);
|
||
fireEvent.change(screen.getByLabelText("启用凭据编号"), {
|
||
target: { value: "proof-a" },
|
||
});
|
||
fireEvent.click(screen.getByRole("button", { name: "核对已测版本" }));
|
||
await waitFor(() => expect(enable.disabled).toBe(false));
|
||
expect(mocks.post).not.toHaveBeenCalled();
|
||
fireEvent.click(enable);
|
||
await waitFor(() => expect(mocks.refetch).toHaveBeenCalledTimes(1));
|
||
expect(mocks.post).toHaveBeenCalledWith(
|
||
"/api/v1/methods/{method_id}/state",
|
||
expect.objectContaining({
|
||
body: expect.objectContaining({
|
||
method_id: "method-a",
|
||
expected_state_revision: 3,
|
||
启用凭据: "proof-a",
|
||
action: "enable",
|
||
}),
|
||
}),
|
||
);
|
||
expect(enable.disabled).toBe(true);
|
||
});
|
||
|
||
// @muse-case {"case_id":"NC-ui-method-proof-scope","environment":"离线组件与传输替身","given":"确切方法确认版本和明确作者身份","when":"核对启用凭据并执行当前目标的作者状态操作","then":["换方法或修改凭据后旧核对不再放行"],"contract":"docs/系统架构/新版设计/模块设计/B10-效果评测.md"}
|
||
it("NC-ui-method-proof-scope:换方法或修改凭据后旧核对不再放行", async () => {
|
||
const view = render(<Ui方法详情 methodId="method-a" />);
|
||
fireEvent.change(screen.getByLabelText("启用凭据编号"), {
|
||
target: { value: "proof-a" },
|
||
});
|
||
fireEvent.click(screen.getByRole("button", { name: "核对已测版本" }));
|
||
await waitFor(() =>
|
||
expect(
|
||
(
|
||
screen.getByRole("button", {
|
||
name: "确认启用写手用途",
|
||
}) as HTMLButtonElement
|
||
).disabled,
|
||
).toBe(false),
|
||
);
|
||
view.rerender(<Ui方法详情 methodId="method-b" />);
|
||
expect(
|
||
(
|
||
screen.getByRole("button", {
|
||
name: "确认启用写手用途",
|
||
}) as HTMLButtonElement
|
||
).disabled,
|
||
).toBe(true);
|
||
fireEvent.change(screen.getByLabelText("启用凭据编号"), {
|
||
target: { value: "proof-b" },
|
||
});
|
||
expect(
|
||
(
|
||
screen.getByRole("button", {
|
||
name: "确认启用写手用途",
|
||
}) as HTMLButtonElement
|
||
).disabled,
|
||
).toBe(true);
|
||
expect(mocks.post).not.toHaveBeenCalled();
|
||
});
|
||
|
||
// @muse-case {"case_id":"NC-ui-method-proof-error","environment":"离线组件与传输替身","given":"确切方法确认版本和明确作者身份","when":"核对启用凭据并执行当前目标的作者状态操作","then":["失效凭据的拒绝可见且不触发启用"],"contract":"docs/系统架构/新版设计/模块设计/B10-效果评测.md"}
|
||
it("NC-ui-method-proof-error:失效凭据的拒绝可见且不触发启用", async () => {
|
||
mocks.get.mockResolvedValue({ error: { message: "标定来源已停止" } });
|
||
render(<Ui方法详情 methodId="method-a" />);
|
||
fireEvent.change(screen.getByLabelText("启用凭据编号"), {
|
||
target: { value: "stopped" },
|
||
});
|
||
fireEvent.click(screen.getByRole("button", { name: "核对已测版本" }));
|
||
await screen.findByText("标定来源已停止");
|
||
expect(
|
||
(
|
||
screen.getByRole("button", {
|
||
name: "确认启用写手用途",
|
||
}) as HTMLButtonElement
|
||
).disabled,
|
||
).toBe(true);
|
||
expect(mocks.post).not.toHaveBeenCalled();
|
||
});
|