1+ AWSTemplateFormatVersion : ' 2010-09-09'
2+ Description : ' Neotoma API infrastructure'
3+
4+ Parameters :
5+ Environment :
6+ Type : String
7+ AllowedValues : [dev, prod]
8+ Description : Environment name
9+
10+ ImageUri :
11+ Type : String
12+ Description : ECR image URI
13+
14+ RDSHostname :
15+ Type : String
16+ Description : RDS endpoint
17+
18+ RDSPort :
19+ Type : String
20+ Default : ' 5432'
21+
22+ RDSDatabase :
23+ Type : String
24+ Description : Database name
25+
26+ VPCId :
27+ Type : AWS::EC2::VPC::Id
28+ Description : VPC ID where resources will be created
29+
30+ PrivateSubnets :
31+ Type : List<AWS::EC2::Subnet::Id>
32+ Description : Private subnets for VPC connector
33+
34+ Resources :
35+ # ECR Repository
36+ ECRRepository :
37+ Type : AWS::ECR::Repository
38+ Properties :
39+ RepositoryName : !Sub 'neotoma-api-${Environment}'
40+ ImageScanningConfiguration :
41+ ScanOnPush : true
42+ LifecyclePolicy :
43+ LifecyclePolicyText : |
44+ {
45+ "rules": [
46+ {
47+ "rulePriority": 1,
48+ "selection": {
49+ "tagStatus": "untagged",
50+ "countType": "sinceImagePushed",
51+ "countUnit": "days",
52+ "countNumber": 1
53+ },
54+ "action": {
55+ "type": "expire"
56+ }
57+ }
58+ ]
59+ }
60+
61+ # Secrets for database credentials
62+ DatabaseSecret :
63+ Type : AWS::SecretsManager::Secret
64+ Properties :
65+ Name : !Sub 'neotoma-api/${Environment}/rds-credentials'
66+ Description : RDS credentials for Neotoma API
67+ GenerateSecretString :
68+ SecretStringTemplate : ' {"username": "your-username"}'
69+ GenerateStringKey : ' password'
70+ PasswordLength : 32
71+ ExcludeCharacters : ' "@/\'
72+
73+ # Security Group for App Runner
74+ AppRunnerSecurityGroup :
75+ Type : AWS::EC2::SecurityGroup
76+ Properties :
77+ GroupName : !Sub 'apprunner-neotoma-${Environment}-sg'
78+ GroupDescription : Security group for Neotoma App Runner service
79+ VpcId : !Ref VPCId
80+ SecurityGroupEgress :
81+ - IpProtocol : tcp
82+ FromPort : 5432
83+ ToPort : 5432
84+ CidrIp : 10.0.0.0/8
85+ - IpProtocol : tcp
86+ FromPort : 443
87+ ToPort : 443
88+ CidrIp : 0.0.0.0/0
89+
90+ # VPC Connector for App Runner
91+ VPCConnector :
92+ Type : AWS::AppRunner::VpcConnector
93+ Properties :
94+ VpcConnectorName : !Sub 'neotoma-vpc-connector-${Environment}'
95+ Subnets : !Ref PrivateSubnets
96+ SecurityGroups :
97+ - !Ref AppRunnerSecurityGroup
98+
99+ # App Runner Service
100+ AppRunnerService :
101+ Type : AWS::AppRunner::Service
102+ Properties :
103+ ServiceName : !Sub 'neotoma-api-${Environment}'
104+ SourceConfiguration :
105+ ImageRepository :
106+ ImageIdentifier : !Ref ImageUri
107+ ImageConfiguration :
108+ Port : ' 3001'
109+ RuntimeEnvironmentVariables :
110+ NODE_ENV : !Ref Environment
111+ RDS_HOSTNAME : !Ref RDSHostname
112+ RDS_PORT : !Ref RDSPort
113+ RDS_DATABASE : !Ref RDSDatabase
114+ DB_SSL : ' true'
115+ PORT : ' 3001'
116+ RuntimeEnvironmentSecrets :
117+ RDS_USERNAME : !Sub '${DatabaseSecret}:username::'
118+ RDS_PASSWORD : !Sub '${DatabaseSecret}:password::'
119+ ImageRepositoryType : ECR
120+ AutoDeploymentsEnabled : true
121+ InstanceConfiguration :
122+ Cpu : 0.25 vCPU
123+ Memory : 0.5 GB
124+ InstanceRoleArn : !GetAtt AppRunnerInstanceRole.Arn
125+ NetworkConfiguration :
126+ EgressConfiguration :
127+ EgressType : VPC
128+ VpcConnectorArn : !GetAtt VPCConnector.VpcConnectorArn
129+ HealthCheckConfiguration :
130+ Protocol : HTTP
131+ Path : /v2.0/routes/healthwatch
132+ Interval : 20
133+ Timeout : 5
134+ HealthyThreshold : 1
135+ UnhealthyThreshold : 5
136+
137+ # IAM Role for App Runner Instance
138+ AppRunnerInstanceRole :
139+ Type : AWS::IAM::Role
140+ Properties :
141+ RoleName : !Sub 'AppRunnerInstanceRole-${Environment}'
142+ AssumeRolePolicyDocument :
143+ Version : ' 2012-10-17'
144+ Statement :
145+ - Effect : Allow
146+ Principal :
147+ Service : tasks.apprunner.amazonaws.com
148+ Action : sts:AssumeRole
149+ ManagedPolicyArns :
150+ - arn:aws:iam::aws:policy/service-role/AWSAppRunnerServicePolicyForECRAccess
151+ Policies :
152+ - PolicyName : SecretsManagerAccess
153+ PolicyDocument :
154+ Version : ' 2012-10-17'
155+ Statement :
156+ - Effect : Allow
157+ Action :
158+ - secretsmanager:GetSecretValue
159+ Resource : !Ref DatabaseSecret
160+
161+ Outputs :
162+ ServiceUrl :
163+ Description : App Runner service URL
164+ Value : !Sub 'https://${AppRunnerService.ServiceUrl}'
165+ Export :
166+ Name : !Sub '${AWS::StackName}-ServiceUrl'
167+
168+ ECRRepository :
169+ Description : ECR Repository URI
170+ Value : !Sub '${AWS::AccountId}.dkr.ecr.${AWS::Region}.amazonaws.com/${ECRRepository}'
171+ Export :
172+ Name : !Sub '${AWS::StackName}-ECRRepository'
0 commit comments