Azure Kubernetes Service (AKS) - Deploying Angular, ASP.NET Core and SQL Server on Linux

Azure Kubernetes Service (AKS) makes it simple to deploy a managed Kubernetes cluster in Azure. The sample application for this article is developed in Angular, ASP.net core and SQL Server. I will go through the steps needed to deploy these components to AKS.

The dev tools used to develop these components are Visual Studio for Mac/Visual Studio 2017 and Visual Studio Code. AKS Dashboard as well as kubectl commands are used to create Kubernetes resources in AKS.

The sample use case is a front end app (Angular) which loads users from Web API (ASP.net Core) and these users are saved in SQL Server DB. The steps needed to deploy these components to AKS are

  • SQL Server on Linux
    • Create PersistentVolumeClaim
    • Create Secret to specify sa user password
    • Create service for SQL Server
    • Create deployment for SQL Server
  • ASP.net Core Web API 
    • Create ASP.net Core Web API sample application
    • Create a Docker Hub repository
    • Create a docker image 
    • Publish docker image to Docker Hub 
    • Create service for ASP.net Core Web API
    • Create deployment for ASP.net Core Web API 
  • Angular App
    • Create an Angular App sample application
    • Create a Docker Hub repository
    • Create a docker image 
    • Publish docker image to Docker Hub 
    • Create service for Angular App
    • Create deployment for Angular App

This is the first part of this series. You can go though second part of this series which explains multiple ways to load App Configuration in ASP.net Core Web API.

https://blogs.msdn.microsoft.com/atverma/2018/10/19/asp-net-core-2-1-web-api-load-app-configuration-from-appsettings-json-dockerfile-environment-variables-azure-key-vault-secrets-and-kubernetes-configmaps-secrets

Azure Kubernetes Service (AKS) Cluster

In case you don’t have AKS cluster up and running, please go through this article to Create AKS Cluster. Once AKS cluster is up and running, you can go through the rest of the article. The code snippets in this article are mostly yaml snippets and are included for reference only as formatting may get distorted thus please refer to GitHub repository for formatted resources.

SQL Server on Linux

The steps needed to deploy SQL Server to AKS are listed below

Create a Persistent Volume

Persistent volume claim is needed to store SQL Server data and yaml snippet to create a 5 GB storage is displayed below. The deployment file is going to mount files to this storage claim. You can read more about Persistent Volumes. apiVersion: v1kind: PersistentVolumeClaimmetadata:  name: mssql-sample-data-claimspec:  accessModes:  - ReadWriteOnce  resources:   requests:    storage: 5Gi

Create a Kubernetes Secret

The password for sa user will be created as a Kubernetes Secret. Please replace 'UEBzc3dvcmQxJA==' password with actual base64 password you intend to specify for your SQL Server instance. Your can read more about Secrets kind: SecretapiVersion: v1metadata:  name: mssql-sample-secret  namespace: defaultdata:  # Password is P@ssword1$ so update it with password of your choice    SA_PASSWORD: UEBzc3dvcmQxJA==type: Opaque

Create a Kubernetes Service

The next step is to create a Kubernetes Service for SQL Server. As you can see in yaml snippet below, port 1433 is used and type is ClusterIP i.e. this service doesn't has external endpoints. Kubernetes will use to selector 'app: mssql-sample' to map to the deployment as you are going to see next. You can read more about Services apiVersion: v1kind: Servicemetadata:  name: mssql-sample-servicespec:  selector:    app: mssql-sample  ports:    - protocol: TCP      port: 1433      targetPort: 1433  type: ClusterIP

Create a Deployment

The next step is to create a SQL Server deployment which is defined in yaml snippet displayed below and a few pointers are

  • app: mssql-sample matches to the selector defined in the service.
  • I have specified replicas: 1 which means that only one instance of Pod will be created by Kubernetes for this deployment. You can update this value as needed.
  • The docker image being used to create this deployment is image: microsoft/mssql-server-linux.
  • The secret defined in previous step is used in this deployment file to specific sa user password i.e. secretKeyRef: name: mssql-sample-secret. Please note that there are SQL server password policy requirements.
  • Lastly, persistent volume claim created above is also used in this deployment file i.e. persistentVolumeClaim: claimName: mssql-sample-data-claim.

apiVersion: apps/v1beta1kind: Deploymentmetadata:  name: mssql-sample-deploymentspec:  replicas: 1  template:    metadata:      labels:        app: mssql-sample    spec:      terminationGracePeriodSeconds: 10      containers:      - name: mssql        image: microsoft/mssql-server-linux        ports:        - containerPort: 1433        env:        - name: ACCEPT_EULA          value: "Y"        - name: SA_PASSWORD          valueFrom:            secretKeyRef:              name: mssql-sample-secret              key: SA_PASSWORD        volumeMounts:        - name: mssql-persistent-storage          mountPath: /var/opt/mssql      volumes:      - name: mssql-persistent-storage        persistentVolumeClaim:          claimName: mssql-sample-data-claim

The Kubernetes files for setting up SQL Server are available at GitHub.

After creating all the resources needed to configure SQL Server, the next step is to setup ASP.net Core Web API.

ASP.net Core Web API

The idea was to create a plain vanilla ASP.net Core Web API which communicates with SQL Server database and is hosted in AKS cluster. Thus, to keep things simple Auth isn't implemented for this component. The main steps needed to deploy ASP.net Core Web API to AKS are

Create a ASP.net Core Web API solution

You can view source code for this solution at GitHub. Please update DatabaseConnectionString setting in 'appsettings.json' file with the database connection string based on your 'sa' user password. This Web.API uses EntityFrameworkCore to create database and seed sample data. There is only one method in the Controller to get list of users from database to keep things simple.

The main steps needed to deploy this web api to AKS are

Create Docker Image

ASP.net Core Web API project has DockerFile as displayed below

FROM microsoft/dotnet:2.1-aspnetcore-runtime AS baseWORKDIR /appEXPOSE 80FROM microsoft/dotnet:2.1-sdk AS buildWORKDIR /srcCOPY ["SampleWebApp/SampleWebApp.csproj", "."]RUN dotnet restore "SampleWebApp.csproj"COPY . .RUN dotnet build "SampleWebApp.csproj" -c Release -o /appFROM build AS publishRUN dotnet publish "SampleWebApp.csproj" -c Release -o /appFROM base AS finalWORKDIR /appCOPY --from=publish /app .ENTRYPOINT ["dotnet", "SampleWebApp.dll"]

The next step is to create a Docker Hub repository. The commands to build Docker Image are listed below

  • Build Docker Image: docker build -t samplewebapp .
  • Tag Docker Image: docker tag samplewebapp {YOUR_DOCKER_REPO}
  • Publish Image to Docker Hub: docker push {YOUR_DOCKER_REPO}

Please update {YOUR_DOCKER_REPO} placeholder with your docker repository.

Create a Kubernetes Service

The next step is to create a Kubernetes Service for this Web API. As you can see in yaml snippet below since  type: LoadBalancer, AKS is going to create a external endpoint/load balancer ingress for this service. The creation of this service is going to take a while and once done you can get the external endpoint of this service either by opening AKS Dashboard or running Kubectl command kubectl describe services samplewebappapiVersion: v1kind: Servicemetadata:  name: samplewebapp  labels:    app: samplewebappspec:  type: LoadBalancer  ports:  - protocol: TCP    port: 80  selector:    app: samplewebapp
Please take a note of this endpoint as it is going to be used by Angular App.

Create a Kubernetes Deployment

The next step is to create a Kubernetes Deployment for ASP.net Web API application. The yaml snipped is displayed below and a few pointers are

  • You need to update image path i.e. image: atverma/samplewebapp with your docker hub repository
  • You can change the number of pods by updating replicas: 1
  • Label app: samplewebapp has to match the selector defined in the service

apiVersion: apps/v1beta1kind: Deploymentmetadata:  name: samplewebapp  namespace: default  labels:    app: samplewebappspec:  replicas: 1  selector:    matchLabels:        app: samplewebapp  template:    metadata:      name: samplewebapp      labels:        app: samplewebapp    spec:      containers:      - name: samplewebapp        image: atverma/samplewebapp        resources: {}        terminationMessagePath: "/dev/termination-log"        terminationMessagePolicy: File        imagePullPolicy: Always        securityContext:          privileged: false      restartPolicy: Always      terminationGracePeriodSeconds: 30      dnsPolicy: ClusterFirst      securityContext: {}      schedulerName: default-scheduler
The Kubernetes snippets to create these resources can be downloaded from GitHub. The next step is to setup Angular App.

Angular App

This is the final component and before we proceed, we need to update external endpoint value of the Web API Service in Angular App. You can view the source code of Angular App at GitHub.

You will need to update environment.ts and environment.prod.ts to update API_URLexport const environment = { ApplicationConfig: { 'API_URL': 'https://{YOUR_WEB_API_ENDPOINT}/api/' } };

The main steps needed to deploy Angular App to AKS are

Create Docker Image

Angular App project has DockerFile as displayed below

FROM node as node# set working directoryRUN mkdir /usr/src/appWORKDIR /usr/src/appCOPY package.json /usr/src/app/package.jsonRUN npm installCOPY . /usr/src/appARG env=prodRUN npm run build -- --prodFROM nginxCOPY --from=node /usr/src/app/dist/ /usr/share/nginx/htmlCOPY nginx-custom.conf /etc/nginx/conf.d/default.conf
The next step is to create a Docker Hub repository. The commands to build Docker Image are listed below

  • Build Docker Image: docker build -t sampleangularapp .
  • Tag Docker Image: docker tag sampleangularapp {YOUR_DOCKER_REPO}
  • Publish Image to Docker Hub: docker push {YOUR_DOCKER_REPO}

Please update {YOUR_DOCKER_REPO} placeholder with your docker repository.

Create a Kubernetes Service

The next step is to create a Kubernetes Service for this Anguar App. As you can see in yaml snippet below since  type: LoadBalancer, AKS is going to create a external endpoint/load balancer ingress for this service. The creation of this service is going to take a while and once done you can get the external endpoint of this service either by opening AKS Dashboard or running Kubectl command kubectl describe services sampleangularappapiVersion: v1 kind: Service metadata:   name: sampleangularapp   labels:     app: sampleangularapp spec:   type: LoadBalancer   ports:   - protocol: TCP     port: 80   selector:     app: sampleangularapp
Please take a note of external endpoint as this will be needed to launch Angular App in browser later.

Create a Kubernetes Deployment

The next step is to create a Kubernetes Deployment for Angular application. The yaml snippet is displayed below and a few pointers are

  • You need to update image path i.e. image: atverma/sampleangularapp with your docker hub repository
  • Two pods will be created for this deployment. You can change the number of pods by updating replicas: 2
  • Label app: sampleangularapp has to match the selector defined in the service

kind: DeploymentapiVersion: extensions/v1beta1metadata:  name: sampleangularapp  namespace: default  labels:    app: sampleangularappspec:  replicas: 2  selector:    matchLabels:      app: sampleangularapp  template:    metadata:      name: sampleangularapp      labels:        app: sampleangularapp    spec:      containers:      - name: sampleangularapp        image: atverma/sampleangularapp        resources: {}        terminationMessagePath: "/dev/termination-log"        terminationMessagePolicy: File        imagePullPolicy: Always        securityContext:          privileged: false      restartPolicy: Always      terminationGracePeriodSeconds: 30      dnsPolicy: ClusterFirst      securityContext: {}      schedulerName: default-scheduler
The Kubernetes snippets to create these resources can be downloaded from GitHub.

Running Angular App

After all the components have been configured and deployed to Azure Kubernetes Service (AKS) cluster, run the Angular App by opening external endpoint (of Angular App Service) in browser and you will see list of users on click of 'Get All Users (DB)' button.

Summary

This article covered the ease of deploying multi-tier components to Azure Kubernetes Service (AKS). The complete source code for this application can be downloaded from GitHub