proposal-system/infra/lib/config.ts

81 lines
3 KiB
TypeScript
Raw Normal View History

import * as cdk from 'aws-cdk-lib';
// Multi-environment configuration (PR2). Resolved from CDK context: `-c env=staging`,
// default `prod`. CRITICAL: the prod config MUST keep the exact construct IDs, stack
// names, and resource settings the deployed stacks already use — renaming a deployed
// CloudFormation stack triggers replace-and-delete, which would destroy the RDS instance.
// Only non-prod environments take a stack-name suffix.
export type EnvName = 'prod' | 'staging';
export interface EnvConfig {
readonly envName: EnvName;
readonly env: cdk.Environment;
/** Suffix for stack names + construct IDs. '' for prod so deployed stacks are untouched. */
readonly stackSuffix: string;
/** S3 bucket CORS allowed origins. */
readonly s3CorsOrigins: string[];
/** API Gateway CORS allowed origins. */
readonly apiCorsOrigins: string[];
/** Cognito web-client callback / logout URLs. */
readonly webCallbackUrls: string[];
readonly webLogoutUrls: string[];
/** Cognito hosted-UI domain prefix (must be globally unique). */
readonly cognitoDomainPrefix: string;
/** Email subscribed to the CloudWatch alarm SNS topic. */
readonly alarmsEmail: string;
/** Retain stateful resources (RDS, buckets) on stack deletion. */
readonly retainData: boolean;
}
const ACCOUNT = '328440206208';
const REGION = 'us-east-1';
// Prod values reproduce the currently-deployed stacks EXACTLY (verified against
// foundation-stack.ts / compute-stack.ts) so `cdk diff` shows no prod changes.
const PROD: EnvConfig = {
envName: 'prod',
env: { account: ACCOUNT, region: REGION },
stackSuffix: '',
s3CorsOrigins: ['https://proposals.seahaven.com', 'http://localhost:5173'],
apiCorsOrigins: [
'https://proposals.seahaven.com',
'https://d2yevct5e5uuz5.cloudfront.net',
'http://localhost:5173',
],
webCallbackUrls: [
'https://proposals.seahaven.com/callback',
'http://localhost:5173/callback',
],
webLogoutUrls: ['https://proposals.seahaven.com', 'http://localhost:5173'],
cognitoDomainPrefix: 'proposal-system-seahaven',
alarmsEmail: 'adam@seahavenind.com',
retainData: true,
};
// Staging: same AWS account (Adam, 2026-06-12), suffixed stacks, no permanent domain
// yet (CloudFront default URL + localhost), data not retained.
const STAGING: EnvConfig = {
envName: 'staging',
env: { account: ACCOUNT, region: REGION },
stackSuffix: '-staging',
s3CorsOrigins: ['http://localhost:5173'],
apiCorsOrigins: ['http://localhost:5173'],
webCallbackUrls: ['http://localhost:5173/callback'],
webLogoutUrls: ['http://localhost:5173'],
cognitoDomainPrefix: 'proposal-system-seahaven-staging',
alarmsEmail: 'adam@seahavenind.com',
retainData: false,
};
const CONFIGS: Record<EnvName, EnvConfig> = { prod: PROD, staging: STAGING };
export function resolveConfig(app: cdk.App): EnvConfig {
const name = (app.node.tryGetContext('env') as EnvName | undefined) ?? 'prod';
const config = CONFIGS[name];
if (!config) {
throw new Error(`Unknown env '${name}'. Use -c env=prod (default) or -c env=staging.`);
}
return config;
}