/**
* c_send_email
*
* Sends an email to the verified user via the cloud gateway.
* The gateway resolves the recipient from the session handle —
* the agent never controls who receives the message.
*
* Wire contract
* -------------
* POST ${CLOUD_GATEWAY_URL}/api/eoc/email/send
* X-Idemeum-Eoc-Api-Key: ${CLOUD_GATEWAY_API_KEY}
* X-Idemeum-User-Session: ${userSessionHandle}
* Body: { "subject": "...", "body": "..." }
*/
import { z } from "zod" ;
import { cloudGatewayCall, type CloudGatewayResult } from "./_shared/cloudGateway" ;
// -- Meta ---------------------------------------------------------------------
export const meta = {
name: "c_send_email" ,
description:
"Sends an email to the user via the cloud gateway. " +
"The recipient is resolved server-side from the verified session — " +
"the agent cannot control who receives the message. " +
"Use this to deliver summaries, instructions, or confirmation details " +
"that the user will need after the conversation ends." ,
riskLevel: "medium" ,
destructive: false ,
requiresConsent: true ,
supportsDryRun: false ,
auditRequired: true ,
affectedScope: [ "network" ],
requiresVerifiedIdentity: true ,
sensitiveParams: [],
outputKeys: [
"status" ,
"message" ,
"httpStatus" ,
"failureReason" ,
],
schema: {
subject: z. string (). min ( 1 ). max ( 200 ). describe (
"Email subject line. Keep it short and descriptive." ,
),
body: z. string (). min ( 1 ). max ( 10_000 ). describe (
"Plain-text email body. May include the resolution summary, " +
"steps taken, or follow-up instructions for the user." ,
),
},
} as const ;
// -- Types --------------------------------------------------------------------
interface SendEmailData {
status : "sent" | "failed" ;
message : string ;
}
export interface SendEmailResult {
status : "ok" | "failed" | "not-configured" ;
message : string ;
httpStatus ?: number ;
failureReason ?: CloudGatewayResult [ "failureReason" ];
}
// -- Implementation -----------------------------------------------------------
export async function run (
args : { subject : string ; body : string },
ctx ?: { verifiedUpn ?: string ; userSessionHandle ?: string },
) : Promise < SendEmailResult > {
if ( ! ctx?.verifiedUpn) {
return {
status: "failed" ,
message: "No verified identity for this run." ,
} as never ;
}
const r = await cloudGatewayCall < SendEmailData >({
method: "POST" ,
path: "/email/send" ,
body: { subject: args.subject, body: args.body },
userSessionHandle: ctx?.userSessionHandle,
});
if (r.status !== "ok" ) {
return {
status: r.status === "not-configured" ? "not-configured" : "failed" ,
message: r.message,
httpStatus: r.httpStatus,
failureReason: r.failureReason,
};
}
const d = r.data ! ;
return {
status: d.status === "sent" ? "ok" : "failed" ,
message: d.message,
};
}