Skip to content

Commit 8875dbd

Browse files
committed
refactor(msteams): split monitor handler and poll store
1 parent 475d598 commit 8875dbd

8 files changed

Lines changed: 819 additions & 583 deletions

File tree

docs/cli/message.md

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -155,6 +155,20 @@ clawdbot message poll --provider discord \
155155
--poll-multi --poll-duration-hours 48
156156
```
157157

158+
Send a Teams proactive message:
159+
```
160+
clawdbot message send --provider msteams \
161+
--to conversation:19:[email protected] --message "hi"
162+
```
163+
164+
Create a Teams poll:
165+
```
166+
clawdbot message poll --provider msteams \
167+
--to conversation:19:[email protected] \
168+
--poll-question "Lunch?" \
169+
--poll-option Pizza --poll-option Sushi
170+
```
171+
158172
React in Slack:
159173
```
160174
clawdbot message react --provider slack \

src/infra/outbound/message.test.ts

Lines changed: 77 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,77 @@
1+
import { beforeEach, describe, expect, it, vi } from "vitest";
2+
3+
import { sendMessage, sendPoll } from "./message.js";
4+
5+
const callGatewayMock = vi.fn();
6+
vi.mock("../../gateway/call.js", () => ({
7+
callGateway: (...args: unknown[]) => callGatewayMock(...args),
8+
randomIdempotencyKey: () => "idem-1",
9+
}));
10+
11+
describe("sendMessage provider normalization", () => {
12+
beforeEach(() => {
13+
callGatewayMock.mockReset();
14+
});
15+
16+
it("normalizes Teams alias", async () => {
17+
const sendMSTeams = vi.fn(async () => ({
18+
messageId: "m1",
19+
conversationId: "c1",
20+
}));
21+
const result = await sendMessage({
22+
cfg: {},
23+
to: "conversation:19:[email protected]",
24+
content: "hi",
25+
provider: "teams",
26+
deps: { sendMSTeams },
27+
});
28+
29+
expect(sendMSTeams).toHaveBeenCalledWith(
30+
"conversation:19:[email protected]",
31+
"hi",
32+
);
33+
expect(result.provider).toBe("msteams");
34+
});
35+
36+
it("normalizes iMessage alias", async () => {
37+
const sendIMessage = vi.fn(async () => ({ messageId: "i1" }));
38+
const result = await sendMessage({
39+
cfg: {},
40+
41+
content: "hi",
42+
provider: "imsg",
43+
deps: { sendIMessage },
44+
});
45+
46+
expect(sendIMessage).toHaveBeenCalledWith(
47+
48+
"hi",
49+
expect.any(Object),
50+
);
51+
expect(result.provider).toBe("imessage");
52+
});
53+
});
54+
55+
describe("sendPoll provider normalization", () => {
56+
beforeEach(() => {
57+
callGatewayMock.mockReset();
58+
});
59+
60+
it("normalizes Teams alias for polls", async () => {
61+
callGatewayMock.mockResolvedValueOnce({ messageId: "p1" });
62+
63+
const result = await sendPoll({
64+
cfg: {},
65+
to: "conversation:19:[email protected]",
66+
question: "Lunch?",
67+
options: ["Pizza", "Sushi"],
68+
provider: "Teams",
69+
});
70+
71+
const call = callGatewayMock.mock.calls[0]?.[0] as {
72+
params?: Record<string, unknown>;
73+
};
74+
expect(call?.params?.provider).toBe("msteams");
75+
expect(result.provider).toBe("msteams");
76+
});
77+
});

0 commit comments

Comments
 (0)