refactor: centralize WhatsApp target normalization
This commit is contained in:
@@ -96,6 +96,21 @@ describe("resolveHeartbeatDeliveryTarget", () => {
|
||||
});
|
||||
});
|
||||
|
||||
it("normalizes explicit WhatsApp targets when allowFrom is '*'", () => {
|
||||
const cfg: ClawdbotConfig = {
|
||||
agents: {
|
||||
defaults: {
|
||||
heartbeat: { target: "whatsapp", to: "whatsapp:(555) 123" },
|
||||
},
|
||||
},
|
||||
whatsapp: { allowFrom: ["*"] },
|
||||
};
|
||||
expect(resolveHeartbeatDeliveryTarget({ cfg, entry: baseEntry })).toEqual({
|
||||
provider: "whatsapp",
|
||||
to: "+555123",
|
||||
});
|
||||
});
|
||||
|
||||
it("skips when last route is webchat", () => {
|
||||
const cfg: ClawdbotConfig = {};
|
||||
const entry = {
|
||||
|
||||
@@ -3,39 +3,64 @@ import { describe, expect, it } from "vitest";
|
||||
import { resolveOutboundTarget } from "./targets.js";
|
||||
|
||||
describe("resolveOutboundTarget", () => {
|
||||
it("falls back to whatsapp allowFrom", () => {
|
||||
const res = resolveOutboundTarget({
|
||||
provider: "whatsapp",
|
||||
to: "",
|
||||
allowFrom: ["+1555"],
|
||||
});
|
||||
expect(res).toEqual({ ok: true, to: "+1555" });
|
||||
});
|
||||
|
||||
it("normalizes whatsapp allowFrom fallback targets", () => {
|
||||
const res = resolveOutboundTarget({
|
||||
provider: "whatsapp",
|
||||
to: "",
|
||||
allowFrom: ["whatsapp:(555) 123-4567"],
|
||||
});
|
||||
expect(res).toEqual({ ok: true, to: "+5551234567" });
|
||||
});
|
||||
|
||||
it("normalizes whatsapp target when provided", () => {
|
||||
const res = resolveOutboundTarget({
|
||||
provider: "whatsapp",
|
||||
to: " (555) 123-4567 ",
|
||||
});
|
||||
if (!res.ok) throw res.error;
|
||||
expect(res.to).toBe("+5551234567");
|
||||
});
|
||||
|
||||
it("keeps whatsapp group targets", () => {
|
||||
const res = resolveOutboundTarget({
|
||||
provider: "whatsapp",
|
||||
to: "120363401234567890@g.us",
|
||||
});
|
||||
expect(res).toEqual({ ok: true, to: "120363401234567890@g.us" });
|
||||
it.each([
|
||||
{
|
||||
name: "normalizes whatsapp target when provided",
|
||||
input: { provider: "whatsapp" as const, to: " (555) 123-4567 " },
|
||||
expected: { ok: true as const, to: "+5551234567" },
|
||||
},
|
||||
{
|
||||
name: "keeps whatsapp group targets",
|
||||
input: { provider: "whatsapp" as const, to: "120363401234567890@g.us" },
|
||||
expected: { ok: true as const, to: "120363401234567890@g.us" },
|
||||
},
|
||||
{
|
||||
name: "normalizes prefixed/uppercase whatsapp group targets",
|
||||
input: {
|
||||
provider: "whatsapp" as const,
|
||||
to: " WhatsApp:Group:120363401234567890@G.US ",
|
||||
},
|
||||
expected: { ok: true as const, to: "120363401234567890@g.us" },
|
||||
},
|
||||
{
|
||||
name: "falls back to whatsapp allowFrom",
|
||||
input: { provider: "whatsapp" as const, to: "", allowFrom: ["+1555"] },
|
||||
expected: { ok: true as const, to: "+1555" },
|
||||
},
|
||||
{
|
||||
name: "normalizes whatsapp allowFrom fallback targets",
|
||||
input: {
|
||||
provider: "whatsapp" as const,
|
||||
to: "",
|
||||
allowFrom: ["whatsapp:(555) 123-4567"],
|
||||
},
|
||||
expected: { ok: true as const, to: "+5551234567" },
|
||||
},
|
||||
{
|
||||
name: "rejects invalid whatsapp target",
|
||||
input: { provider: "whatsapp" as const, to: "wat" },
|
||||
expectedErrorIncludes: "WhatsApp",
|
||||
},
|
||||
{
|
||||
name: "rejects whatsapp without to when allowFrom missing",
|
||||
input: { provider: "whatsapp" as const, to: " " },
|
||||
expectedErrorIncludes: "WhatsApp",
|
||||
},
|
||||
{
|
||||
name: "rejects whatsapp allowFrom fallback when invalid",
|
||||
input: { provider: "whatsapp" as const, to: "", allowFrom: ["wat"] },
|
||||
expectedErrorIncludes: "WhatsApp",
|
||||
},
|
||||
])("$name", ({ input, expected, expectedErrorIncludes }) => {
|
||||
const res = resolveOutboundTarget(input);
|
||||
if (expected) {
|
||||
expect(res).toEqual(expected);
|
||||
return;
|
||||
}
|
||||
expect(res.ok).toBe(false);
|
||||
if (!res.ok) {
|
||||
expect(res.error.message).toContain(expectedErrorIncludes);
|
||||
}
|
||||
});
|
||||
|
||||
it("rejects telegram with missing target", () => {
|
||||
|
||||
@@ -4,11 +4,11 @@ import type {
|
||||
DeliverableMessageProvider,
|
||||
GatewayMessageProvider,
|
||||
} from "../../utils/message-provider.js";
|
||||
import { normalizeE164 } from "../../utils.js";
|
||||
import {
|
||||
isWhatsAppGroupJid,
|
||||
normalizeE164,
|
||||
normalizeWhatsAppTarget,
|
||||
} from "../../utils.js";
|
||||
} from "../../whatsapp/normalize.js";
|
||||
|
||||
export type OutboundProvider = DeliverableMessageProvider | "none";
|
||||
|
||||
@@ -24,7 +24,7 @@ export type OutboundTargetResolution =
|
||||
| { ok: true; to: string }
|
||||
| { ok: false; error: Error };
|
||||
|
||||
export function resolveOutboundTarget(params: {
|
||||
export function normalizeOutboundTarget(params: {
|
||||
provider: GatewayMessageProvider;
|
||||
to?: string;
|
||||
allowFrom?: string[];
|
||||
@@ -129,6 +129,14 @@ export function resolveOutboundTarget(params: {
|
||||
};
|
||||
}
|
||||
|
||||
export function resolveOutboundTarget(params: {
|
||||
provider: GatewayMessageProvider;
|
||||
to?: string;
|
||||
allowFrom?: string[];
|
||||
}): OutboundTargetResolution {
|
||||
return normalizeOutboundTarget(params);
|
||||
}
|
||||
|
||||
export function resolveHeartbeatDeliveryTarget(params: {
|
||||
cfg: ClawdbotConfig;
|
||||
entry?: SessionEntry;
|
||||
@@ -194,14 +202,14 @@ export function resolveHeartbeatDeliveryTarget(params: {
|
||||
}
|
||||
|
||||
if (provider !== "whatsapp") {
|
||||
const resolved = resolveOutboundTarget({ provider, to });
|
||||
const resolved = normalizeOutboundTarget({ provider, to });
|
||||
return resolved.ok
|
||||
? { provider, to: resolved.to }
|
||||
: { provider: "none", reason: "no-target" };
|
||||
}
|
||||
|
||||
const rawAllow = cfg.whatsapp?.allowFrom ?? [];
|
||||
const resolved = resolveOutboundTarget({
|
||||
const resolved = normalizeOutboundTarget({
|
||||
provider: "whatsapp",
|
||||
to,
|
||||
allowFrom: rawAllow,
|
||||
|
||||
Reference in New Issue
Block a user