68 lines
2.9 KiB
TypeScript
68 lines
2.9 KiB
TypeScript
import net from "node:net";
|
|
import { afterEach, describe, expect, it } from "vitest";
|
|
import type { CatalogComponent, FlowNode } from "../../src/types";
|
|
import type { RunContext } from "../../src/engine/types";
|
|
import { getHandler, hasCapability } from "../../src/engine/registry";
|
|
import "../../src/capabilities/message";
|
|
|
|
const context = {} as RunContext;
|
|
const component = {} as CatalogComponent;
|
|
const node = (id: string): FlowNode => ({ id, componentId: id, position: { x: 0, y: 0 }, values: {}, options: {} });
|
|
const ids = [
|
|
"Mail_FindMail", "Mail_FindMail_v1", "Mail_FindMail_v2",
|
|
"Mail_ReplyMail", "Mail_ReplyMail_v1", "Mail_ReplyMail_v2",
|
|
"Mail_DoGetMailMessage", "Mail_DoGetMailMessage_v1", "Mail_DoGetMailMessage_v2"
|
|
];
|
|
|
|
afterEach(async () => {});
|
|
|
|
describe("mail receive and reply", () => {
|
|
it("registers find, reply and Outlook message capabilities", () => {
|
|
for (const id of ids) expect(hasCapability(id), id).toBe(true);
|
|
});
|
|
|
|
it("replies through SMTP with the selected mail sender", async () => {
|
|
let received = "";
|
|
const server = net.createServer((socket) => {
|
|
socket.setEncoding("utf8");
|
|
socket.write("220 localhost ESMTP\r\n");
|
|
let buffer = "";
|
|
let dataMode = false;
|
|
socket.on("data", (chunk) => {
|
|
buffer += chunk;
|
|
const lines = buffer.split("\r\n");
|
|
buffer = lines.pop() || "";
|
|
for (const line of lines) {
|
|
if (dataMode) {
|
|
if (line === ".") {
|
|
dataMode = false;
|
|
socket.write("250 queued\r\n");
|
|
} else received += line + "\n";
|
|
} else if (/^EHLO/i.test(line)) socket.write("250-localhost\r\n250 OK\r\n");
|
|
else if (/^MAIL FROM/i.test(line)) socket.write("250 ok\r\n");
|
|
else if (/^RCPT TO/i.test(line)) socket.write("250 ok\r\n");
|
|
else if (/^DATA/i.test(line)) { dataMode = true; socket.write("354 end with dot\r\n"); }
|
|
else if (/^QUIT/i.test(line)) { socket.write("221 bye\r\n"); socket.end(); }
|
|
else socket.write("250 OK\r\n");
|
|
}
|
|
});
|
|
});
|
|
await new Promise<void>((resolve) => server.listen(0, "127.0.0.1", resolve));
|
|
const port = (server.address() as net.AddressInfo).port;
|
|
try {
|
|
const handler = getHandler("Mail_ReplyMail_v2");
|
|
expect(handler).toBeTruthy();
|
|
const result = await handler!(context, node("Mail_ReplyMail_v2"), {
|
|
account_obj: { host: "127.0.0.1", port, account: "robot@example.com", secure: "False" },
|
|
mail_obj: { from: "owner@example.com", subject: "status", messageId: "<abc@example.com>" },
|
|
content: "reply delivered"
|
|
}, component);
|
|
expect(result).toMatchObject({ accepted: ["owner@example.com"] });
|
|
expect(received).toContain("reply delivered");
|
|
expect(received).toContain("Re: status");
|
|
} finally {
|
|
await new Promise<void>((resolve) => server.close(() => resolve()));
|
|
}
|
|
}, 30000);
|
|
});
|