Send through a provider
Configure a Resend account and HTTP transport, then send from an Effect program.
A sending program depends on Email. Your application supplies a provider Layer to select the account and a transport Layer to make network requests. Keeping those dependencies separate lets you reuse the program with an offline recorder or another compatible provider.
Configure Resend
The following example provides resendEmailLayer with a Redacted API key and an explicit HTTP client:
import { Effect, Layer } from "effect";
import type { Redacted } from "effect";
import { FetchHttpClient } from "effect/http";
import { Email } from "@corven/email-sdk";
import { resendEmailLayer } from "@corven/email-sdk/resend";
export const emailHttpLayer = FetchHttpClient.layer.pipe(
Layer.provide(Layer.succeed(FetchHttpClient.RequestInit, { redirect: "manual" })),
);
export const sendNotification = (apiKey: Redacted.Redacted) =>
Effect.gen(function* sendNotification() {
const email = yield* Email;
return yield* email.send(
{
body: { text: "Your fictional order is ready." },
from: "sender@example.test",
subject: "Order ready",
to: "recipient@example.test",
},
{ idempotencyKey: "orders/order-42/ready" },
);
}).pipe(Effect.provide(resendEmailLayer({ apiKey }).pipe(Layer.provide(emailHttpLayer))));
Acquire apiKey in trusted application code before calling sendNotification. The SDK does not read environment variables, credential files or cloud identity endpoints. Keep credentials out of source code, logs, browser bundles and model input.
Execute the program
Calling sendNotification(apiKey) constructs an Effect. Run the Effect in your application’s entrypoint to submit the provider request.
Before running it:
- Replace the fictional
.testaddresses with addresses your account is authorized to use. - Choose and persist an idempotency key for the logical event. The example key identifies one fictional order notification; unrelated notifications need different keys.
- Handle the receipt and typed failures as described in receipts, errors and retries.
Configure transport behavior
The example sets redirect: "manual" to disable automatic redirects. Your HTTP client must also avoid hidden send retries and sensitive request or response logging. A retry underneath the SDK can repeat a request whose outcome is unknown, outside the SDK’s submission policy.
You can reuse a transport Layer across provider accounts. Idempotency remains specific to each account.
Change providers
For Postmark, import postmarkEmailLayer from @corven/email-sdk/postmark and supply its serverToken. The application still uses Email, but the provider must support every field and option you request.
Postmark does not support idempotency keys in this SDK, so the keyed Resend example fails local validation. Select a provider that supports keys if your workflow requires them. Scheduling, attachments and recipient results also vary by provider. Check providers and validation before switching. Handle unsupported fields as validation errors; do not drop them automatically.
Use the higher-level Email service for normal application workflows. EmailSender is the lower-level submission capability used to build provider integrations.