Skip to content

Commit 7993122

Browse files
ElderMattElderMatt
and
ElderMatt
authored
feat: added linode as a deploy option (#1622)
Co-authored-by: ElderMatt <“[email protected]”>
1 parent 7cbb16c commit 7993122

File tree

1 file changed

+186
-0
lines changed

1 file changed

+186
-0
lines changed

.github/workflows/integration.yml

+186
Original file line numberDiff line numberDiff line change
@@ -49,6 +49,7 @@ on:
4949
type: choice
5050
options:
5151
- scaleway
52+
- linode
5253
- digitalocean
5354
default: 'scaleway'
5455
kubernetes_versions:
@@ -200,6 +201,30 @@ jobs:
200201
echo $versions
201202
echo "versions=$versions" >> $GITHUB_OUTPUT
202203
204+
preprocess-linode-input:
205+
needs: preprocess-input
206+
if: ${{ inputs.cloud_provider == 'linode' }}
207+
name: Preprocess input variables for linode
208+
runs-on: ubuntu-latest
209+
outputs:
210+
kubernetes_versions: ${{ steps.k8s-versions.outputs.versions }}
211+
steps:
212+
- name: Install the Linode CLI
213+
uses: linode/action-linode-cli@v1
214+
with:
215+
token: ${{ secrets.LINODE_TOKEN }}
216+
- id: k8s-versions
217+
name: Process k8s version input
218+
run: |
219+
if [ -z '${{ inputs.kubernetes_versions }}' ]; then
220+
echo "Kubernetes versions not specified, determine Linode supported versions"
221+
versions=`linode-cli lke versions-list --json | jq -ce '.[] | .id'`
222+
else
223+
versions='${{ inputs.kubernetes_versions }}'
224+
fi
225+
echo $versions
226+
echo "versions=$versions" >> $GITHUB_OUTPUT
227+
203228
run-integration-test-scaleway:
204229
if: ${{ inputs.cloud_provider == 'scaleway' }}
205230
name: Run integration test on scaleway cluster
@@ -472,3 +497,164 @@ jobs:
472497
SLACK_ICON: https://github.com/redkubes.png?size=48
473498
SLACK_TITLE: Scheduled integration tests
474499
SLACK_USERNAME: RedKubesBot
500+
501+
run-integration-test-linode:
502+
if: ${{ inputs.cloud_provider == 'linode' }}
503+
name: Run integration test on linode cluster
504+
needs: preprocess-linode-input
505+
runs-on: ubuntu-latest
506+
strategy:
507+
fail-fast: false
508+
matrix:
509+
kubernetes_versions: ${{ fromJSON(needs.preprocess-linode-input.outputs.kubernetes_versions) }}
510+
max-parallel: 5
511+
steps:
512+
- name: Install the Linode CLI
513+
uses: linode/action-linode-cli@v1
514+
with:
515+
token: ${{ secrets.LINODE_TOKEN }}
516+
- name: Set k8s cluster name
517+
run: |
518+
echo "LINODE_CLUSTER_NAME=$(echo ${{ github.actor }} | tr '[:upper:]' '[:lower:]')-$(TZ='GMT-2' date +'%m-%d-%H-%M')" >> $GITHUB_ENV
519+
# Cluster name must be no longer than 63 characters
520+
- name: Determine exact k8s version
521+
run: |
522+
echo LINODE_K8S_VERSION=$(linode-cli lke versions-list --json | jq -ce --arg version "${{ matrix.kubernetes_versions }}" '.[] | select(.id | tostring | startswith($version)) | .id') >> $GITHUB_ENV
523+
- name: Create k8s cluster for testing
524+
run: |
525+
linode-cli lke cluster-create \
526+
--label ${{ env.LINODE_CLUSTER_NAME }} \
527+
--region nl-ams \
528+
--k8s_version ${{ env.LINODE_K8S_VERSION }} \
529+
--control_plane.high_availability true \
530+
--node_pools.type g6-dedicated-8 --node_pools.count 3 \
531+
--node_pools.autoscaler.enabled true \
532+
--node_pools.autoscaler.max 3 \
533+
--node_pools.autoscaler.min 3 \
534+
--tags testing \
535+
--no-defaults
536+
- name: Retrieve cluster id
537+
run: echo "LINODE_CLUSTER_ID=$(linode-cli lke clusters-list --json | jq -ce '.[] | select(.label | startswith("${{ env.LINODE_CLUSTER_NAME }}")) | .id')" >> $GITHUB_ENV
538+
- name: Wait for cluster to be ready
539+
run: |
540+
echo "Waiting for the cluster to be active..."
541+
542+
while :; do
543+
rawOutput=$(linode-cli lke pools-list ${{ env.LINODE_CLUSTER_ID }} --json)
544+
545+
allReady=$(echo "$rawOutput" | jq -r 'map(.nodes | .status == "ready") | all')
546+
echo "All nodes ready: $allReady"
547+
548+
if [ "$allReady" == "true" ]; then
549+
echo "Cluster is ready"
550+
break
551+
fi
552+
553+
sleep 30
554+
done
555+
- name: Save kubectl config with auth token and Get kubectl environment and create docker secret
556+
run: |
557+
# Get the kubeconfig from linode-cli
558+
kubeconfig=$(linode-cli lke kubeconfig-view ${{ env.LINODE_CLUSTER_ID }} --text | sed 1d | base64 --decode)
559+
560+
# Save the kubeconfig to a file
561+
kubeconfigDir="$HOME/.kube"
562+
kubeconfigPath="$HOME/.kube/config"
563+
mkdir -p "$kubeconfigDir" # Create the directory if it doesn't exist
564+
echo "$kubeconfig" > "$kubeconfigPath"
565+
echo "Kubeconfig saved to $kubeconfigPath"
566+
567+
# Set the kubectl context to use the new kubeconfig
568+
export KUBECONFIG="$kubeconfigPath"
569+
contextName=$(kubectl config get-contexts -o name | head -n 1)
570+
kubectl config use-context "$contextName"
571+
echo "Kubectl context set to linode"
572+
echo LINODE_CLUSTER_CONTEXT=`kubectl config current-context` >> $GITHUB_ENV
573+
- name: Create image pull secret on test cluster
574+
run: |
575+
kubectl create secret docker-registry reg-otomi-github \
576+
--docker-server=${{ env.CACHE_REGISTRY }} \
577+
--docker-username=${{ env.GIT_USER }} \
578+
--docker-password='${{ secrets.NPM_TOKEN }}'
579+
- name: Checkout
580+
uses: actions/checkout@v4
581+
- name: Prepare Otomi chart
582+
if: ${{ inputs.install_profile != 'no-otomi' }}
583+
run: |
584+
ref=${{ github.event.pull_request.head.ref || github.ref }}
585+
tag=${ref##*/}
586+
sed --in-place "s/APP_VERSION_PLACEHOLDER/$tag/g" chart/otomi/Chart.yaml
587+
sed --in-place "s/CONTEXT_PLACEHOLDER/${{ env.LINODE_CLUSTER_CONTEXT }}/g" tests/integration/${{ inputs.install_profile }}.yaml
588+
sed --in-place "s/OTOMI_VERSION_PLACEHOLDER/${GITHUB_REF##*/}/g" tests/integration/${{ inputs.install_profile }}.yaml
589+
touch values-container-registry.yaml
590+
591+
# If a pipeline installs Otomi from the semver tag then pull container image from DockerHub
592+
[[ ${GITHUB_REF##*/} =~ ^v[0-9].+$ ]] && exit 0
593+
594+
# Pull image from cache registry
595+
cat << EOF > values-container-registry.yaml
596+
imageName: "${{ env.CACHE_REGISTRY }}/${{ env.CACHE_REPO }}"
597+
imagePullSecretNames:
598+
- reg-otomi-github
599+
EOF
600+
- name: Otomi install
601+
if: ${{ inputs.install_profile != 'no-otomi' }}
602+
env:
603+
AZ_DNS: ${{ secrets.AZ_DNS }}
604+
AZ_KMS: ${{ secrets.AZ_KMS }}
605+
AZ_OIDC: ${{ secrets.AZ_OIDC }}
606+
LETSENCRYPT_STAGING: ${{ secrets.LETSENCRYPT_STAGING }}
607+
LETSENCRYPT_PRODUCTION: ${{ secrets.LETSENCRYPT_PRODUCTION }}
608+
OTOMI_LICENSE: ${{ secrets.OTOMI_LICENSE }}
609+
run: |
610+
domainSuffix=''
611+
touch values.yaml
612+
[[ '${{ inputs.license }}' == 'yes' ]] && echo "$OTOMI_LICENSE" >> values.yaml
613+
[[ '${{ inputs.dns }}' == 'az_dns' ]] && echo "$AZ_DNS" >> values.yaml && domainSuffix='--set cluster.domainSuffix=tst-${{ github.run_id }}.aks.redkubes.net'
614+
[[ '${{ inputs.kms }}' == 'az_kms' ]] && echo "$AZ_KMS" >> values.yaml
615+
[[ '${{ inputs.oidc }}' == 'az_oidc' ]] && echo "$AZ_OIDC" >> values.yaml
616+
[[ '${{ inputs.certificate }}' == 'letsencrypt_staging' ]] && echo "$LETSENCRYPT_STAGING" >> values.yaml
617+
[[ '${{ inputs.certificate }}' == 'letsencrypt_production' ]] && echo "$LETSENCRYPT_PRODUCTION" >> values.yaml
618+
619+
install_args="--wait --wait-for-jobs --timeout 90m0s otomi chart/otomi \
620+
--values tests/integration/${{ inputs.install_profile }}.yaml \
621+
--values values-container-registry.yaml
622+
--values values.yaml \
623+
--set cluster.provider=${{ inputs.cloud_provider }}
624+
$domainSuffix"
625+
626+
[[ '${{ inputs.generate_password }}' == 'no' ]] && install_args="$install_args --set otomi.adminPassword=welcomeotomi"
627+
628+
helm install $install_args
629+
630+
- name: Gather k8s events on failure
631+
if: failure()
632+
run: |
633+
kubectl get events --sort-by='.lastTimestamp' -A
634+
- name: Gather k8s pods on failure
635+
if: failure()
636+
run: |
637+
kubectl get pods -A -o wide
638+
- name: Gather otomi logs on failure
639+
if: failure()
640+
run: |
641+
kubectl logs jobs/otomi --tail 150
642+
- name: Gather otomi-e2e logs on failure
643+
if: failure()
644+
run: |
645+
kubectl logs -n maintenance -l app.kubernetes.io/instance=job-e2e --tail 15000
646+
- name: Remove the test cluster
647+
if: always()
648+
run: |
649+
[[ "${{ inputs.cluster_persistence }}" == "preserve" ]] && echo "The cluster ${{ env.LINODE_CLUSTER_NAME }} will NOT be destroyed!!" && exit 0
650+
linode-cli lke cluster-delete ${{ env.LINODE_CLUSTER_ID }}
651+
- name: Slack Notification
652+
if: always()
653+
uses: rtCamp/action-slack-notify@v2
654+
env:
655+
SLACK_WEBHOOK: ${{ secrets.SLACK_WEBHOOK }}
656+
SLACK_CHANNEL: github-ci
657+
SLACK_COLOR: ${{ job.status }}
658+
SLACK_ICON: https://github.com/redkubes.png?size=48
659+
SLACK_TITLE: Scheduled integration tests
660+
SLACK_USERNAME: RedKubesBot

0 commit comments

Comments
 (0)