Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.
Comment: Revalidated and updated some of the code for DX8
English
This article provides a tutorial on deploying, running and scaling Joget on Azure Kubernetes Service (AKS). AKS is a managed Kubernetes service offered by Azure.
Info
If you are not familiar with Kubernetes, refer to Joget on Kubernetes for a quick introduction.

Table of Contents

Deploy Joget on Azure Kubernetes Service

...

From the Azure portal, go to the Kubernetes services then Create a Kubernetes cluster.

Image RemovedImage Added

In the Basics page, choose the Subscription, Resource Group and input the Kubernetes cluster name. Adjust the other configuration settings as desired, or leave as default.

Image RemovedImage Added

In the Node pools tab, you can configure to add node pools into the cluster. Read on multiple node pools in AKS. For this guide, we will use a single node configuration.

Image RemovedImage Added

For other tab options - Access, Networking, Integrations, Advanced and Tags, you can leave the default options or make adjustments/changes as necessary. After that, you can click on the Review + create and deploy the Kubernetes cluster. 

Image RemovedImage Added

When the resource has completed their deployment, you can then connect to the cluster (read here) using Azure CLI/Azure Cloud Shell.

...

Once we have a running cluster, you will need to deploy a database to be used by the Joget platform. You can pretty much follow the same method of deploying MySQL DB as in the Joget Kubernetes pageapply the example yaml files below to deploy the PV, PVC and MySQL database to the Kubernetes cluster.

  • Create persistent storage using PersistentVolume and PersistentVolumeClaim
Code Block
kubectl apply -f https://k8s.io/examples/application/mysql/mysql-pv.yaml

...

languageyml
titlemysql-pv.yaml
apiVersion: v1
kind: PersistentVolume
metadata:
  name: mysql-pv-volume
  labels:
    type: local
spec:
  storageClassName: manual
  capacity:
    storage: 10Gi
  accessModes:
    - ReadWriteOnce
  hostPath:
    path: "/mnt/data"
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: mysql-pv-claim
spec:
  storageClassName: manual
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 5Gi


Code Block
kubectl apply -f mysql-pv.yaml
  • Deploy the MySQL image
Code Block
languageyml
titlemysql-deployment.yaml
apiVersion: v1
kind: Service
metadata:
  name: mysql
spec:
  ports:
  - port: 3306
  selector:
    app: mysql
  clusterIP: None
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: mysql
spec:
  selector:
    matchLabels:
      app: mysql
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: mysql
    spec:
      containers:
      - image: mysql:8.0
        name: mysql
        env:
          # Use secret in real usage
        - name: MYSQL_ROOT_PASSWORD
          value: password
        ports:
        - containerPort: 3306
          name: mysql
        volumeMounts:
        - name: mysql-persistent-storage
          mountPath: /var/lib/mysql
      volumes:
      - name: mysql-persistent-storage
        persistentVolumeClaim:
          claimName: mysql-pv-claim


Code Block
kubectl apply -f https://k8s.io/examples/application/mysql/mysql-deployment.yaml
  • Inspect the deployment

...

With the prerequisite database and persistent storage available, you can now deploy Joget. You can apply the example joget-dx7dx8-tomcat9-aks.yaml file to deploy.

Example joget-dx7dx8-tomcat9-aks.yaml;

Code Block
languageyml
apiVersion: apps/v1
kind: Deployment
metadata:
  name: joget-dx7dx8-tomcat9
  labels:
    app: joget-dx7dx8-tomcat9
spec:
  replicas: 1
  selector:
    matchLabels:
      app: joget-dx7dx8-tomcat9
  template:
    metadata:
      labels:
        app: joget-dx7dx8-tomcat9
    spec:
      initContainers:
       - name: init-volume
         image: busybox:1.28
         command: ['sh', '-c', 'chmod -f -R g+w /opt/joget/wflow; exit 0']
         volumeMounts:
           - name: joget-dx7dx8-tomcat9-volume
             mountPath: "/opt/joget/wflow"
      volumes:
        - name: joget-dx7dx8-tomcat9-volume
          persistentVolumeClaim:
            claimName: aks-nfs
      securityContext:
        runAsUser: 1000
        fsGroup: 0
      containers:
        - name: joget-dx7dx8-tomcat9
          image: jogetworkflow/joget-dx7dx8-tomcat9:latest
          ports:
            - containerPort: 8080
            - containerPort: 9080
          volumeMounts:
            - name: joget-dx7dx8-tomcat9-volume
              mountPath: /opt/joget/wflow
          env:
            - name: KUBERNETES_NAMESPACE
              valueFrom:
                fieldRef:
                    fieldPath: metadata.namespace
---
apiVersion: v1
kind: Service
metadata:
  name: joget-dx7dx8-tomcat9
  labels:
    app: joget-dx7dx8-tomcat9
spec:
  ports:
  - name: http
    port: 8080
    targetPort: 8080
  - name: https
    port: 9080
    targetPort: 9080  
  selector:
    app: joget-dx7dx8-tomcat9
  type: ClusterIP
---
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
  name: joget-dx7dx8-tomcat9-clusterrolebinding
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: view
subjects:
  - kind: ServiceAccount
    name: default
    namespace: default

You can then check the deployment progress from the Azure portal. (Or use kubectl commands eg. kubectl get deployment joget-dx7dx8-tomcat9)

Image RemovedImage Added

Image Removed

5.Deploy Ingress for external connections

...

You can refer to the AKS documentation regarding creating ingress-nginx and also the nginx-ingress document.

There are 2 known methods of deploying the Nginx Ingress Controller to the AKS cluster;

...

the nginx-ingress document.

Install using Helm

Using Azure CLI/Cloud shell, set up the Helm for Nginx Ingress

Code Block
helm repo add ingress-nginx https://kubernetes.github.io/ingress-nginx
helm repo update

helm install ingress-nginx ingress-nginx/ingress-nginx --create-namespace --namespace nginx-ingress

Install using yaml file

You can use kubectl apply command.

Code Block
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.4.0/deploy/static/provider/cloud/deploy.yaml --set controller.service.annotations."service\.beta\.kubernetes\.io/azure-load-balancer-health-probe-request-path"=/healthz --set controller.service.externalTrafficPolicy=Local


After the Ingress Controller has been deployed, we can then apply the Ingress yaml so that we can access the Joget application externally.

...

Code Block
languageyml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: joget-dx7dx8-tomcat9-ingress
  annotations:
    nginx.ingress.kubernetes.io/affinity: cookie
    nginx.ingress.kubernetes.io/ssl-redirect: "false"
spec:
  ingressClassName: nginx
  rules:
    - http:
        paths:
          - path: /jw
            pathType: Prefix
            backend:
                service:
                name: joget-dx7dx8-tomcat9
                port:
                  number: 8080

...

Once the setup is complete, click on Done and you will be brought to the Joget App Center.

Image RemovedImage Added

6.Setup cert-manager for TLS termination

...

Code Block
kubectl apply -f https://github.com/cert-manager/cert-manager/releases/download/v1.1015.01/cert-manager.yaml

Configure Let’s Encrypt issuer

...

Code Block
languageyml
apiVersion: cert-manager.io/v1
kind: ClusterIssuerIssuer
  metadata:
     name: letsencrypt-staging
  spec:
     acme:
        # The ACME server URL
        server: https://acme-staging-v02.api.letsencrypt.org/directory
        # Email address used for ACME registration
        email: [updateUpdate email here]
        # Name of a secret used to store the ACME account private key
        privateKeySecretRef:
           name: letsencrypt-staging
        # Enable the HTTP-01 challenge provider
        solvers:
        - http01:
              ingress:
                 classingressClassName:  nginx
Code Block
kubectl apply -f stagingissuer.yaml

...

Code Block
languageyml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: joget-dx7dx8-tomcat9-ingress
  annotations:
    nginx.ingress.kubernetes.io/affinity: cookie
    nginx.ingress.kubernetes.io/ssl-redirect: "true"
    cert-manager.io/cluster-issuer: "letsencrypt-staging"
spec:
  ingressClassName: nginx
  tls:
  - hosts:
    - exampledomain.com
    secretName : aks-jogetworkflow
  rules:
    - host: exampledomain.com
      http:
        paths:
          - path: /jw
            pathType: Prefix
            backend:
              service:
                name: joget-dx7dx8-tomcat9
                port:
                  number: 9080

...

Code Block
languageyml
apiVersion: cert-manager.io/v1
kind: ClusterIssuer
metadata:
  name: letsencrypt-prod
spec:
  acme:
    # The ACME server URL
    server: https://acme-v02.api.letsencrypt.org/directory
    # Email address used for ACME registration
    email: [update email here]
    # Name of a secret used to store the ACME account private key
    privateKeySecretRef:
      name: letsencrypt-prod
    # Enable the HTTP-01 challenge provider
    solvers:
    - http01:
        ingress:
             classingressClassName:  nginx

Update the ingress yaml file with the production annotation.

Code Block
languageyml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
  name: joget-dx7dx8-tomcat9-ingress
  annotations:
    nginx.ingress.kubernetes.io/affinity: cookie
    nginx.ingress.kubernetes.io/ssl-redirect: "true"
    cert-manager.io/issuer: "letsencrypt-prod"
spec:
  ingressClassName: nginx
  tls:
  - hosts:
    - exampledomain.com
    secretName : aks-jogetworkflow
  rules:
    - host: exampledomain.com
    - http:
        paths:
          - path: /jw
            pathType: Prefix
            backend:
              service:
                name: joget-dx7dx8-tomcat9
                port:
                  number: 9080

...

Code Block
kubectl scale –replicas=3 deployment/joget-dx7dx8-tomcat9

Adjust the replica number as you desired and the desired number of pods will initialize and startup.

...