# CDK Construct Reference

Source: https://wraps.dev/docs/cdk-reference

# @wraps.dev/cdk

AWS CDK construct for deploying Wraps email infrastructure to your AWS account. Zero credentials stored, full AWS ownership, sensible defaults.

## Installation

Copy for AI

npmpnpmyarnbun

npm install @wraps.dev/cdk

**Requirements:** Node.js 20+, AWS CDK 2.x, constructs 10.x

## Quick Start

Copy for AI

email-stack.ts

```
import { WrapsEmail } from "@wraps.dev/cdk";import * as cdk from "aws-cdk-lib";const app = new cdk.App();const stack = new cdk.Stack(app, "EmailStack");// Minimal setup with Vercel OIDCconst email = new WrapsEmail(stack, "Email", {  vercel: {    teamSlug: "my-team",    projectName: "my-app",  },});// Access outputsconsole.log("Role ARN:", email.roleArn);console.log("Config Set:", email.configSetName);
```

Outputs are automatically created as CloudFormation exports (WrapsEmailRoleArn, WrapsEmailConfigSetName, etc.)

## With Domain and Event Tracking

Copy for AI

with-domain.ts

```
const email = new WrapsEmail(stack, "Email", {  vercel: {    teamSlug: "my-team",    projectName: "my-app",  },  domain: "example.com",  events: {    types: ["SEND", "DELIVERY", "BOUNCE", "COMPLAINT", "OPEN", "CLICK"],    storeHistory: true,    retention: "90days",  },});// DKIM records are output for DNS configurationemail.dkimRecords?.forEach((record, i) => {  console.log(`DKIM ${i + 1}: ${record.name} CNAME ${record.value}`);});
```

## Full Configuration

Copy for AI

full-config.ts

```
import * as cdk from "aws-cdk-lib";const email = new WrapsEmail(stack, "Email", {  // Authentication (choose one)  vercel: {    teamSlug: "my-team",    projectName: "my-app",  },  // Or custom OIDC:  // oidc: {  //   providerUrl: "https://token.actions.githubusercontent.com",  //   audience: "sts.amazonaws.com",  //   subjectPattern: "repo:my-org/my-repo:*",  // },  // Domain configuration  domain: "example.com",  mailFromSubdomain: "mail", // Creates mail.example.com  hostedZoneId: "Z1234567890", // Auto-creates DNS records  // Event tracking  events: {    types: ["SEND", "DELIVERY", "BOUNCE", "COMPLAINT", "OPEN", "CLICK"],    storeHistory: true,    retention: "90days", // "7days" | "30days" | "90days" | "6months" | "1year" | "unlimited"  },  // Email settings  reputationMetrics: true,  tlsRequired: false,  sendingEnabled: true,  // Suppression list  suppressionList: {    enabled: true,    reasons: ["BOUNCE", "COMPLAINT"],  },  // SMTP credentials (for legacy systems)  smtp: {    enabled: false,  },  // CDK removal policy  removalPolicy: cdk.RemovalPolicy.RETAIN,});
```

## Constructor Props

Copy for AI

| Property | Type | Description |
| --- | --- | --- |
| `vercel` | VercelOIDCConfig | Vercel OIDC configuration (teamSlug, projectName) |
| `oidc` | OIDCConfig | Custom OIDC provider (GitHub Actions, GitLab, etc.) |
| `domain` | string | Primary sending domain with DKIM |
| `hostedZoneId` | string | Route53 zone ID for automatic DNS records |
| `mailFromSubdomain` | string | MAIL FROM subdomain (default: "mail") |
| `events` | EventsConfig | Event tracking and history storage |
| `smtp` | SMTPConfig | SMTP credentials for legacy systems |
| `suppressionList` | SuppressionListConfig | Bounce/complaint suppression |
| `reputationMetrics` | boolean | Enable SES reputation metrics (default: true) |
| `tlsRequired` | boolean | Require TLS for outbound emails (default: false) |
| `sendingEnabled` | boolean | Enable sending (default: true) |
| `removalPolicy` | RemovalPolicy | CDK removal policy for stateful resources |

## Outputs

Copy for AI

| Property | Type | Description |
| --- | --- | --- |
| `roleArn` | string | IAM role ARN for SDK authentication |
| `configSetName` | string | SES configuration set name |
| `domain` | string | Primary domain (if configured) |
| `dkimRecords` | Array | DKIM CNAME records for DNS |
| `tableName` | string | DynamoDB table name (if history enabled) |
| `queueUrl` | string | SQS queue URL (if events enabled) |
| `smtpEndpoint` | string | SMTP endpoint (if SMTP enabled) |

## Grant Methods

Copy for AI

The construct provides CDK-style grant methods for easy IAM permission management.

grants.ts

```
import * as lambda from "aws-cdk-lib/aws-lambda";const email = new WrapsEmail(stack, "Email", { /* ... */ });// Create a Lambda functionconst myFunction = new lambda.Function(stack, "MyFunction", {  runtime: lambda.Runtime.NODEJS_20_X,  handler: "index.handler",  code: lambda.Code.fromAsset("./lambda"),});// Grant send permissionsemail.grantSend(myFunction);// Grant read access to email historyemail.grantReadHistory(myFunction);// Grant access to consume events from SQSemail.grantConsumeEvents(myFunction);
```

#### Available Grant Methods

| Method | Description |
| --- | --- |
| `grantSend(grantee)` | Grant permissions to send emails |
| `grantReadHistory(grantee)` | Grant read access to email history table |
| `grantConsumeEvents(grantee)` | Grant access to consume events from SQS |

## Accessing Underlying Resources

Copy for AI

resources.ts

```
const email = new WrapsEmail(stack, "Email", { /* ... */ });// Access CDK constructs via .resourcesemail.resources.role;           // iam.IRoleemail.resources.configSet;      // ses.IConfigurationSetemail.resources.emailIdentity;  // ses.IEmailIdentity (if domain)email.resources.table;          // dynamodb.ITable (if events.storeHistory)email.resources.queue;          // sqs.IQueue (if events)email.resources.dlq;            // sqs.IQueue (if events)email.resources.eventProcessor; // lambda.IFunction (if events.storeHistory)email.resources.oidcProvider;   // iam.IOpenIdConnectProvider (if OIDC)// Example: Add custom policy to roleemail.resources.role.addToPolicy(  new iam.PolicyStatement({    actions: ["ses:ListIdentities"],    resources: ["*"],  }));
```

#### Available Resources

| Property | Type | When Available |
| --- | --- | --- |
| `role` | iam.IRole | Always |
| `oidcProvider` | iam.IOpenIdConnectProvider | If Vercel or custom OIDC |
| `configSet` | ses.IConfigurationSet | Always |
| `emailIdentity` | ses.IEmailIdentity | If domain is provided |
| `table` | dynamodb.ITable | If events.storeHistory is true |
| `queue` | sqs.IQueue | If events is configured |
| `eventProcessor` | lambda.IFunction | If events.storeHistory is true |

## GitHub Actions OIDC

Copy for AI

Use custom OIDC configuration for GitHub Actions or other providers.

github-actions.ts

```
const email = new WrapsEmail(stack, "Email", {  oidc: {    providerUrl: "https://token.actions.githubusercontent.com",    audience: "sts.amazonaws.com",    subjectPattern: "repo:my-org/my-repo:*",  },  domain: "example.com",});
```

## Using with @wraps.dev/email SDK

Copy for AI

After deploying, use the @wraps.dev/email SDK to send emails:

send-email.ts

```
import { WrapsEmail } from "@wraps.dev/email";const email = new WrapsEmail();await email.send({  from: "hello@example.com",  to: "user@example.com",  subject: "Hello from Wraps!",  html: "<h1>Welcome!</h1>",});
```

## Next Steps

View on npm

Check out the package on npm for the latest version and changelog.

[View Package](https://www.npmjs.com/package/@wraps.dev/cdk)

Email SDK

Learn how to send emails with the @wraps.dev/email SDK.

[SDK Reference](https://wraps.dev/docs/sdk-reference)

AWS CDK Docs

Learn more about AWS CDK and infrastructure as code.

[CDK Docs](https://docs.aws.amazon.com/cdk/)
