Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
65 changes: 65 additions & 0 deletions .github/workflows/deploy.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
name: Deploy Infrastructure and Website

on:
push:
branches: [main]
pull_request:
branches: [main]

permissions:
id-token: write
contents: read

jobs:
deploy:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4

- name: Setup Dart SDK
uses: dart-lang/setup-dart@v1
with:
sdk: stable

- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: "22"

- name: Setup pnpm
uses: pnpm/action-setup@v2
with:
version: 10

- name: Setup Pulumi CLI
uses: pulumi/actions@v4

- name: Install dependencies
run: pnpm install

- name: Build website
run: pnpm build

- name: Configure AWS credentials for infra account
uses: aws-actions/configure-aws-credentials@v5
with:
aws-region: us-east-1
role-to-assume: ${{ secrets.AWS_INFRA_ROLE_ARN }}
mask-aws-account-id: true

- name: Pulumi login
working-directory: infra
run: pulumi login 's3://embedding-explorer-pulumi-state?region=us-east-1&awssdk=v2'

- name: Deploy infrastructure
if: github.ref == 'refs/heads/main'
env:
AWS_WORKLOADS_ROLE_ARN: ${{ secrets.AWS_WORKLOADS_ROLE_ARN }}
run: pnpm run infra:up

- name: Preview infrastructure changes
if: github.event_name == 'pull_request'
env:
AWS_WORKLOADS_ROLE_ARN: ${{ secrets.AWS_WORKLOADS_ROLE_ARN }}
run: pnpm run infra:preview
1 change: 0 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,6 @@ This project uses a pnpm workspace to manage infrastructure, JavaScript bundling

1. **Dart SDK** - Install from [dart.dev](https://dart.dev/get-dart)
2. **pnpm** - For managing the JavaScript toolchain
3. **Pulumi CLI** - For infrastructure management, install from [pulumi.com](https://www.pulumi.com/docs/install/)

### Getting Started

Expand Down
6 changes: 4 additions & 2 deletions infra/Pulumi.prod.yaml
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
secretsprovider: awskms://5bd0c37c-4a15-404a-972d-a2dd93c97118?region=us-east-1&awssdk=v2&profile=infra-provisioning&context_project=embedding-explorer&context_environment=prod
secretsprovider: awskms://5bd0c37c-4a15-404a-972d-a2dd93c97118?region=us-east-1&awssdk=v2&context_project=embedding-explorer&context_environment=prod
encryptedkey: AQICAHjgf0qA6SBRnPa+ecmHyx5sb0x/FGffr+UXHk96B9VakAFX2hj8J2pFkFHsvV+xb96dAAAAfjB8BgkqhkiG9w0BBwagbzBtAgEAMGgGCSqGSIb3DQEHATAeBglghkgBZQMEAS4wEQQMo0kR8RlAjs7ey6ZcAgEQgDuCC/6miDZjoEuCZ2i0O2HWs8ujJSvrT+ONeUZJZXU4UwsZH8v6nRd+MkbZHuvlgvf8D+08OkfFy8G/Fw==
config:
aws:region: us-east-1
aws:profile: workloads-prod
embedding-explorer:domain: embeddings.thestartupapi.com
embedding-explorer:githubRepo: dnys1/embedding_explorer
pulumi:disable-default-providers:
- aws
2 changes: 0 additions & 2 deletions infra/Pulumi.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -4,5 +4,3 @@ runtime:
name: nodejs
options:
packagemanager: pnpm
backend:
url: s3://embedding-explorer-pulumi-state?region=us-east-1&awssdk=v2&profile=infra-provisioning
145 changes: 145 additions & 0 deletions infra/github.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,145 @@
import * as pulumi from "@pulumi/pulumi";
import * as aws from "@pulumi/aws";

import { infraProvider, workloadsProvider } from "./providers";

const config = new pulumi.Config();
const githubRepo = config.require("githubRepo");

// Sets up the necessary roles in the Infrastructure and Workloads accounts so that GitHub actions
// can assume them.
//
// 1. GitHub actions assumes the infra role via OIDC, granting it access to Pulumi state and encryption key.
// 2. The infra role can then assume the workloads role to perform deployments (S3, CloudFront, Route53, ACM, etc).

// GitHub OIDC Identity Provider
const githubOidcProvider = aws.iam.getOpenIdConnectProviderOutput(
{
url: "https://token.actions.githubusercontent.com",
},
{ provider: infraProvider }
);

// IAM Role for GitHub Actions - Infrastructure Provisioning
export const githubActionsInfraRole = new aws.iam.Role(
"githubActionsInfraRole",
{
name: "embedding-explorer-github-actions-infra",
assumeRolePolicy: {
Version: "2012-10-17",
Statement: [
{
Effect: "Allow",
Principal: {
Federated: githubOidcProvider.arn,
},
Action: "sts:AssumeRoleWithWebIdentity",
Condition: {
StringEquals: {
"token.actions.githubusercontent.com:aud": "sts.amazonaws.com",
},
StringLike: {
"token.actions.githubusercontent.com:sub": `repo:${githubRepo}:*`,
},
},
},
],
},
},
{ provider: infraProvider }
);

// IAM Role for GitHub Actions - Workloads (S3/CloudFront operations)
export const githubActionsWorkloadsRole = new aws.iam.Role(
"githubActionsWorkloadsRole",
{
name: "embedding-explorer-github-actions-workloads",
assumeRolePolicy: {
Version: "2012-10-17",
Statement: [
{
Effect: "Allow",
Principal: {
AWS: githubActionsInfraRole.arn,
},
Action: ["sts:AssumeRole", "sts:TagSession"],
},
],
},
},
{ provider: workloadsProvider }
);

// Policy for infrastructure provisioning (Pulumi state management)
new aws.iam.RolePolicy(
"infraProvisioningPolicy",
{
role: githubActionsInfraRole.id,
policy: {
Version: "2012-10-17",
Statement: [
{
Effect: "Allow",
Action: [
"s3:GetObject",
"s3:PutObject",
"s3:DeleteObject",
"s3:ListBucket",
],
Resource: [
"arn:aws:s3:::embedding-explorer-pulumi-state",
"arn:aws:s3:::embedding-explorer-pulumi-state/*",
],
},
{
Effect: "Allow",
Action: ["kms:Decrypt", "kms:Encrypt", "kms:GenerateDataKey"],
Resource:
"arn:aws:kms:us-east-1:*:key/5bd0c37c-4a15-404a-972d-a2dd93c97118",
},
{
Effect: "Allow",
Action: ["sts:AssumeRole", "sts:TagSession"],
Resource: githubActionsWorkloadsRole.arn,
},
{
Effect: "Allow",
Action: [
"iam:CreateRole",
"iam:DeleteRole",
"iam:GetRole",
"iam:PutRolePolicy",
"iam:DeleteRolePolicy",
"iam:ListRolePolicies",
"iam:PassRole",
"iam:CreateOpenIDConnectProvider",
"iam:DeleteOpenIDConnectProvider",
"iam:GetOpenIDConnectProvider",
"iam:ListOpenIDConnectProviders",
],
Resource: "*",
},
],
},
},
{ provider: infraProvider }
);

// Policy for workloads deployment (S3, CloudFront, Route53, ACM, etc.)
new aws.iam.RolePolicy(
"workloadsDeploymentPolicy",
{
role: githubActionsWorkloadsRole.id,
policy: {
Version: "2012-10-17",
Statement: [
{
Effect: "Allow",
Action: ["s3:*", "cloudfront:*", "route53:*", "acm:*"],
Resource: "*",
},
],
},
},
{ provider: workloadsProvider }
);
Loading
Loading