diff --git a/.github/actions/deploy-to-environment/action.yaml b/.github/actions/deploy-to-environment/action.yaml new file mode 100644 index 0000000..58422d4 --- /dev/null +++ b/.github/actions/deploy-to-environment/action.yaml @@ -0,0 +1,59 @@ +name: Deploy to Environment +description: Deploys an image to the defined environment +inputs: + app_name: + description: Application general Name + required: true + acronym: + description: Application acronym + required: true + environment: + description: Logical Github Environment + required: true + job_name: + description: Job/Instance name + required: true + namespace_prefix: + description: Openshift Namespace common prefix + required: true + namespace_environment: + description: Openshift Namespace environment suffix + required: true + openshift_server: + description: Openshift API Endpoint + required: true + openshift_token: + description: Openshift Service Account Token + required: true + +runs: + using: composite + steps: + - name: Checkout repository + uses: actions/checkout@v3 + + - name: Login to OpenShift Cluster + uses: redhat-actions/oc-login@v1 + with: + openshift_server_url: ${{ inputs.openshift_server }} + openshift_token: ${{ inputs.openshift_token }} + insecure_skip_tls_verify: true + namespace: ${{ inputs.namespace_prefix }}-${{ inputs.namespace_environment }} + + - name: Helm Deploy + shell: bash + run: >- + helm upgrade --install --atomic ${{ inputs.job_name }} ${{ inputs.app_name }} + --namespace ${{ inputs.namespace_prefix }}-${{ inputs.namespace_environment }} + --repo https://bcgov.github.io/${{ inputs.app_name }} + --values ./.github/environments/values.${{ inputs.environment }}.yaml + --set image.repository=ghcr.io/${{ github.repository_owner }} + --set image.tag=sha-$(git rev-parse --short HEAD) + --set route.host=${{ inputs.acronym }}-${{ inputs.namespace_environment }}-${{ inputs.job_name }}.apps.silver.devops.gov.bc.ca + --timeout 10m + --wait + + - name: Wait on Deployment + shell: bash + run: | + oc rollout --namespace ${{ inputs.namespace_prefix }}-${{ inputs.namespace_environment }} status dc/${{ inputs.app_name }}-${{ inputs.job_name }} --watch=true diff --git a/.github/environments/values.dev.yaml b/.github/environments/values.dev.yaml new file mode 100644 index 0000000..6e3ff9a --- /dev/null +++ b/.github/environments/values.dev.yaml @@ -0,0 +1,16 @@ +--- +config: + enabled: true + configMap: + FRONTEND_KC_CLIENTID: ches-showcase-frontend-4105 + FRONTEND_KC_REALM: standard + FRONTEND_KC_SERVERURL: https://dev.loginproxy.gov.bc.ca/auth + # FRONTEND_DASHBOARDURL: https://ches-metabase.apps.silver.devops.gov.bc.ca/public/dashboard/6f388f95-dba7-4632-be4c-8855ee645f31 + SERVER_KC_PUBLICKEY: MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuy7zfh2ZgpDV5mH/aXyLDTddZK81rGakJcTy4KvCNOkDDxt1KAhW02lmbCo8YhHCOzjNZBp1+Vi6QiMRgBqAe2GTPZYEiV70aXfROGZe3Nvwcjbtki6HoyRte3SpqLJEIPL2F+hjJkw1UPGnjPTWZkEx9p74b9i3BjuE8RnjJ0Sza2MWw83zoQUZEJRGiopSL0yuVej6t2LO2btVdVf7QuZfPt9ehkcQYlPKpVvJA+pfeqPAdnNt7OjEIeYxinjurZr8Z04hz8UhkRefcWlSbFzFQYmL7O7iArjW0bsSvq8yNUd5r0KCOQkFduwZy26yTzTxj8OLFT91fEmbBBl4rQIDAQAB + SERVER_KC_REALM: standard + SERVER_KC_SERVERURL: https://dev.loginproxy.gov.bc.ca/auth + # SERVER_LOGFILE: ./app.log + SERVER_LOGLEVEL: http + SERVER_PORT: "8080" + SC_CHES_ENDPOINT: https://ches-dev.api.gov.bc.ca/api + SC_CS_TOKEN_ENDPOINT: https://dev.loginproxy.gov.bc.ca/auth/realms/comsvcauth/protocol/openid-connect/token diff --git a/.github/environments/values.pr.yaml b/.github/environments/values.pr.yaml new file mode 100644 index 0000000..ed97d53 --- /dev/null +++ b/.github/environments/values.pr.yaml @@ -0,0 +1 @@ +--- diff --git a/.github/environments/values.prod.yaml b/.github/environments/values.prod.yaml new file mode 100644 index 0000000..6df93c8 --- /dev/null +++ b/.github/environments/values.prod.yaml @@ -0,0 +1,16 @@ +--- +config: + enabled: true + configMap: + FRONTEND_KC_CLIENTID: ches-showcase-frontend-4105 + FRONTEND_KC_REALM: standard + FRONTEND_KC_SERVERURL: https://loginproxy.gov.bc.ca/auth + # FRONTEND_DASHBOARDURL: https://ches-metabase.apps.silver.devops.gov.bc.ca/public/dashboard/6f388f95-dba7-4632-be4c-8855ee645f31 + SERVER_KC_PUBLICKEY: MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAmHiuPKOkpkq4GXN1ktr23rJtDl6Vdu/Y37ZAd3PnQ8/IDfAODvy1Y81aAUZicKe9egolv+OTRANN3yOg+TAbRhkeXLE5p/473EK0aQ0NazTCuWo6Am3oDQ7Yt8x0pw56/qcLtkTuXNyo5EnVV2Z2BzCnnaL31JOhyitolku0DNT6GDoRBmT4o2ItqEVHk5nM25cf1t2zbwI2790W6if1B2qVRkxxivS8tbH7nYC61Is3XCPockKptkH22cm2ZQJmtYd5sZKuXaGsvtyzHmn8/l0Kd1xnHmUu4JNuQ67YiNZGu3hOkrF0Js3BzAk1Qm4kvYRaxbJFCs/qokLZ4Z0W9wIDAQAB + SERVER_KC_REALM: standard + SERVER_KC_SERVERURL: https://loginproxy.gov.bc.ca/auth + # SERVER_LOGFILE: ./app.log + SERVER_LOGLEVEL: http + SERVER_PORT: "8080" + SC_CHES_ENDPOINT: https://ches.api.gov.bc.ca/api + SC_CS_TOKEN_ENDPOINT: https://loginproxy.gov.bc.ca/auth/realms/comsvcauth/protocol/openid-connect/token diff --git a/.github/environments/values.test.yaml b/.github/environments/values.test.yaml new file mode 100644 index 0000000..d1f1fa0 --- /dev/null +++ b/.github/environments/values.test.yaml @@ -0,0 +1,16 @@ +--- +config: + enabled: true + configMap: + FRONTEND_KC_CLIENTID: ches-showcase-frontend-4105 + FRONTEND_KC_REALM: standard + FRONTEND_KC_SERVERURL: https://test.loginproxy.gov.bc.ca/auth + # FRONTEND_DASHBOARDURL: https://ches-metabase.apps.silver.devops.gov.bc.ca/public/dashboard/6f388f95-dba7-4632-be4c-8855ee645f31 + SERVER_KC_PUBLICKEY: MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAiFdv9GA83uHuy8Eu9yiZHGGF9j6J8t7FkbcpaN81GDjwbjsIJ0OJO9dKRAx6BAtTC4ubJTBJMPvQER5ikOhIeBi4o25fg61jpgsU6oRZHkCXc9gX6mrjMjbsPaf3/bjjYxP5jicBDJQeD1oRa24+tiGggoQ7k6gDEN+cRYqqNpzC/GQbkUPk8YsgroncEgu8ChMh/3ERsLV2zorchMANUq76max16mHrhtWIQxrb/STpSt4JuSlUzzBV/dcXjJe5gywZHe0jAutFhNqjHzHdgyaC4RAd3eYQo+Kl/JOgy2AZrnx+CiPmvOJKe9tAW4k4H087ng8aVE40v4HW/FEbnwIDAQAB + SERVER_KC_REALM: standard + SERVER_KC_SERVERURL: https://test.loginproxy.gov.bc.ca/auth + # SERVER_LOGFILE: ./app.log + SERVER_LOGLEVEL: http + SERVER_PORT: "8080" + SC_CHES_ENDPOINT: https://ches-test.api.gov.bc.ca/api + SC_CS_TOKEN_ENDPOINT: https://test.loginproxy.gov.bc.ca/auth/realms/comsvcauth/protocol/openid-connect/token diff --git a/.github/workflows/charts-release.yaml b/.github/workflows/charts-release.yaml new file mode 100644 index 0000000..62919f9 --- /dev/null +++ b/.github/workflows/charts-release.yaml @@ -0,0 +1,27 @@ +name: Release Charts + +on: + push: + paths: + - 'charts/**' + branches: + - master + +jobs: + release: + runs-on: ubuntu-latest + steps: + - name: Checkout + uses: actions/checkout@v3 + with: + fetch-depth: 0 + + - name: Configure Git + run: | + git config user.name "$GITHUB_ACTOR" + git config user.email "$GITHUB_ACTOR@users.noreply.github.com" + + - name: Run chart-releaser + uses: helm/chart-releaser-action@v1.5.0 + env: + CR_TOKEN: "${{ secrets.GITHUB_TOKEN }}" diff --git a/.github/workflows/codeql-analysis.yaml b/.github/workflows/codeql-analysis.yaml new file mode 100644 index 0000000..1ea8655 --- /dev/null +++ b/.github/workflows/codeql-analysis.yaml @@ -0,0 +1,74 @@ +# For most projects, this workflow file will not need changing; you simply need +# to commit it to your repository. +# +# You may wish to alter this file to override the set of languages analyzed, +# or to provide custom queries or build logic. +# +# ******** NOTE ******** +# We have attempted to detect the languages in your repository. Please check +# the `language` matrix defined below to confirm you have the correct set of +# supported CodeQL languages. +# +--- +name: "CodeQL" + +on: + push: + branches: + - master + pull_request: + # The branches below must be a subset of the branches above + branches: + - master + schedule: + - cron: "38 6 * * 5" + +jobs: + analyze: + name: Analyze + runs-on: ubuntu-latest + permissions: + actions: read + contents: read + security-events: write + + strategy: + fail-fast: false + matrix: + language: + - javascript + # CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python', 'ruby' ] + # Learn more about CodeQL language support at https://git.io/codeql-language-support + + steps: + - name: Checkout repository + uses: actions/checkout@v3 + + # Initializes the CodeQL tools for scanning. + - name: Initialize CodeQL + uses: github/codeql-action/init@v2 + with: + languages: ${{ matrix.language }} + # If you wish to specify custom queries, you can do so here or in a config file. + # By default, queries listed here will override any specified in a config file. + # Prefix the list here with "+" to use these queries and those in the config file. + # queries: ./path/to/local/query, your-org/your-repo/queries@main + + # Autobuild attempts to build any compiled languages (C/C++, C#, or Java). + # If this step fails, then you should remove it and run the build manually (see below) + - name: Autobuild + uses: github/codeql-action/autobuild@v2 + + # ℹī¸ Command-line programs to run using the OS shell. + # 📚 https://git.io/JvXDl + + # ✏ī¸ If the Autobuild fails above, remove it and uncomment the following three lines + # and modify them (or add more) to build your code if your project + # uses a compiled language + + #- run: | + # make bootstrap + # make release + + - name: Perform CodeQL Analysis + uses: github/codeql-action/analyze@v2 diff --git a/.github/workflows/on-pr-closed.yaml b/.github/workflows/on-pr-closed.yaml new file mode 100644 index 0000000..8af073c --- /dev/null +++ b/.github/workflows/on-pr-closed.yaml @@ -0,0 +1,53 @@ +name: Pull Request Closed + +env: + ACRONYM: chess + APP_NAME: common-hosted-email-service-showcase + NAMESPACE_PREFIX: 10d873 + +on: + pull_request: + branches: + - master + types: + - closed + +concurrency: + group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }} + cancel-in-progress: true + +jobs: + remove-pr-dev: + name: Remove PR build from dev namespace + if: "! github.event.pull_request.head.repo.fork" + environment: + name: pr + url: https://${{ env.ACRONYM }}-dev-pr-${{ github.event.number }}.apps.silver.devops.gov.bc.ca + runs-on: ubuntu-latest + timeout-minutes: 12 + steps: + - name: Checkout + uses: actions/checkout@v3 + - name: Login to OpenShift Cluster + uses: redhat-actions/oc-login@v1 + with: + openshift_server_url: ${{ secrets.OPENSHIFT_SERVER }} + openshift_token: ${{ secrets.OPENSHIFT_TOKEN }} + insecure_skip_tls_verify: true + namespace: ${{ env.NAMESPACE_PREFIX }}-dev + - name: Remove PR Deployment + shell: bash + run: | + helm uninstall --namespace ${{ env.NAMESPACE_PREFIX }}-dev pr-${{ github.event.number }} --timeout 10m --wait + oc delete --namespace ${{ env.NAMESPACE_PREFIX }}-dev cm,secret --selector app.kubernetes.io/instance=pr-${{ github.event.number }} + - name: Remove Release Comment on PR + uses: marocchino/sticky-pull-request-comment@v2 + with: + header: release + delete: true + - name: Remove Github Deployment Environment + uses: strumwolf/delete-deployment-environment@v2 + with: + environment: pr + onlyRemoveDeployments: true + token: ${{ secrets.GITHUB_TOKEN }} diff --git a/.github/workflows/on-pr-opened.yaml b/.github/workflows/on-pr-opened.yaml new file mode 100644 index 0000000..c79745e --- /dev/null +++ b/.github/workflows/on-pr-opened.yaml @@ -0,0 +1,66 @@ +name: Pull Request Opened + +env: + ACRONYM: chess + APP_NAME: common-hosted-email-service-showcase + NAMESPACE_PREFIX: 10d873 + +on: + pull_request: + branches: + - master + types: + - opened + - reopened + - synchronize + +concurrency: + group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }} + cancel-in-progress: true + +jobs: + build: + name: Build & Push + if: "! github.event.pull_request.head.repo.fork" + runs-on: ubuntu-latest + timeout-minutes: 10 + steps: + - name: Checkout + uses: actions/checkout@v3 + - name: Build & Push + uses: ./.github/actions/build-push-container + with: + context: . + image_name: ${{ env.APP_NAME }} + github_username: ${{ github.repository_owner }} + github_token: ${{ secrets.GITHUB_TOKEN }} + + deploy-pr-dev: + name: Deploy Pull Request to Dev + environment: + name: pr + url: https://${{ env.ACRONYM }}-dev-pr-${{ github.event.number }}.apps.silver.devops.gov.bc.ca + runs-on: ubuntu-latest + needs: build + timeout-minutes: 12 + steps: + - name: Checkout + uses: actions/checkout@v3 + - name: Deploy to Dev + uses: ./.github/actions/deploy-to-environment + with: + app_name: ${{ env.APP_NAME }} + acronym: ${{ env.ACRONYM }} + environment: pr + job_name: pr-${{ github.event.number }} + namespace_prefix: ${{ env.NAMESPACE_PREFIX }} + namespace_environment: dev + openshift_server: ${{ secrets.OPENSHIFT_SERVER }} + openshift_token: ${{ secrets.OPENSHIFT_TOKEN }} + - name: Release Comment on PR + uses: marocchino/sticky-pull-request-comment@v2 + if: success() + with: + header: release + message: | + Release ${{ github.sha }} deployed at diff --git a/charts/chess/.helmignore b/charts/chess/.helmignore new file mode 100644 index 0000000..0e8a0eb --- /dev/null +++ b/charts/chess/.helmignore @@ -0,0 +1,23 @@ +# Patterns to ignore when building packages. +# This supports shell glob matching, relative path matching, and +# negation (prefixed with !). Only one pattern per line. +.DS_Store +# Common VCS dirs +.git/ +.gitignore +.bzr/ +.bzrignore +.hg/ +.hgignore +.svn/ +# Common backup files +*.swp +*.bak +*.tmp +*.orig +*~ +# Various IDEs +.project +.idea/ +*.tmproj +.vscode/ diff --git a/charts/chess/Chart.yaml b/charts/chess/Chart.yaml new file mode 100644 index 0000000..4172178 --- /dev/null +++ b/charts/chess/Chart.yaml @@ -0,0 +1,37 @@ +apiVersion: v2 +name: common-hosted-email-service-showcase +# This is the chart version. This version number should be incremented each time you make changes +# to the chart and its templates, including the app version. +# Versions are expected to follow Semantic Versioning (https://semver.org/) +version: 0.0.1 +kubeVersion: ">= 1.13.0" +description: A Showcase application to demonstrate features of the Common Document Generation Service +# A chart can be either an 'application' or a 'library' chart. +# Application charts are a collection of templates that can be packaged into versioned archives +# to be deployed. +# Library charts provide useful utilities or functions for the chart developer. They're included as +# a dependency of application charts to inject those utilities and functions into the rendering +# pipeline. Library charts do not define any templates and therefore cannot be deployed. +type: application +keywords: + - nodejs + - javascript + - docker + - microservice + - email + - vue +home: https://bcgov.github.io/common-hosted-email-service-showcase +sources: + - https://github.com/bcgov/common-hosted-email-service-showcase +dependencies: [] +maintainers: + - name: NR Common Service Showcase Team + email: NR.CommonServiceShowcase@gov.bc.ca + url: https://bcgov.github.io/common-service-showcase/team.html +# This is the version number of the application being deployed. This version number should be +# incremented each time you make changes to the application. Versions are not expected to +# follow Semantic Versioning. They should reflect the version the application is using. +# It is recommended to use it with quotes. +appVersion: "1.0.0" +deprecated: false +annotations: {} diff --git a/charts/chess/README.md b/charts/chess/README.md new file mode 100644 index 0000000..880628d --- /dev/null +++ b/charts/chess/README.md @@ -0,0 +1,76 @@ +# common-hosted-email-service-showcase + +![Version: 0.0.1](https://img.shields.io/badge/Version-0.0.1-informational?style=flat-square) ![Type: application](https://img.shields.io/badge/Type-application-informational?style=flat-square) ![AppVersion: 2.0.0](https://img.shields.io/badge/AppVersion-2.0.0-informational?style=flat-square) + +A Showcase application to demonstrate features of the Common Document Generation Service + +**Homepage:** + +## Maintainers + +| Name | Email | Url | +| ---- | ------ | --- | +| NR Common Service Showcase Team | | | + +## Source Code + +* + +## Requirements + +Kubernetes: `>= 1.13.0` + +## Values + +| Key | Type | Default | Description | +|-----|------|---------|-------------| +| autoscaling.behavior.scaleDown.policies[0].periodSeconds | int | `120` | | +| autoscaling.behavior.scaleDown.policies[0].type | string | `"Pods"` | | +| autoscaling.behavior.scaleDown.policies[0].value | int | `1` | | +| autoscaling.behavior.scaleDown.selectPolicy | string | `"Max"` | | +| autoscaling.behavior.scaleDown.stabilizationWindowSeconds | int | `120` | | +| autoscaling.behavior.scaleUp.policies[0].periodSeconds | int | `30` | | +| autoscaling.behavior.scaleUp.policies[0].type | string | `"Pods"` | | +| autoscaling.behavior.scaleUp.policies[0].value | int | `2` | | +| autoscaling.behavior.scaleUp.selectPolicy | string | `"Max"` | | +| autoscaling.behavior.scaleUp.stabilizationWindowSeconds | int | `0` | | +| autoscaling.enabled | bool | `false` | | +| autoscaling.maxReplicas | int | `16` | | +| autoscaling.minReplicas | int | `2` | | +| autoscaling.targetCPUUtilizationPercentage | int | `80` | | +| config.configMap.FRONTEND_APIPATH | string | `"api/v2"` | | +| config.configMap.SERVER_APIPATH | string | `"/api/v2"` | | +| config.configMap.SERVER_BODYLIMIT | string | `"30mb"` | | +| config.enabled | bool | `false` | | +| config.releaseScoped | bool | `false` | | +| failurePolicy | string | `"Retry"` | | +| fullnameOverride | string | `nil` | | +| image.pullPolicy | string | `"IfNotPresent"` | | +| image.repository | string | `"ghcr.io/bcgov"` | | +| image.tag | string | `nil` | | +| imagePullSecrets | list | `[]` | | +| nameOverride | string | `nil` | | +| networkPolicy.enabled | bool | `true` | | +| podAnnotations | object | `{}` | | +| podSecurityContext | object | `{}` | | +| replicaCount | int | `2` | | +| resources.limits.cpu | string | `"200m"` | | +| resources.limits.memory | string | `"256Mi"` | | +| resources.requests.cpu | string | `"10m"` | | +| resources.requests.memory | string | `"128Mi"` | | +| route.annotations | object | `{}` | | +| route.enabled | bool | `true` | | +| route.host | string | `"chart-example.local"` | | +| route.tls.insecureEdgeTerminationPolicy | string | `"Redirect"` | | +| route.tls.termination | string | `"edge"` | | +| route.wildcardPolicy | string | `"None"` | | +| securityContext | object | `{}` | | +| service.port | int | `8080` | | +| service.portName | string | `"http"` | | +| service.type | string | `"ClusterIP"` | | +| serviceAccount.annotations | object | `{}` | | +| serviceAccount.enabled | bool | `false` | | +| serviceAccount.name | string | `nil` | | + +---------------------------------------------- +Autogenerated from chart metadata using [helm-docs v1.11.0](https://github.com/norwoodj/helm-docs/releases/v1.11.0) diff --git a/charts/chess/templates/NOTES.txt b/charts/chess/templates/NOTES.txt new file mode 100644 index 0000000..41dac03 --- /dev/null +++ b/charts/chess/templates/NOTES.txt @@ -0,0 +1,24 @@ +{{- $configMapName := printf "%s-%s" (include "chess.configname" .) "config" }} +{{- $configMap := (lookup "v1" "ConfigMap" .Release.Namespace $configMapName ) }} +Get the application URL by running these commands: +{{- if .Values.route.enabled }} + http{{ if $.Values.route.tls }}s{{ end }}://{{ .Values.route.host }}{{ .Values.route.path }} +{{- else if contains "NodePort" .Values.service.type }} + export NODE_PORT=$(kubectl get --namespace {{ .Release.Namespace }} -o jsonpath="{.spec.ports[0].nodePort}" services {{ include "chess.fullname" . }}) + export NODE_IP=$(kubectl get nodes --namespace {{ .Release.Namespace }} -o jsonpath="{.items[0].status.addresses[0].address}") + echo http://$NODE_IP:$NODE_PORT +{{- else if contains "LoadBalancer" .Values.service.type }} + NOTE: It may take a few minutes for the LoadBalancer IP to be available. + You can watch the status of by running 'kubectl get --namespace {{ .Release.Namespace }} svc -w {{ include "chess.fullname" . }}' + export SERVICE_IP=$(kubectl get svc --namespace {{ .Release.Namespace }} {{ include "chess.fullname" . }} --template "{{"{{ range (index .status.loadBalancer.ingress 0) }}{{.}}{{ end }}"}}") + echo http://$SERVICE_IP:{{ .Values.service.port }} +{{- else if contains "ClusterIP" .Values.service.type }} + export POD_NAME=$(kubectl get pods --namespace {{ .Release.Namespace }} -l "app.kubernetes.io/name={{ include "chess.name" . }},app.kubernetes.io/instance={{ .Release.Name }}" -o jsonpath="{.items[0].metadata.name}") + export CONTAINER_PORT=$(kubectl get pod --namespace {{ .Release.Namespace }} $POD_NAME -o jsonpath="{.spec.containers[0].ports[0].containerPort}") + echo "Visit http://127.0.0.1:8080 to use your application" + kubectl --namespace {{ .Release.Namespace }} port-forward $POD_NAME 8080:$CONTAINER_PORT +{{- end }} +{{- if not $configMap }} + +Make sure that ConfigMap "{{ $configMapName }}" is defined in the namespace; the deployment will fail to run without it! +{{- end }} diff --git a/charts/chess/templates/_helpers.tpl b/charts/chess/templates/_helpers.tpl new file mode 100644 index 0000000..fc7d49f --- /dev/null +++ b/charts/chess/templates/_helpers.tpl @@ -0,0 +1,77 @@ +{{/* +Expand the name of the chart. +*/}} +{{- define "chess.name" -}} +{{- default .Chart.Name .Values.nameOverride | trunc 63 | trimSuffix "-" }} +{{- end }} + +{{/* +Create a default fully qualified app name. +We truncate at 63 chars because some Kubernetes name fields are limited to this (by the DNS naming spec). +If release name contains chart name it will be used as a full name. +*/}} +{{- define "chess.fullname" -}} +{{- if .Values.fullnameOverride }} +{{- .Values.fullnameOverride | trunc 63 | trimSuffix "-" }} +{{- else }} +{{- $name := default .Chart.Name .Values.nameOverride }} +{{- if contains $name .Release.Name }} +{{- .Release.Name | trunc 63 | trimSuffix "-" }} +{{- else }} +{{- printf "%s-%s" $name .Release.Name | trunc 63 | trimSuffix "-" }} +{{- end }} +{{- end }} +{{- end }} + +{{/* +Define the config pattern of the chart based on options. +*/}} +{{- define "chess.configname" -}} +{{- if .Values.config.releaseScoped }} +{{- include "chess.fullname" . }} +{{- else }} +{{- include "chess.name" . }} +{{- end }} +{{- end }} + +{{/* +Create chart name and version as used by the chart label. +*/}} +{{- define "chess.chart" -}} +{{- printf "%s-%s" .Chart.Name .Chart.Version | replace "+" "_" | trunc 63 | trimSuffix "-" }} +{{- end }} + +{{/* +Common labels +*/}} +{{- define "chess.labels" -}} +helm.sh/chart: {{ include "chess.chart" . }} +app: {{ include "chess.fullname" . }} +{{ include "chess.selectorLabels" . }} +{{- if .Chart.AppVersion }} +app.kubernetes.io/version: {{ .Chart.AppVersion | quote }} +{{- end }} +app.kubernetes.io/component: backend +app.kubernetes.io/managed-by: {{ .Release.Service }} +app.kubernetes.io/part-of: {{ .Release.Name }} +app.openshift.io/runtime: nodejs +{{- end }} + +{{/* +Selector labels +*/}} +{{- define "chess.selectorLabels" -}} +app.kubernetes.io/name: {{ include "chess.name" . }} +app.kubernetes.io/instance: {{ .Release.Name }} +{{- end }} + +{{/* +Create the name of the service account to use +*/}} +{{- define "chess.serviceAccountName" -}} +{{- if .Values.serviceAccount.create }} +{{- default (include "chess.fullname" .) .Values.serviceAccount.name }} +{{- else }} +{{- default "default" .Values.serviceAccount.name }} +{{- end }} +{{- end }} diff --git a/charts/chess/templates/configmap.yaml b/charts/chess/templates/configmap.yaml new file mode 100644 index 0000000..4b17361 --- /dev/null +++ b/charts/chess/templates/configmap.yaml @@ -0,0 +1,12 @@ +{{- if .Values.config.enabled }} +--- +apiVersion: v1 +kind: ConfigMap +metadata: + name: {{ include "chess.configname" . }}-config + {{- if not .Values.config.releaseScoped }} + annotations: + "helm.sh/resource-policy": keep + {{- end }} +data: {{ toYaml .Values.config.configMap | nindent 2 }} +{{- end }} diff --git a/charts/chess/templates/deploymentconfig.yaml b/charts/chess/templates/deploymentconfig.yaml new file mode 100644 index 0000000..227a96c --- /dev/null +++ b/charts/chess/templates/deploymentconfig.yaml @@ -0,0 +1,90 @@ +--- +apiVersion: apps.openshift.io/v1 +kind: DeploymentConfig +metadata: + name: {{ include "chess.fullname" . }} + labels: + {{- include "chess.labels" . | nindent 4 }} +spec: + replicas: {{ .Values.replicaCount }} + revisionHistoryLimit: 10 + selector: + {{- include "chess.selectorLabels" . | nindent 4 }} + strategy: + resources: + {{- toYaml .Values.resources | nindent 6 }} + rollingParams: + timeoutSeconds: 600 + type: Rolling + template: + metadata: + labels: {{ include "chess.selectorLabels" . | nindent 8 }} + spec: + {{- with .Values.imagePullSecrets }} + imagePullSecrets: {{ toYaml . | nindent 8 }} + {{- end }} + {{- if .Values.serviceAccount.create }} + serviceAccountName: {{ include "chess.serviceAccountName" . }} + {{- end }} + {{- with .Values.podSecurityContext }} + securityContext: {{ toYaml . | nindent 8 }} + {{- end }} + containers: + - name: app + {{- with .Values.securityContext }} + securityContext: {{ toYaml . | nindent 12 }} + {{- end }} + image: "{{ .Values.image.repository }}/{{ .Chart.Name }}:{{ .Values.image.tag | default .Chart.AppVersion }}" + imagePullPolicy: {{ .Values.image.pullPolicy }} + ports: + - containerPort: {{ .Values.service.port }} + protocol: TCP + livenessProbe: + failureThreshold: 3 + httpGet: + path: {{ .Values.route.path }} + port: {{ .Values.service.port }} + scheme: HTTP + initialDelaySeconds: 10 + timeoutSeconds: 1 + readinessProbe: + failureThreshold: 3 + httpGet: + path: {{ .Values.route.path }} + port: {{ .Values.service.port }} + scheme: HTTP + initialDelaySeconds: 10 + timeoutSeconds: 1 + resources: {{ toYaml .Values.resources | nindent 12 }} + env: + - name: NODE_ENV + value: production + # secrets: + - name: SERVER_KC_CLIENTID + valueFrom: + secretKeyRef: + key: username + name: chess-keycloak-secret + - name: SERVER_KC_CLIENTSECRET + valueFrom: + secretKeyRef: + key: password + name: chess-keycloak-secret + - name: SC_CHES_USERNAME + valueFrom: + secretKeyRef: + key: username + name: chess-sc-ches-secret + - name: SC_CHES_PASSWORD + valueFrom: + secretKeyRef: + key: password + name: chess-sc-ches-secret + envFrom: + - configMapRef: + name: {{ include "chess.configname" . }}-config + restartPolicy: Always + terminationGracePeriodSeconds: 30 + test: false + triggers: + - type: ConfigChange diff --git a/charts/chess/templates/hpa.yaml b/charts/chess/templates/hpa.yaml new file mode 100644 index 0000000..2d3f696 --- /dev/null +++ b/charts/chess/templates/hpa.yaml @@ -0,0 +1,37 @@ +{{- if .Values.autoscaling.enabled }} +--- +apiVersion: autoscaling/v2 +kind: HorizontalPodAutoscaler +metadata: + name: {{ include "chess.fullname" . }} + labels: + {{- include "chess.labels" . | nindent 4 }} +spec: + scaleTargetRef: + apiVersion: apps.openshift.io/v1 + kind: DeploymentConfig + name: {{ include "chess.fullname" . }} + minReplicas: {{ .Values.autoscaling.minReplicas }} + maxReplicas: {{ .Values.autoscaling.maxReplicas }} + metrics: + {{- if .Values.autoscaling.targetCPUUtilizationPercentage }} + - type: Resource + resource: + name: cpu + target: + type: Utilization + averageUtilization: {{ .Values.autoscaling.targetCPUUtilizationPercentage }} + {{- end }} + {{- if .Values.autoscaling.targetMemoryUtilizationPercentage }} + - type: Resource + resource: + name: memory + target: + type: Utilization + averageUtilization: {{ .Values.autoscaling.targetMemoryUtilizationPercentage }} + {{- end }} + {{- with .Values.autoscaling.behavior }} + behavior: + {{- toYaml . | nindent 4 }} + {{- end }} +{{- end }} diff --git a/charts/chess/templates/networkpolicy.yaml b/charts/chess/templates/networkpolicy.yaml new file mode 100644 index 0000000..292faf2 --- /dev/null +++ b/charts/chess/templates/networkpolicy.yaml @@ -0,0 +1,22 @@ +{{- if .Values.networkPolicy.enabled }} +--- +apiVersion: networking.k8s.io/v1 +kind: NetworkPolicy +metadata: + name: allow-openshift-ingress-to-{{ include "chess.fullname" . }}-app + labels: + {{- include "chess.labels" . | nindent 4 }} +spec: + ingress: + - from: + - namespaceSelector: + matchLabels: + network.openshift.io/policy-group: ingress + - podSelector: + matchLabels: {{ include "chess.selectorLabels" . | nindent 14 }} + ports: + - port: {{ default "8080" .Values.config.configMap.SERVER_PORT | atoi }} + protocol: TCP + podSelector: + matchLabels: {{- include "chess.selectorLabels" . | nindent 6 }} +{{- end }} diff --git a/charts/chess/templates/route.yaml b/charts/chess/templates/route.yaml new file mode 100644 index 0000000..83f69fa --- /dev/null +++ b/charts/chess/templates/route.yaml @@ -0,0 +1,28 @@ +{{- if .Values.route.enabled -}} +--- +apiVersion: route.openshift.io/v1 +kind: Route +metadata: + name: {{ include "chess.fullname" . }} + labels: + {{- include "chess.labels" . | nindent 4 }} + {{- with .Values.route.annotations }} + annotations: + {{- toYaml . | nindent 4 }} + {{- end }} +spec: + host: {{ .Values.route.host | quote }} + {{- if .Values.route.path }} + path: {{ .Values.route.path }} + {{- end }} + port: + targetPort: {{ .Values.service.portName }} + tls: + insecureEdgeTerminationPolicy: {{ .Values.route.tls.insecureEdgeTerminationPolicy }} + termination: {{ .Values.route.tls.termination }} + to: + kind: Service + name: {{ include "chess.fullname" . }} + weight: 100 + wildcardPolicy: {{ .Values.route.wildcardPolicy }} +{{- end }} diff --git a/charts/chess/templates/service.yaml b/charts/chess/templates/service.yaml new file mode 100644 index 0000000..99d7342 --- /dev/null +++ b/charts/chess/templates/service.yaml @@ -0,0 +1,16 @@ +--- +apiVersion: v1 +kind: Service +metadata: + name: {{ include "chess.fullname" . }} + labels: + {{- include "chess.labels" . | nindent 4 }} +spec: + type: {{ .Values.service.type }} + ports: + - name: {{ .Values.service.portName }} + port: {{ .Values.service.port }} + protocol: TCP + targetPort: {{ .Values.service.port }} + selector: + {{- include "chess.selectorLabels" . | nindent 4 }} diff --git a/charts/chess/templates/serviceaccount.yaml b/charts/chess/templates/serviceaccount.yaml new file mode 100644 index 0000000..0d47d5e --- /dev/null +++ b/charts/chess/templates/serviceaccount.yaml @@ -0,0 +1,13 @@ +{{- if .Values.serviceAccount.enabled -}} +--- +apiVersion: v1 +kind: ServiceAccount +metadata: + name: {{ include "chess.serviceAccountName" . }} + labels: + {{- include "chess.labels" . | nindent 4 }} + {{- with .Values.serviceAccount.annotations }} + annotations: + {{- toYaml . | nindent 4 }} + {{- end }} +{{- end }} diff --git a/charts/chess/values.yaml b/charts/chess/values.yaml new file mode 100644 index 0000000..844e83f --- /dev/null +++ b/charts/chess/values.yaml @@ -0,0 +1,118 @@ +# Default values for chess. +# This is a YAML-formatted file. +# Declare variables to be passed into your templates. + +replicaCount: 2 + +image: + repository: ghcr.io/bcgov + pullPolicy: IfNotPresent + # Overrides the image tag whose default is the chart appVersion. + tag: ~ + +imagePullSecrets: [] +nameOverride: ~ +fullnameOverride: ~ + +# DeploymentConfig pre-hook failure behavior +failurePolicy: Retry + +podAnnotations: {} + +podSecurityContext: {} + # fsGroup: 2000 + +securityContext: {} + # capabilities: + # drop: + # - ALL + # readOnlyRootFilesystem: true + # runAsNonRoot: true + # runAsUser: 1000 + +autoscaling: + enabled: false + + # Directly modify scaling behavior and frequency + behavior: + scaleDown: + stabilizationWindowSeconds: 120 + selectPolicy: Max + policies: + - type: Pods + value: 1 + periodSeconds: 120 + scaleUp: + stabilizationWindowSeconds: 0 + selectPolicy: Max + policies: + - type: Pods + value: 2 + periodSeconds: 30 + minReplicas: 2 + maxReplicas: 16 + targetCPUUtilizationPercentage: 80 + # targetMemoryUtilizationPercentage: 80 + +serviceAccount: + # Specifies whether a service account should be created + enabled: false + # Annotations to add to the service account + annotations: {} + # The name of the service account to use. + # If not set and create is true, a name is generated using the fullname template + name: ~ + +networkPolicy: + enabled: true + +service: + type: ClusterIP + port: 8080 + portName: http + +route: + enabled: true + annotations: {} + # kubernetes.io/ingress.class: nginx + # kubernetes.io/tls-acme: "true" + host: chart-example.local + path: / + tls: + insecureEdgeTerminationPolicy: Redirect + termination: edge + wildcardPolicy: None + +resources: + # We usually recommend not to specify default resources and to leave this as a conscious + # choice for the user. This also increases chances charts run on environments with little + # resources, such as Minikube. If you do want to specify resources, uncomment the following + # lines, adjust them as necessary, and remove the curly braces after 'resources:'. + limits: + cpu: 200m + memory: 256Mi + requests: + cpu: 10m + memory: 128Mi + +config: + # Set to true if you want to let Helm manage and overwrite your configmaps. + enabled: false + + # This should be set to true if and only if you require configmaps and secrets to be release + # scoped. In the event you want all instances in the same namespace to share a similar + # configuration, this should be set to false + releaseScoped: false + + # These values will be wholesale added to the configmap as is; refer to the chess + # documentation for what each of these values mean and whether you need them defined. + # Ensure that all values are represented explicitly as strings, as non-string values will + # not translate over as expected into container environment variables. + # For configuration keys named `*_ENABLED`, either leave them commented/undefined, or set them + # to string value "true". + configMap: + FRONTEND_APIPATH: "api/v1" + FRONTEND_BASEPATH: "/app" + SERVER_APIPATH: "/api/v1" + SERVER_BASEPATH: "/app" + SERVER_BODYLIMIT: "30mb"