Tutorial on Automated Deployment Using AWS CodeDeploy:
In Part 2 of the AWS DevOps tools, we saw how the CodeBuild service was used to build the J2EE project using Maven.
In this tutorial, we will see how the artifact WAR file that is stored in the S3 bucket can be used for deployment to the Tomcat application server using the CodeDeploy service.
Check out => Ideal Guide on DevOps Training
AWS CodeDeploy is the deployment service that automates the deployment of the application to the Amazon EC2 Linux or Windows instances.
This tutorial will also explain how Jenkins can be integrated with CodeDeploy.
Pre-Requisite:
- An account with AWS preferably a free tier.
- Good and fast internet connection.
- AWS Region used – Asia Pacific (Singapore).
- Amazon Linux or RHEL EC2 instance.
- Tomcat was installed on the EC2 instance.
Note: In order to deploy the content AWS CodeCommit repository is not supported for the CodeDeploy service. Only S3 and GitHub are supported.
Table of Contents:
Setup CodeDeploy
AWS CodeDeploy will need to work namely with two entities to access the EC2 instance and the S3 bucket where the artifacts (WAR file) are stored for deployment. In order to provide permission for the CodeDeploy service to access those IAM, roles will need to be set up. The IAM roles are not defined for IAM users but they only have access to the entities.
#1) Create the first role for the CodeDeploy service to access the EC2 instance.
Launch IAM and click on Roles-> Create Role.
Under AWS Service click on EC2 -> Select your use case -> EC2 and click on Next-> Permissions.
Select the AWSCodeDeployRole under Policy name and click Next->Review.
Enter a role name and click on Create Role.
Lastly, edit the Trust relationship for this role to ensure that the CodeDeploy service is accessible overall or specific regions /endpoints.
Click on the role and update the trust relationship as shown below.
In the policy, change EC2 to Codedeploy and click on Update Trust Policy.
2) Create the second role for the EC2 instance using the CodeDeploy service to access the S3 bucket.
Repeat the above steps for this role and enter as below:
- Go to IAM -> Roles -> Create Role.
- Under AWS Service, select EC2.
- Under that Select your use case again and click on EC2 and click the button Next-> Permissions.
- In the attached permission policy screen, select AmazonS3ReadOnlyAccess and click the button Next-> Review.
- Name the role HW-Codedeploy-EC2-S3 and click on the Create Role.
Both the roles should now be available.
Launch Amazon Linux EC2 Instance
In this section, we now provision the EC2 instance.
While provisioning the instance make sure to select the role HW-Codedeploy-EC2-S3 during Configure Instance Details step. Also, ensure to make open port 8080.
Along with this, we will also need to install the CodeDeploy agent and Tomcat as an application server which will be used for the deployment of our application.
#1) Install and configure CodeDeploy Agent on the Amazon Linux instance
CodeDeploy agent helps in deployments and has to be installed in every instance (environments) where the deployment will be done.
Log in to the Linux instance and download the agent as per the region being used. In our case, it is the Singapore region where the identifier is ap-southeast-1.
The command to download the agent would be in the format:
wget https://aws-codedeploy-<region-identifier>.s3.amazonaws.com/latest/install
#2) Install Tomcat on the EC2 instance
- To install and run Tomcat do the following steps in order.
yum install tomcat7 tomcat7-webapps tomcat7-docs-webapp tomcat7-admin-webapps
- Enable the tomcat user for the application manager. Do the changes as shown in the /etc/tomcat7/tomcat-users.xml file
- Lastly, start Tomcat service.
service tomcat7 start
- Launch Tomcat Web Application Manager and check if it is working using the URL http://<EC2-Instance>:8080/manager
Integrating AWS CodeDeploy with S3
As mentioned in part 2 that CodeDeploy supports only S3 and GitHub as code repository which is used to deploy the latest versions of the application. Since our application WAR file is stored in an S3 bucket, we need to ensure that the format maintained is a ZIP file.
This means that the WAR file should be in a ZIP file which is what is supported by the deployment process using CodeDeploy.
- AWS CLI (Command-line interface) also needs to be installed on the Linux instance. Please refer to the URL to install.
- Run the following steps in the Linux instance to download the WAR from the S3 bucket. The following steps normally need to be done on the build machine.
set AWS_ACCESS_KEY_ID=<Set the access key of the IAM user>
set AWS_SECRET_ACCESS_KEY=<Set the secret key of the IAM user>
set AWS_DEFAULT_REGION=ap-southeast-1
cd /opt/niranjan
aws s3 cp s3://hwcodebuildbucket/HWJavaWebTarget/target/AWS-HelloWorld-1.0.0.war /opt/niranjan
- CodeDeploy uses an appspec.yml file that contains deployment instructions to the EC2 instances. This file has to be at the root of a folder where the application WAR file is downloaded.
Create the appspec.yml file and the scripts folder as shown below:
The events run in the following order during deployment.
#1) ApplicationStop
#2) BeforeInstall
#3) Install (files section is called and WAR file copied)
#4) ApplicationStart
- The folder hierarchy used is
/opt/niranjan
appspec.yml
AWS-HelloWorld-1.0.0.war
scripts
start_application
stop_application
uninstall_war_file
- Scripts contents
stop_application:
curl –user tomcat:tomcat http://ec2-54-169-56-238.ap-southeast-1.compute.amazonaws.com:8080/manager/text/stop?path=/AWS-HelloWorld-1.0.0
start_application:
curl –user tomcat:tomcat http://ec2-54-169-56-238.ap-southeast-1.compute.amazonaws.com:8080/manager/text/start?path=/AWS-HelloWorld-1.0.0
uninstall_war_file
rm -rf /var/lib/tomcat7/webapps/AWS-HelloWorld-1.0.0.war
rm -rf /var/lib/tomcat7/webapps/AWS-HelloWorld-1.0.0
- ZIP the contents and upload the ZIP file to the S3 bucket. Ensure that VERSIONING is enabled on the bucket.
zip –r AWS-HelloWorld-1.0.0.war.zip AWS-HelloWorld-1.0.0.war appspec.yml scripts
aws s3 cp /opt/niranjan/AWS-HelloWorld-1.0.0.war.zip
s3://hwcodebuildbucket/HWJavaWebTarget/target/AWS-HelloWorld-1.0.0.war.zip
ZIP file uploaded to the S3 bucket is as seen in the below screen:
Instead of running the commands one by one you can create an executable script and add the above commands into it and run it every time a new application WAR file is available from the build.
Create CodeDeploy Application
CodeDeploy application is created to ensure that proper revision of the WAR file is deployed to the appropriate environment which is the EC2 instance.
Launch the CodeDeploy service and click on the Create Application button.
Enter Application Name, Deployment Group (Example: QA-Env), and select the EC2 instances running.
At the end of the form select the service role. This is the other role that was created earlier in the tutorial.
Click on the Create Application button.
Select the Deployment Group (QA-Env) and select Actions -> Deploy new revision.
Since the ZIP file is in the S3 bucket, enter the Revision location as follows:
s3://hwcodebuildbucket/HWJavaWebTarget/target/AWS-HelloWorld-1.0.0.war.zip
Click on the Deploy button. The deployment is successful as shown below.
The WAR file is successfully copied to the tomcat webapps directory.
Browse the application URL to ensure that the application is deployed successfully.
Jenkins Integration with AWS CodeDeploy
As we have seen in the previous 2 tutorials, Jenkins integrates very well with AWS DevOps tools. To integrate Jenkins with CodeDeploy, the plugin needs to be installed. Click here to download and install the CodeDeploy plugin.
Firstly enter the Access and Secret Key for the IAM user in Jenkins -> Configuration.
Sample Jenkins Job configuration as part of the Post-build Action step can be seen as shown below:
Conclusion
So far we have seen how CodeDeploy can be used to automate the deployment of a J2EE application WAR file stored in the S3 bucket to the EC2 instance that is running the Tomcat application server.
The series of these three tools i.e. CodeCommit, CodeBuild, and CodeDeploy help in the Continuous Integration and Continuous Delivery aspects of DevOps. Along with these 3 tools, AWS CodePipeline is one other tool that helps in the end-to-end visualization of the application delivery.
Stay tuned to our upcoming tutorial to know more about the .NET web application deployment to AWS using Elastic Beanstalk.