An open API service indexing awesome lists of open source software.

https://github.com/thunder-so/thunder

AWS CDK stacks to deploy apps like a pro
https://github.com/thunder-so/thunder

aws aws-cloudfront aws-ec2 aws-ecs-fargate aws-lambda aws-s3 aws-s3-cloudfront

Last synced: 3 months ago
JSON representation

AWS CDK stacks to deploy apps like a pro

Awesome Lists containing this project

README

          

# thunder


Version
License

Build full-stack apps on your own AWS.

Thunder is a CDK library and CLI for deploying modern web applications on AWS. One library to rule them all: [Static SPAs](#static), [Lambda Functions](#lambda), [Containers on Fargate](#fargate) and [EC2](#ec2), and [Serverless Full-stack Frameworks](#serverless-frameworks).

## Table of Contents

- [Features](#features)
- [Supported Frameworks & Patterns](#supported-frameworks--patterns)
- [Quick Start](#quick-start)
- [Stacks](#stacks)
- [Static](#static) - S3 + CloudFront + Route53
- [Lambda](#lambda) - API Gateway + Lambda
- [Fargate](#fargate) - ECS Fargate + ALB + CloudFront
- [EC2](#ec2) - EC2 + Docker + Elastic IP
- [Serverless Frameworks](#serverless-frameworks) - Full-stack meta-frameworks with Lambda + S3 + CloudFront
- [Template](#template) - Coolify-style templates
- [CLI Commands](#cli-commands)
- [Documentation](#documentation)
- [License](#license)

## Features

- **Constructs:** One-line deployment for `Static`, `Lambda`, `Fargate`, `EC2`, `Serverless`, and framework-specific constructs.
- **Thunder CLI (`th`):** Context-aware CLI for initializing, deploying, and managing your infrastructure.
- **VPC Link Pattern:** Easily connect your compute resources to a shared VPC.
- **High-Performance Serving:** Pre-configured [CloudFront](https://aws.amazon.com/cloudfront/) distributions with OAC, security headers, and edge optimizations.
- **Built-in CI/CD:** Optional [AWS CodePipeline](https://aws.amazon.com/codepipeline/) integration with GitHub support.

## Supported Frameworks & Patterns

- **Static:** Vite (React, Vue, Svelte, Solid), Next.js (SSG), Astro (SSG), Gatsby.
- **Serverless:** Node.js Lambda, Bun, Container-based Lambda.
- **Containers:** [ECS Fargate](https://aws.amazon.com/fargate/) with ALB, Docker on [EC2](https://aws.amazon.com/ec2/) with Elastic IP.
- **Full-stack SSR:** [Nuxt](https://nuxt.com/), [Astro](https://astro.build/), [TanStack Start](https://tanstack.com/start), [SvelteKit](https://kit.svelte.dev/), [Solid Start](https://start.solidjs.com/), [AnalogJS](https://analogjs.org/).

## Quick Start

### 1. Install

```bash
bun add @thunder-so/thunder --development
```

### 2. Initialize

```bash
npx th init
```

### 3. Configure

Create a stack file (e.g., `stack/dev.ts`):

```typescript
import { Cdk, Static, type StaticProps } from "@thunder-so/thunder";

const myApp: StaticProps = {
env: {
account: "123456789012",
region: "us-east-1",
},
application: "myapp",
service: "web",
environment: "prod",

rootDir: ".",
outputDir: "dist",
};

new Static(
new Cdk.App(),
`${myApp.application}-${myApp.service}-${myApp.environment}-stack`,
myApp,
);
```

### 4. Deploy

```bash
npx cdk deploy --app "npx tsx stack/dev.ts" --profile default
```

## Stacks

### Static

Deploy static websites to [S3](https://aws.amazon.com/s3/) with [CloudFront](https://aws.amazon.com/cloudfront/) CDN and [Route53](https://aws.amazon.com/route53/) DNS.

**Best for:** Static sites, SPAs, JAMstack applications

**AWS Resources:**

- [S3 Bucket](https://aws.amazon.com/s3/) - Static file hosting
- [CloudFront Distribution](https://aws.amazon.com/cloudfront/) - Global CDN with caching
- [Route53](https://aws.amazon.com/route53/) - DNS management (optional)
- [ACM Certificate](https://aws.amazon.com/certificate-manager/) - SSL/TLS certificates (optional)
- [Lambda@Edge](https://aws.amazon.com/lambda/edge/) - Request/response manipulation (optional)

**Example:**

```typescript
import { Cdk, Static, type StaticProps } from "@thunder-so/thunder";

const config: StaticProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "web",
environment: "prod",
rootDir: ".",
outputDir: "dist",

// Optional: Custom domain
domain: "example.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",

// Optional: Lambda@Edge for redirects/headers/rewrites
redirects: [{ source: "/old", destination: "/" }],
rewrites: [{ source: "/old", destination: "/new" }],
headers: [{ path: "/*", name: "X-Custom-Header", value: "value" }],
};

new Static(new Cdk.App(), "myapp-web-prod-stack", config);
```

---

### Lambda

Deploy serverless functions with [API Gateway](https://aws.amazon.com/api-gateway/) and optional [Lambda Function URL](https://docs.aws.amazon.com/lambda/latest/dg/lambda-urls.html).

**Best for:** Serverless APIs, microservices, event-driven applications

**AWS Resources:**

- [Lambda Function](https://aws.amazon.com/lambda/) - Compute layer
- [API Gateway](https://aws.amazon.com/api-gateway/) - HTTP API with custom domain support
- [CloudWatch Logs](https://aws.amazon.com/cloudwatch/) - Logging and monitoring
- [Secrets Manager](https://aws.amazon.com/secrets-manager/) - Secure secret injection (optional)

**Example:**

```typescript
import { Cdk, Lambda, type LambdaProps } from "@thunder-so/thunder";

const config: LambdaProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "api",
environment: "prod",
rootDir: ".",

functionProps: {
runtime: Cdk.aws_lambda.Runtime.NODEJS_22_X,
architecture: Cdk.aws_lambda.Architecture.ARM_64,
codeDir: "src",
handler: "index.handler",
memorySize: 512,
timeout: 30,
url: true, // Enable function URL
keepWarm: true, // Prevent cold starts
variables: [{ NODE_ENV: "production" }],
secrets: [{ key: "DATABASE_URL", resource: "arn:aws:secretsmanager:..." }],
},

// Optional: Custom domain
domain: "api.example.com",
regionalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new Lambda(new Cdk.App(), "myapp-api-prod-stack", config);
```

---

### Fargate

Deploy containerized applications on [ECS Fargate](https://aws.amazon.com/fargate/) with Application Load Balancer and [CloudFront](https://aws.amazon.com/cloudfront/).

**Best for:** Containerized web applications, microservices, long-running processes

**AWS Resources:**

- [ECS Cluster](https://aws.amazon.com/ecs/) - Container orchestration
- [Fargate Task](https://aws.amazon.com/fargate/) - Serverless containers
- [Application Load Balancer](https://aws.amazon.com/elasticloadbalancing/) - Traffic distribution
- [ECR Repository](https://aws.amazon.com/ecr/) - Container registry (via CodePipeline)
- [CloudWatch Logs](https://aws.amazon.com/cloudwatch/) - Container logging

**Example:**

```typescript
import { Cdk, Fargate, type FargateProps } from "@thunder-so/thunder";

const config: FargateProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "api",
environment: "prod",
rootDir: ".",

serviceProps: {
architecture: Cdk.aws_ecs.CpuArchitecture.ARM64,
desiredCount: 2,
cpu: 512, // 0.5 vCPU
memorySize: 1024, // 1 GB
port: 3000,
healthCheckPath: "/health",
variables: [{ NODE_ENV: "production" }],
dockerFile: "Dockerfile",
},

// Optional: Custom domain
domain: "api.example.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new Fargate(new Cdk.App(), "myapp-api-prod-stack", config);
```

---

### EC2

Deploy Docker containers on [EC2](https://aws.amazon.com/ec2/) instances with Elastic IP for simple, cost-effective hosting.

**Best for:** Single-instance applications, development environments, simple Docker deployments

**AWS Resources:**

- [EC2 Instance](https://aws.amazon.com/ec2/) - Virtual server
- [Elastic IP](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/elastic-ip-addresses-eip.html) - Static public IP
- [VPC](https://aws.amazon.com/vpc/) - Network isolation
- [Security Group](https://docs.aws.amazon.com/vpc/latest/userguide/security-groups.html) - Firewall rules
- [Route53](https://aws.amazon.com/route53/) - DNS records (optional)

**Example:**

```typescript
import { Cdk, Ec2, type Ec2Props } from "@thunder-so/thunder";

const config: Ec2Props = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "api",
environment: "prod",
rootDir: ".",

serviceProps: {
instanceType: "t3.micro",
port: 3000,
authorizedKeys: ["ssh-rsa AAAAB3... user@example.com"],
dockerFile: "Dockerfile",
variables: [{ NODE_ENV: "production" }],
},

// Optional: Custom domain with SSL
domain: "api.example.com",
hostedZoneId: "Z123456789",
acmeEmail: "admin@example.com", // For Let's Encrypt
};

new Ec2(new Cdk.App(), "myapp-api-prod-stack", config);
```

---

### Serverless Frameworks

Deploy modern meta-frameworks as serverless applications with unified infrastructure - Lambda for server-side rendering and S3 for static assets, all behind CloudFront.

**Best for:** Full-stack applications with server-side rendering, API routes, and static asset optimization

**Supported Frameworks:** Nuxt, Astro, TanStack Start, SvelteKit, Solid Start, AnalogJS, or any Vite/Nitro-based framework using the generic `Serverless` construct.

**AWS Resources:**

- [Lambda Function](https://aws.amazon.com/lambda/) - SSR server with container support
- [S3 Bucket](https://aws.amazon.com/s3/) - Static assets with OAC
- [CloudFront Distribution](https://aws.amazon.com/cloudfront/) - Global CDN with custom domain
- [API Gateway](https://aws.amazon.com/api-gateway/) - HTTP API for server functions
- [Route53](https://aws.amazon.com/route53/) - DNS management (optional)
- [ACM](https://aws.amazon.com/certificate-manager/) - SSL certificates (optional)

**Supported Frameworks:**

- [TanStack Start](https://tanstack.com/start) - Type-safe full-stack React framework
- [Nuxt](https://nuxt.com/) - Vue-based full-stack framework
- [Astro](https://astro.build/) - Content-focused web framework with islands architecture
- [SvelteKit](https://kit.svelte.dev/) - Svelte-based full-stack framework
- [Solid Start](https://start.solidjs.com/) - SolidJS full-stack framework
- [AnalogJS](https://analogjs.org/) - Angular-based full-stack framework

#### TanStack Start

**Example:**

```typescript
import {
Cdk,
TanStackStart,
type TanStackStartProps,
} from "@thunder-so/thunder";

const config: TanStackStartProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "web",
environment: "prod",
rootDir: ".",

serverProps: {
runtime: Cdk.aws_lambda.Runtime.NODEJS_22_X,
architecture: Cdk.aws_lambda.Architecture.ARM_64,
memorySize: 1792,
timeout: 10,
keepWarm: true,
variables: [{ NODE_ENV: "production" }],
},

// Optional: Custom domain
domain: "myapp.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new TanStackStart(new Cdk.App(), "myapp-web-prod-stack", config);
```

#### Nuxt

**Example:**

```typescript
import { Cdk, Nuxt, type NuxtProps } from "@thunder-so/thunder";

const config: NuxtProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "web",
environment: "prod",
rootDir: ".",

serverProps: {
runtime: Cdk.aws_lambda.Runtime.NODEJS_22_X,
architecture: Cdk.aws_lambda.Architecture.ARM_64,
memorySize: 1792,
timeout: 10,
keepWarm: true,
streaming: true,
variables: [{ NODE_ENV: "production" }],
secrets: [{ key: "DATABASE_URL", resource: "arn:aws:secretsmanager:..." }],
},

// Optional: Custom domain
domain: "myapp.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new Nuxt(new Cdk.App(), "myapp-web-prod-stack", config);
```

#### Astro

**Example:**

```typescript
import { Cdk, Astro, type AstroProps } from "@thunder-so/thunder";

const config: AstroProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "web",
environment: "prod",
rootDir: ".",

serverProps: {
runtime: Cdk.aws_lambda.Runtime.NODEJS_22_X,
architecture: Cdk.aws_lambda.Architecture.ARM_64,
memorySize: 1024,
timeout: 10,
keepWarm: true,
variables: [{ NODE_ENV: "production" }],
},

// Optional: Custom domain
domain: "myapp.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new Astro(new Cdk.App(), "myapp-web-prod-stack", config);
```

#### SvelteKit

**Example:**

```typescript
import { Cdk, SvelteKit, type SvelteKitProps } from "@thunder-so/thunder";

const config: SvelteKitProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "web",
environment: "prod",
rootDir: ".",

serverProps: {
runtime: Cdk.aws_lambda.Runtime.NODEJS_22_X,
architecture: Cdk.aws_lambda.Architecture.ARM_64,
memorySize: 1024,
timeout: 10,
keepWarm: true,
variables: [{ NODE_ENV: "production" }],
},

// Optional: Custom domain
domain: "myapp.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new SvelteKit(new Cdk.App(), "myapp-web-prod-stack", config);
```

#### Solid Start

**Example:**

```typescript
import { Cdk, SolidStart, type SolidStartProps } from "@thunder-so/thunder";

const config: SolidStartProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "web",
environment: "prod",
rootDir: ".",

serverProps: {
runtime: Cdk.aws_lambda.Runtime.NODEJS_22_X,
architecture: Cdk.aws_lambda.Architecture.ARM_64,
memorySize: 1024,
timeout: 10,
keepWarm: true,
variables: [{ NODE_ENV: "production" }],
},

// Optional: Custom domain
domain: "myapp.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new SolidStart(new Cdk.App(), "myapp-web-prod-stack", config);
```

#### AnalogJS

**Example:**

```typescript
import { Cdk, AnalogJS, type AnalogJSProps } from "@thunder-so/thunder";

const config: AnalogJSProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "web",
environment: "prod",
rootDir: ".",

serverProps: {
runtime: Cdk.aws_lambda.Runtime.NODEJS_22_X,
architecture: Cdk.aws_lambda.Architecture.ARM_64,
memorySize: 1024,
timeout: 10,
keepWarm: true,
variables: [{ NODE_ENV: "production" }],
},

// Optional: Custom domain
domain: "myapp.com",
globalCertificateArn: "arn:aws:acm:us-east-1:...",
hostedZoneId: "Z123456789",
};

new AnalogJS(new Cdk.App(), "myapp-web-prod-stack", config);
```

---

### Template

Deploy [Coolify](https://coolify.io/)-style templates on EC2. Automatically fetches and hydrates Docker Compose templates from the [Coolify templates repository](https://github.com/coollabsio/coolify).

**Best for:** Self-hosted applications, databases, dev tools (e.g., n8n, WordPress, databases)

**AWS Resources:** Same as [EC2](#ec2)

**Example:**

```typescript
import {
Cdk,
Template,
type TemplateProps,
fetchTemplate,
hydrateTemplate,
} from "@thunder-so/thunder";
import { InstanceType, InstanceClass, InstanceSize } from "aws-cdk-lib/aws-ec2";

async function main() {
// Fetch template from Coolify repository
const { parsed: parsedTemplate, port } = await fetchTemplate("n8n");

// Hydrate template with variables
const hydrateResult = hydrateTemplate(parsedTemplate, {
domain: "n8n.example.com",
fallbackPort: port,
});

const config: TemplateProps = {
env: { account: "123456789012", region: "us-east-1" },
application: "myapp",
service: "n8n",
environment: "prod",

templateSlug: "n8n",
instanceType: InstanceType.of(InstanceClass.T3, InstanceSize.MICRO),
authorizedKeys: ["ssh-rsa AAAAB3... user@example.com"],
hydrateResult,

// Optional: Custom domain with SSL
domain: "n8n.example.com",
hostedZoneId: "Z123456789",
acmeEmail: "admin@example.com",
};

new Template(new Cdk.App(), "myapp-n8n-prod-stack", config);
}

main();
```

**Available Templates:** See the [Coolify templates repository](https://github.com/coollabsio/coolify/tree/v4.x/templates/compose) for available templates.

---

## CLI Commands

| Command | Description |
| :----------- | :-------------------------------- |
| `th init` | Scaffold a new project or service |
| `th deploy` | Deploy stacks to AWS |
| `th destroy` | Remove resources from AWS |

## Documentation

For detailed documentation on each construct and advanced configurations, see the [Wiki](https://github.com/thunder-so/thunder/wiki).

### Static

| Guide | Description |
| :---------------------------------------------------------- | :------------------------------------------------------ |
| [static-basic.md](./docs/static-basic.md) | Deploy a static site or SPA to S3 + CloudFront |
| [static-edge-functions.md](./docs/static-edge-functions.md) | Redirects, rewrites, and custom headers via Lambda@Edge |
| [static-full.md](./docs/static-full.md) | Full `StaticProps` configuration reference |

### Lambda

| Guide | Description |
| :-------------------------------------------------- | :------------------------------------------------ |
| [lambda-basic.md](./docs/lambda-basic.md) | Deploy a serverless API with Lambda + API Gateway |
| [lambda-containers.md](./docs/lambda-containers.md) | Container images and Bun runtime |
| [lambda-full.md](./docs/lambda-full.md) | Full `LambdaProps` configuration reference |

### Fargate

| Guide | Description |
| :------------------------------------------------ | :-------------------------------------------- |
| [fargate-basic.md](./docs/fargate-basic.md) | Deploy a containerized service on ECS Fargate |
| [fargate-nixpacks.md](./docs/fargate-nixpacks.md) | Auto-generate Dockerfiles with Nixpacks |
| [fargate-full.md](./docs/fargate-full.md) | Full `FargateProps` configuration reference |

### Serverless (Full-Stack Frameworks)

| Guide | Description |
| :------------------------------------ | :----------------------------------------- |
| [serverless.md](./docs/serverless.md) | Deploy full-stack meta-frameworks with SSR |

### Framework Guides

**Static Deployment:**

- [Next.js Static](./docs/frameworks/nextjs-static.md)
- [Astro Static](./docs/frameworks/astro-static.md)

**Serverless (Lambda + S3 + CloudFront):**

- [Nuxt](./docs/frameworks/nuxt-serverless.md)
- [Astro SSR](./docs/frameworks/astro-serverless.md)
- [TanStack Start](./docs/frameworks/tanstack-start-serverless.md)
- [SvelteKit](./docs/frameworks/sveltekit-serverless.md)
- [Solid Start](./docs/frameworks/solidstart-serverless.md)
- [AnalogJS](./docs/frameworks/analogjs-serverless.md)

**Fargate (Containers):**

- [Next.js with Dockerfile](./docs/frameworks/nextjs-fargate-dockerfile.md)
- [Next.js with Nixpacks](./docs/frameworks/nextjs-fargate-nixpacks.md)
- [Astro](./docs/frameworks/astro-fargate.md)
- [Nuxt](./docs/frameworks/nuxt-fargate.md)
- [TanStack Start](./docs/frameworks/tanstack-start-fargate.md)
- [SvelteKit](./docs/frameworks/sveltekit-fargate.md)
- [Solid Start](./docs/frameworks/solidstart-fargate.md)
- [AnalogJS](./docs/frameworks/analogjs-fargate.md)

## License

Apache-2.0