-
-
Notifications
You must be signed in to change notification settings - Fork 9
Expand file tree
/
Copy pathMetaToolApprovalDialog.test.tsx
More file actions
117 lines (105 loc) · 4.12 KB
/
Copy pathMetaToolApprovalDialog.test.tsx
File metadata and controls
117 lines (105 loc) · 4.12 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
/**
* Approval dialog wiring:
* - renders the target-Space chip (so a cross-Space write is obvious),
* - survives a freeform `diff` shape (`{ added_tools }`) without crashing —
* a regression guard for the earlier "Cannot read properties of undefined
* (reading 'length')" bug, and
* - the "Manage approval prompts" link denies the request (fail-closed) and
* routes to the Built-in tab where prompts can be disabled.
*/
import { describe, it, expect, vi, beforeEach } from 'vitest';
import { render, screen, act } from '@testing-library/react';
import userEvent from '@testing-library/user-event';
const { handlers, navigateToSpy } = vi.hoisted(() => ({
handlers: new Map<string, (e: { payload: unknown }) => void>(),
navigateToSpy: vi.fn(),
}));
// Capture the dialog's `listen('meta-tool-approval-request', cb)` so the test
// can deliver synthetic requests.
vi.mock('@tauri-apps/api/event', () => ({
listen: vi.fn((name: string, cb: (e: { payload: unknown }) => void) => {
handlers.set(name, cb);
return Promise.resolve(() => handlers.delete(name));
}),
}));
vi.mock('@tauri-apps/api/core', () => ({ invoke: vi.fn().mockResolvedValue(undefined) }));
vi.mock('@/stores', () => ({ useNavigateTo: () => navigateToSpy }));
import { invoke } from '@tauri-apps/api/core';
import { MetaToolApprovalDialog } from '@/features/metaTools/MetaToolApprovalDialog';
async function emitRequest(payload: Record<string, unknown>) {
await act(async () => {
handlers.get('meta-tool-approval-request')?.({
payload: {
request_id: 'req-1',
client_id: 'client-1',
payload,
expires_at_unix_secs: 9_999_999_999,
},
});
await Promise.resolve();
});
}
describe('MetaToolApprovalDialog', () => {
beforeEach(() => {
handlers.clear();
navigateToSpy.mockClear();
vi.mocked(invoke).mockClear();
});
it('names the target Space when present', async () => {
render(<MetaToolApprovalDialog />);
await emitRequest({
tool_name: 'mcpmux_manage_feature_set',
summary: "Create FeatureSet 'X' in Space 'Personal'",
space_name: 'Personal',
diff: null,
raw_args: {},
affects_other_clients: false,
});
const chip = await screen.findByTestId('meta-tool-approval-space');
expect(chip).toHaveTextContent('Personal');
});
it('omits the Space chip when no target Space is given', async () => {
render(<MetaToolApprovalDialog />);
await emitRequest({
tool_name: 'mcpmux_manage_feature_set',
summary: 'Create FeatureSet',
diff: null,
raw_args: {},
affects_other_clients: false,
});
expect(screen.getByTestId('meta-tool-approval-dialog')).toBeInTheDocument();
expect(screen.queryByTestId('meta-tool-approval-space')).toBeNull();
});
it('renders a freeform { added_tools } diff without crashing', async () => {
render(<MetaToolApprovalDialog />);
await emitRequest({
tool_name: 'mcpmux_manage_feature_set',
summary: 'Create FeatureSet',
diff: { added_tools: ['github_create_issue', 'slack_send'] },
raw_args: {},
affects_other_clients: false,
});
expect(screen.getByTestId('meta-tool-approval-dialog')).toBeInTheDocument();
expect(screen.getByText(/github_create_issue/)).toBeInTheDocument();
expect(screen.getByText(/slack_send/)).toBeInTheDocument();
});
it('"Manage approval prompts" denies the request and routes to the Built-in tab', async () => {
const user = userEvent.setup();
render(<MetaToolApprovalDialog />);
await emitRequest({
tool_name: 'mcpmux_bind_current_workspace',
summary: 'Bind this folder',
diff: null,
raw_args: {},
affects_other_clients: false,
});
await user.click(await screen.findByTestId('meta-tool-approval-manage-link'));
// Fail-closed: the pending request is denied rather than left to time out.
expect(invoke).toHaveBeenCalledWith(
'respond_to_meta_tool_approval',
expect.objectContaining({ decision: 'deny' })
);
// ...and the user lands on the tab that hosts the approval toggle.
expect(navigateToSpy).toHaveBeenCalledWith('builtin-servers');
});
});