Skip to content

Commit 950c118

Browse files
committed
Added CloudFormation
1 parent b6aeb46 commit 950c118

File tree

3 files changed

+240
-5
lines changed

3 files changed

+240
-5
lines changed

CF_spring_cloud_aws_sample.yml

Lines changed: 225 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,225 @@
1+
AWSTemplateFormatVersion: 2010-09-09
2+
Description: AWS Cloud Formation Spring Cloud Aws Example
3+
4+
Parameters:
5+
6+
DatabasePassword:
7+
Description: Database Password
8+
Type: String
9+
NoEcho: true
10+
Default: your_password
11+
12+
KeyName:
13+
Description: "Name of an existing EC2 KeyPair to enable SSH access to the instance."
14+
Type: AWS::EC2::KeyPair::KeyName
15+
ConstraintDescription: "must be the name of an existing EC2 KeyPair."
16+
17+
Mappings:
18+
RegionMap:
19+
eu-west-1:
20+
AMI: ami-02df9ea15c1778c9c
21+
22+
Resources:
23+
24+
SpringCloudAwsRole:
25+
Type: 'AWS::IAM::Role'
26+
Properties:
27+
AssumeRolePolicyDocument:
28+
Version: 2012-10-17
29+
Statement:
30+
- Effect: Allow
31+
Principal:
32+
Service:
33+
- ec2.amazonaws.com
34+
Action:
35+
- 'sts:AssumeRole'
36+
Path: /
37+
Policies:
38+
- PolicyName: SpringCloudAwsRolePolicy
39+
PolicyDocument:
40+
Version: 2012-10-17
41+
Statement:
42+
- Effect: Allow
43+
Action:
44+
- 'rds:DescribeDBInstances'
45+
- 's3:PutObject'
46+
- 's3:GetObject'
47+
- 's3:DeleteObject'
48+
- 'secretsmanager:DescribeSecret'
49+
- 'secretsmanager:GetSecretValue'
50+
- 'secretsmanager:ListSecrets'
51+
- 'secretsmanager:ListSecretVersionIds'
52+
53+
Resource: '*'
54+
RoleName: SpringCloudAwsSampleRole
55+
56+
SpringCloudAwsInstanceProfile:
57+
Type: 'AWS::IAM::InstanceProfile'
58+
DependsOn: SpringCloudAwsRole
59+
Properties:
60+
Path: /
61+
Roles:
62+
- SpringCloudAwsSampleRole
63+
64+
SpringCloudAwsRDS:
65+
Type: AWS::RDS::DBInstance
66+
DependsOn:
67+
- SpringCloudAwsRole
68+
Properties:
69+
AllocatedStorage: '5'
70+
DBInstanceIdentifier: springaws
71+
DBInstanceClass: db.t2.micro
72+
Engine: MySQL
73+
DBName: springaws
74+
MasterUsername: springaws
75+
MasterUserPassword: !Ref DatabasePassword
76+
MultiAZ: false
77+
PubliclyAccessible: true
78+
DBSecurityGroups:
79+
- !Ref SpringCloudAwsRDSSecurityGroup
80+
DeletionPolicy: Delete
81+
82+
SpringCloudAwsRDSSecurityGroup:
83+
Type: AWS::RDS::DBSecurityGroup
84+
Properties:
85+
GroupDescription : Security Group for RDS public Access
86+
DBSecurityGroupIngress:
87+
- CIDRIP: 0.0.0.0/0
88+
89+
SpringCloudAwsServerSecurityGroup:
90+
Type: 'AWS::EC2::SecurityGroup'
91+
Properties:
92+
GroupDescription: Security Group for Spring server
93+
SecurityGroupIngress:
94+
- IpProtocol: tcp
95+
FromPort: 8080
96+
ToPort: 8080
97+
CidrIp: 0.0.0.0/0
98+
99+
S3bucket:
100+
Type: 'AWS::S3::Bucket'
101+
Properties:
102+
BucketName: spring-cloud-aws-sample-s3
103+
DeletionPolicy: Delete
104+
105+
BucketPolicy:
106+
Type: 'AWS::S3::BucketPolicy'
107+
DependsOn: S3bucket
108+
Properties:
109+
Bucket: 'spring-cloud-aws-sample-s3'
110+
PolicyDocument:
111+
Version: '2012-10-17'
112+
Statement:
113+
- Sid: 'AddPerm'
114+
Principal: '*'
115+
Action: 's3:GetObject'
116+
Effect: 'Allow'
117+
Resource:
118+
- 'arn:aws:s3:::spring-cloud-aws-sample-s3/*'
119+
120+
SpringCloudAwsEC2Instance:
121+
Type: AWS::EC2::Instance
122+
Metadata:
123+
Comment: Spring Using AWS services
124+
AWS::CloudFormation::Init:
125+
config:
126+
files:
127+
"/etc/cfn/cfn-hup.conf":
128+
content: !Sub |
129+
[main]
130+
stack=${AWS::StackId}
131+
region=${AWS::Region}
132+
mode: "000400"
133+
owner: "root"
134+
group: "root"
135+
"/etc/cfn/hooks.d/cfn-auto-reloader.conf":
136+
content: !Sub |
137+
[cfn-auto-reloader-hook]
138+
triggers=post.update
139+
path=Resources.SpringCloudAwsEC2Instance.Metadata.AWS::CloudFormation::Init
140+
action=/usr/local/bin/cfn-init -v --stack ${AWS::StackName} --resource SpringCloudAwsEC2Instance --region ${AWS::Region}
141+
mode: "000400"
142+
owner: "root"
143+
group: "root"
144+
"/usr/local/bin/installSoftware.sh":
145+
content: |
146+
#!/bin/bash -xe
147+
set -eu -o pipefail
148+
# installing necessary software
149+
apt-get update
150+
apt-get install -y awscli python-pip
151+
152+
pip install --upgrade awscli
153+
154+
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | apt-key add -
155+
add-apt-repository "deb [arch=amd64] https://download.docker.com/linux/ubuntu xenial stable"
156+
apt-get update
157+
apt-get install -y docker-ce
158+
mode: "000755"
159+
owner: "root"
160+
group: "root"
161+
"/usr/local/bin/check_app_ready.sh":
162+
content: |
163+
#!/bin/bash -xe
164+
set -eu -o pipefail
165+
166+
sleep 1m
167+
168+
while true
169+
do
170+
HTTP_STATUS=$(curl -Ik http://localhost/ | head -n1 | awk '{print $2}')
171+
if [ $HTTP_STATUS == 200 ]; then
172+
break
173+
fi
174+
sleep 1
175+
done
176+
177+
mode: "000755"
178+
owner: "root"
179+
group: "root"
180+
Properties:
181+
ImageId: !FindInMap [RegionMap, !Ref 'AWS::Region', AMI]
182+
InstanceType: t2.micro
183+
KeyName: !Ref KeyName
184+
IamInstanceProfile: !Ref SpringCloudAwsInstanceProfile
185+
SecurityGroupIds:
186+
- !GetAtt 'SpringCloudAwsServerSecurityGroup.GroupId'
187+
Tags:
188+
- Key: Name
189+
Value: 'spring-aws-cloud-sample'
190+
UserData:
191+
"Fn::Base64":
192+
!Sub |
193+
#!/bin/bash -xe
194+
set -eu -o pipefail
195+
apt-get update
196+
apt-get install -y python-pip
197+
pip install https://s3.amazonaws.com/cloudformation-examples/aws-cfn-bootstrap-latest.tar.gz
198+
199+
cfn-init --region ${AWS::Region} --stack ${AWS::StackId} --resource SpringCloudAwsEC2Instance
200+
201+
# Install needed software
202+
/usr/local/bin/installSoftware.sh || { echo "Error installing software"; exit 1; }
203+
204+
# Run App
205+
docker run -e PROG_OPTS='--spring.profiles.active=prod' -p 80:8080 codeurjc/spring-cloud-aws-sample:latest
206+
207+
/usr/local/bin/check_app_ready.sh || { echo "Error installing software"; exit 1; }
208+
209+
# sending the finish call
210+
/usr/local/bin/cfn-signal -e $? --stack ${AWS::StackId} --resource WaitCondition --region ${AWS::Region}
211+
212+
WaitCondition:
213+
Type: AWS::CloudFormation::WaitCondition
214+
CreationPolicy:
215+
ResourceSignal:
216+
Timeout: PT40M
217+
Count: 1
218+
219+
Outputs:
220+
Application:
221+
Description: "Deployed Spring Application"
222+
Value: !Join
223+
- ''
224+
- - 'http://'
225+
- !GetAtt SpringCloudAwsEC2Instance.PublicDnsName

README.md

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ Then, create an RDS instance, with these properties:
3535

3636
### Create an S3 bucket
3737

38-
Create an S3 bucket, name it `spring-cloud-aws-sample` and give read permissions to anonymous users. Just copy and paste this aws policy to enable anonymous read access:
38+
Create an S3 bucket, name it `spring-cloud-aws-sample-s3` and give read permissions to anonymous users. Just copy and paste this aws policy to enable anonymous read access:
3939

4040
{
4141
"Version":"2012-10-17",
@@ -45,7 +45,7 @@ Create an S3 bucket, name it `spring-cloud-aws-sample` and give read permissions
4545
"Effect":"Allow",
4646
"Principal": "*",
4747
"Action":["s3:GetObject"],
48-
"Resource":["arn:aws:s3:::spring-cloud-aws-sample/*"]
48+
"Resource":["arn:aws:s3:::spring-cloud-aws-sample-s3/*"]
4949
}
5050
]
5151
}
@@ -64,7 +64,7 @@ Create a new secret named as: `/secrets-app/springaws_prod`. You can insert your
6464

6565
### To run locally
6666

67-
Some configurations are required in your AWS account for this sample to work. Basically, an _S3 bucket_ (by default `spring-cloud-aws-sample` is used, but it can be changed using `cloud.aws.s3.bucket` property), and an _RDS MySQL instance_ open to the world. Additionally, we need an _IAM user_ with access key and programmatic access to AWS API so that we can access AWS resources from our development machine.
67+
Some configurations are required in your AWS account for this sample to work. Basically, an _S3 bucket_ (by default `spring-cloud-aws-sample-s3` is used, but it can be changed using `cloud.aws.s3.bucket` property), and an _RDS MySQL instance_ open to the world. Additionally, we need an _IAM user_ with access key and programmatic access to AWS API so that we can access AWS resources from our development machine.
6868

6969
#### Create an IAM User
7070

@@ -149,6 +149,16 @@ If your EC2 instance has the appropriate role (see prerequisites above), and the
149149

150150
As you can see is not necessary to put database credentials to run the application, it gets the necessary values from AWS Secret Manager.
151151

152+
### Using CloudFormation
153+
154+
To run with CloudFormation is not necessary to create any AWS resources, only secrets. Steps are the following
155+
156+
1. Insert your secret properties as explained in section [AWS Secrets Manager](#aws-secrets-manager)
157+
2. As parameters to run your stack, you'll need to specify:
158+
- Database password
159+
- Key Name (for ssh)
160+
3. Go to your application by click to the link given at the output section of the cloudformation after the stack have been created.
161+
152162

153163

154164

src/main/resources/application.properties

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,11 +16,11 @@ cloud.aws.region.static=eu-west-1
1616
cloud.aws.stack.auto=false
1717

1818
# Credentials (unnecessary when running in an EC2 instance with a role having enough permissions for S3 and RDS)
19-
#cloud.aws.credentials.accessKey="key"
19+
#cloud.aws.credentials.accessKey="key"
2020
#cloud.aws.credentials.secretKey="secret"
2121

2222
# In AWS use this instead, and create an EC2 role
2323
cloud.aws.credentials.instanceProfile=true
2424

2525
# S3
26-
cloud.aws.s3.bucket=spring-cloud-aws-sample
26+
cloud.aws.s3.bucket=spring-cloud-aws-sample-s3

0 commit comments

Comments
 (0)