Deploy ASP.NET Core App to AWS EB Running a Linux, using Azure DevOps — Part 1
A single-container, dockerized web app is chosen to ease the deployment to Linux host.
Our system has been moved from Windows environment to Linux environment to cut license cost. Fortunately, ASP.NET Core is a web framework with cross platform support and runs very fast in Linux as stated on my previous article.
In order to deploy ASP.NET Core to AWS to get its auto scale feature, we can use ElasticBeanstalk (EB) as an alternative to ECR, because I think it’s easier for deploying monolith system in EB. And the reason why I use Docker is because that’s the only fastest way to deploy ASP.NET Core website using Linux environment in EB.
2. What This Article Cover
- Use docker preconfigured platform of AWS EB instance running Amazon Linux, to host dockerized ASP.NET Core site
- Enable HTTPS using AWS EB with custom domain and AWS Certificate Manager
- Implement CI/CD using Azure DevOps with a Linux user agent
- Auto redirection from non-HTTPS/naked URL to fully qualified HTTPS URL
3. Technology Stacks
- Web App: ASP.NET Core MVC, written in C#
- Unit Test: xUnit
- Host OS: Linux
- Web Server: Nginx with Kestrel as reverse proxy
- Containerization: Docker
- IaaS: AWS EB (Elastic Beanstalk), Classic LB (Load Balancer), ECR (Elastic Container Registry), ACM (AWS Certificate Manager)
- DevOps tools: Azure DevOps
- AWS Account
- Basic knowledge of ASP.NET
- Basic knowledge of cloud infrastructure
5. Hands On
You can always jump to step that you want to explore. To give a big picture, this ‘hands on’ is structured as below:
Step 1–5: Preparing the web app cloud stack using AWS [Part 1 of this article — You’re here]
Step 6–9: Preparing Azure DevOps CI/CD pipeline [Part 2]
Step 10–11: Develop web app using ASP.NET Core and deploy it using CI/CD pipeline [Part 2]
Let’s begin, shall we?
Step 1. Create a domain using AWS Route 53
You can proceed to next step if you already have a domain for your site. Go to AWS Route 53. You can find and register an available domain, or transfer your existing domains to Route 53.
After domain is created, a new hosted zone of your domain will be displayed. You can leave the record sets configuration for now as we don’t have any site to bind yet. Once the EB instance that host your site is running, we will back to record sets configuration to add a record that will be bonded to your site.
Step 2. Create an SSL certificate in AWS ACM
This will make your site can be accessed via HTTPS protocol. Proceed to next step if you already have registered your SSL certificate. Follow the wizard that will guide you for requesting or importing a certificate.
Please be note that SSL will treat www.yourdomain.com (qualified domain) as a different domain from yourdomain.com (naked domain) although it refers to same site. But most of people will just write naked domain in browser address bar to go to some sites. So you have to add both domain (naked and qualified) in the registry.
Also, If you are planning to have multiple sub domains for your site, for ex: sub1.yourdomain.com, sub2.yourdomain.com, we can use asterisk to request a wildcard certificate in the second record in the registry, which should be *.yourdomain.com, replacing the www.yourdomain.com
Step 3. Create AWS EB instance to host web app
Create new application > select environment tier to web server environment > name your environment (ex: production/staging/dev) > select platform in base configuration to preconfigured platform and choose generic that belongs to docker group (We are not going to use .NET platform that using Windows & IIS, instead we choose generic platform because we want to host our web on Linux) > configure more options > configure capacity > set environment type to load balanced > save > configure load balancer as below
Use SSL certificate that you created in Step 2 > Apply. Load balanced environment will enable us to bind internet facing endpoint with SSL. As we are going to use HTTPS, we have to set port 443 on the LB side. For the EB instance side, I prefer to use port 80 for incoming request either from port 80 or 443 of LB side, so there will be HTTPS termination of the incoming request in load balancer. I don’t want to expose any SSL certificate on the web server instance, so I will not open port 443 on the EB instance side. This will ease our docker image configuration.
Step 4. Create DNS record which will be binded to Classic LB
Go to AWS Route 53, hosted zone, select your domain and create an A record that is aliased to Elastic Beanstalk URL. Name field will be your subdomain. Leave name field blank if you want to bind to www. It may take a while for your record to be online. It is better to create an A record aliased to Elastic Beanstalk URL rather than the ELB URL. The reason being that in Elastic Beanstalk, you can start multiple environments within the same application, then swap the URLs around to have blue/green deployment.
This way, if you want to route incoming request to a new environment, you just swap the EB URL and you won’t need to make any DNS changes.
Step 5. Create ECR to store docker image
Follow the wizard to create ECR. After you proceed, take a note on instruction number 1 and 5, and also your repository url with the image tag name (*** .ecr.ap-southeast-1.amazonaws.com/your-asp-project-name:latest) as below. We will use this information in our CI/CD pipeline explained in Part 2 of this article.
Congratulation, that’s everything you need to create the host of our website. In the next tutorial I will show you how to begin deploy the website to these newly created host using Azure DevOps CI/CD.