diff --git a/.dockerignore b/.dockerignore index a0da2d846..b82966939 100644 --- a/.dockerignore +++ b/.dockerignore @@ -1,4 +1,13 @@ +.github +.git +.idea/ +.vscode/ deploy/ +cicd/ artifacts/ -.github -.git \ No newline at end of file +*.md +*.sh +.dockerignore +.gitignore +**/Dockerfile +**/docker-compose.yaml diff --git a/.github/workflows/build.yaml b/.github/workflows/build.yaml index 1f6535f68..5bcd4c2df 100644 --- a/.github/workflows/build.yaml +++ b/.github/workflows/build.yaml @@ -1,110 +1,25 @@ -name: Build -on: +name: Build Service +on: workflow_call: inputs: - image: - required: true - type: string path: + description: 'Path of the service' required: true type: string jobs: build: - name: Build + name: Build ${{ inputs.path }} runs-on: ubuntu-latest steps: - - - name: Checkout - uses: actions/checkout@master - - - uses: actions/setup-go@v3 - name: go-cache - with: - go-version: '1.21' - check-latest: false - cache: true - - - name: Build - env: - GOOS: linux - CGO_ENABLED: 0 - run: go build -v -o app "${{ inputs.path }}" - - - name: Build Release - if: | - github.event_name == 'push' && ( - startsWith(github.event.ref, 'refs/tags/') - || endsWith(github.event.ref, '/master') - ) - run: docker build -t hobbyfarm/"${{ inputs.image }}":${GIT_COMMIT_SHORT_HASH:-dev} -f cicd/Dockerfile . - - - name: Compute Docker Tag - if: | - github.event_name == 'push' && ( - startsWith(github.event.ref, 'refs/tags/') - || endsWith(github.event.ref, '/master') - ) - id: compute_docker_tag - run: | - tag=${GITHUB_REF#refs/tags/} - branch=${GITHUB_REF#refs/heads/} - if [ "$tag" != "$GITHUB_REF" ]; then - tag=$(echo "$tag" | sed -e 's/[^a-zA-Z0-9\-\.]/-/g') - echo ::set-output name=DOCKER_TAG::${tag} - elif [ "$branch" != "$GITHUB_REF" ]; then - branch=$(echo "$branch" | sed -e 's/[^a-zA-Z0-9\-\.]/-/g') - echo ::set-output name=DOCKER_TAG::${branch} - else - echo "unable to determine docker tag" >&2 - exit 1 - fi - - - name: Docker Login - if: | - github.event_name == 'push' && ( - startsWith(github.event.ref, 'refs/tags/') - || endsWith(github.event.ref, '/master') - ) - run: | - echo "${{ secrets.DOCKER_HUB_PASSWORD }}" \ - | docker login -u "${{ secrets.DOCKER_HUB_USER }}" --password-stdin - - - name: Docker Tag - if: | - github.event_name == 'push' && ( - startsWith(github.event.ref, 'refs/tags/') - || endsWith(github.event.ref, '/master') - ) - run: | - docker tag \ - hobbyfarm/"${{ inputs.image }}":${GIT_COMMIT_SHORT_HASH:-dev} \ - hobbyfarm/"${{ inputs.image }}":"${{ steps.compute_docker_tag.outputs.DOCKER_TAG }}" - - name: Docker Push - if: | - github.event_name == 'push' && ( - startsWith(github.event.ref, 'refs/tags/') - || endsWith(github.event.ref, '/master') - ) - run: | - docker push \ - hobbyfarm/"${{ inputs.image }}":"${{ steps.compute_docker_tag.outputs.DOCKER_TAG }}" + - name: Checkout + uses: actions/checkout@v4 - - name: Docker Tag Latest - if: | - github.event_name == 'push' && ( - startsWith(github.event.ref, 'refs/tags/') - ) - run: | - docker tag \ - hobbyfarm/"${{ inputs.image }}":${GIT_COMMIT_SHORT_HASH:-dev} \ - hobbyfarm/"${{ inputs.image }}":latest + - name: Setup go + # caching is enabled by default since setup-go@v4 + uses: actions/setup-go@v5 + with: + go-version: '1.23.6' - - name: Docker Push Latest - if: | - github.event_name == 'push' && ( - startsWith(github.event.ref, 'refs/tags/') - ) - run: | - docker push \ - hobbyfarm/"${{ inputs.image }}":latest + - name: Build + run: go build -ldflags="-s -w" -v -o app "${{ inputs.path }}" diff --git a/.github/workflows/main.yaml b/.github/workflows/pr.yaml similarity index 81% rename from .github/workflows/main.yaml rename to .github/workflows/pr.yaml index 4d6084b96..c1d11b1ae 100644 --- a/.github/workflows/main.yaml +++ b/.github/workflows/pr.yaml @@ -1,135 +1,113 @@ -name: Main -on: [push, pull_request] +name: Pull Request +on: [pull_request] jobs: build-gargantua: uses: ./.github/workflows/build.yaml with: path: ./ - image: gargantua secrets: inherit build-accesscode-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/accesscodesvc - image: accesscode-service secrets: inherit build-authn-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/authnsvc - image: authn-service secrets: inherit build-authr-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/authrsvc - image: authr-service secrets: inherit build-conversion-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/conversionsvc - image: conversion-service secrets: inherit build-cost-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/costsvc - image: cost-service secrets: inherit build-course-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/coursesvc - image: course-service secrets: inherit build-dbconfig-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/dbconfigsvc - image: dbconfig-service secrets: inherit build-environment-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/environmentsvc - image: environment-service secrets: inherit build-progress-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/progresssvc - image: progress-service secrets: inherit build-rbac-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/rbacsvc - image: rbac-service secrets: inherit build-scenario-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/scenariosvc - image: scenario-service secrets: inherit build-scheduledevent-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/scheduledeventsvc - image: scheduledevent-service secrets: inherit build-session-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/sessionsvc - image: session-service secrets: inherit build-setting-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/settingsvc - image: setting-service secrets: inherit build-terraform-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/terraformsvc - image: terraform-service secrets: inherit build-user-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/usersvc - image: user-service secrets: inherit build-vmclaim-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/vmclaimsvc - image: vmclaim-service secrets: inherit build-vmset-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/vmsetsvc - image: vmset-service secrets: inherit build-vm-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/vmsvc - image: vm-service secrets: inherit build-vmtemplate-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/vmtemplatesvc - image: vmtemplate-service secrets: inherit build-score-service: uses: ./.github/workflows/build.yaml with: path: ./v3/services/scoresvc - image: score-service secrets: inherit \ No newline at end of file diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml new file mode 100644 index 000000000..50a44065e --- /dev/null +++ b/.github/workflows/release.yaml @@ -0,0 +1,157 @@ +name: Release +on: [push] +jobs: + release-gargantua: + uses: ./.github/workflows/release_service.yaml + with: + service: gargantua + image: gargantua + dockerfile: ./Dockerfile + secrets: inherit + release-accesscode-service: + uses: ./.github/workflows/release_service.yaml + with: + service: accesscodesvc + image: accesscode-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-authn-service: + uses: ./.github/workflows/release_service.yaml + with: + service: authnsvc + image: authn-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-authr-service: + uses: ./.github/workflows/release_service.yaml + with: + service: authrsvc + image: authr-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-conversion-service: + uses: ./.github/workflows/release_service.yaml + with: + service: conversionsvc + image: conversion-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-cost-service: + uses: ./.github/workflows/release_service.yaml + with: + service: costsvc + image: cost-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-course-service: + uses: ./.github/workflows/release_service.yaml + with: + service: coursesvc + image: course-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-dbconfig-service: + uses: ./.github/workflows/release_service.yaml + with: + service: dbconfigsvc + image: dbconfig-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-environment-service: + uses: ./.github/workflows/release_service.yaml + with: + service: environmentsvc + image: environment-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-progress-service: + uses: ./.github/workflows/release_service.yaml + with: + service: progresssvc + image: progress-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-rbac-service: + uses: ./.github/workflows/release_service.yaml + with: + service: rbacsvc + image: rbac-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-scenario-service: + uses: ./.github/workflows/release_service.yaml + with: + service: scenariosvc + image: scenario-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-scheduledevent-service: + uses: ./.github/workflows/release_service.yaml + with: + service: scheduledeventsvc + image: scheduledevent-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-session-service: + uses: ./.github/workflows/release_service.yaml + with: + service: sessionsvc + image: session-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-setting-service: + uses: ./.github/workflows/release_service.yaml + with: + service: settingsvc + image: setting-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-terraform-service: + uses: ./.github/workflows/release_service.yaml + with: + service: terraformsvc + image: terraform-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-user-service: + uses: ./.github/workflows/release_service.yaml + with: + service: usersvc + image: user-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-vmclaim-service: + uses: ./.github/workflows/release_service.yaml + with: + service: vmclaimsvc + image: vmclaim-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-vmset-service: + uses: ./.github/workflows/release_service.yaml + with: + service: vmsetsvc + image: vmset-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-vm-service: + uses: ./.github/workflows/release_service.yaml + with: + service: vmsvc + image: vm-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-vmtemplate-service: + uses: ./.github/workflows/release_service.yaml + with: + service: vmtemplatesvc + image: vmtemplate-service + dockerfile: ./v3/Dockerfile + secrets: inherit + release-score-service: + uses: ./.github/workflows/release_service.yaml + with: + service: scoresvc + image: score-service + dockerfile: ./v3/Dockerfile + secrets: inherit \ No newline at end of file diff --git a/.github/workflows/release_service.yaml b/.github/workflows/release_service.yaml new file mode 100644 index 000000000..c57edc278 --- /dev/null +++ b/.github/workflows/release_service.yaml @@ -0,0 +1,125 @@ +name: Release Service +on: + workflow_call: + inputs: + service: + description: 'Service to build like costsvc, vmsetsvc' + required: true + type: string + image: + description: 'Base image name like cost-service, vmset-service' + required: true + type: string + dockerfile: + description: 'Dockerfile for the service' + required: true + type: string +jobs: + release: + name: Release ${{ inputs.image }} + runs-on: ubuntu-latest + # run if commit has new tag or push to master branch + if: | + github.event_name == 'push' && ( + startsWith(github.event.ref, 'refs/tags/') + || endsWith(github.event.ref, '/master') + ) + steps: + + - name: Checkout + uses: actions/checkout@v4 + + - name: Generate Docker Metadata + id: compute_docker_tag + uses: docker/metadata-action@v5 + with: + images: ${{ vars.DOCKER_REGISTRY || 'hobbyfarm' }}/${{ inputs.image }} + tags: | + type=ref,event=tag + type=ref,event=branch + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Cache Docker layers + uses: actions/cache@v4 + with: + path: | + ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64 + ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64 + # caching key includes service + key: ${{ runner.os }}-buildx-${{ inputs.image }} + restore-keys: | + ${{ runner.os }}-buildx- + + - name: Build linux/amd64 + uses: docker/build-push-action@v6 + with: + platforms: linux/amd64 + build-args: SERVICE_NAME=${{ inputs.service }} + context: . + file: ${{ inputs.dockerfile }} + cache-from: type=local,src=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64 + cache-to: type=local,dest=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64-new,mode=max + + - name: Build linux/arm64 + uses: docker/build-push-action@v6 + with: + platforms: linux/arm64 + build-args: SERVICE_NAME=${{ inputs.service }} + context: . + file: ${{ inputs.dockerfile }} + cache-from: type=local,src=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64 + cache-to: type=local,dest=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64-new,mode=max + + - name: Push multi-platform image + uses: docker/build-push-action@v6 + if: | + github.event_name == 'push' && ( + startsWith(github.event.ref, 'refs/tags/') + ) + with: + tags: | + ${{ steps.compute_docker_tag.outputs.tags }} + ${{ vars.DOCKER_REGISTRY || 'hobbyfarm' }}/${{ inputs.image }}:latest + platforms: linux/amd64,linux/arm64 + build-args: SERVICE_NAME=${{ inputs.service }} + context: . + file: ${{ inputs.dockerfile }} + push: true + cache-from: | + type=local,src=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64-new + type=local,src=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64-new + + - name: Login to Docker Registry + uses: docker/login-action@v3 + with: + username: ${{ secrets.DOCKER_HUB_USER }} + password: ${{ secrets.DOCKER_HUB_PASSWORD }} + + - name: Push multi-platform image + uses: docker/build-push-action@v6 + if: | + github.event_name == 'push' && ( + endsWith(github.event.ref, '/master') + ) + with: + tags: ${{ steps.compute_docker_tag.outputs.tags }} + platforms: linux/amd64,linux/arm64 + build-args: SERVICE_NAME=${{ inputs.service }} + context: . + file: ${{ inputs.dockerfile }} + push: true + cache-from: | + type=local,src=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64-new + type=local,src=${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64-new + + - # Temp fix + # https://github.com/docker/build-push-action/issues/252 + # https://github.com/moby/buildkit/issues/1896 + name: Move cache + run: | + rm -rf ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64 + mv ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64-new ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-amd64 + rm -rf ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64 + mv ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64-new ${{ runner.temp }}/buildx-cache-${{ inputs.image }}-arm64 diff --git a/Dockerfile b/Dockerfile index 482fa9afd..399d385e7 100644 --- a/Dockerfile +++ b/Dockerfile @@ -1,22 +1,36 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk +##### BUILD STAGE ##### +# use BUILDPLATFORM to pin to the native platform to prevent emulation from kicking in +FROM --platform=$BUILDPLATFORM golang:1.23.6-alpine3.21 AS build + +# os from --platform linux/amd64 +ARG TARGETOS +# architecture from --platform linux/amd64 +ARG TARGETARCH WORKDIR /app +# copy over dependency files and download dependencies COPY go.mod . -# Change to the directory of the service. -RUN go mod download -x +RUN go mod download +# copy over source files COPY . . -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -v -o /tmp/app +# build the service and output the binary to /tmp/app +RUN CGO_ENABLED=0 GOOS=$TARGETOS GOARCH=$TARGETARCH go build -ldflags="-s -w" -o /tmp/app + +##### RUNTIME STAGE ##### +FROM alpine:3.21.3 + +# create group and user app +RUN addgroup -S app && adduser -S app -G app -#RUN ls -lart && go build -o /go/bin/gargantua main.go -###### release image ##### -FROM alpine:latest +# copy over app binary from build stage +COPY --from=build /tmp/app /usr/local/bin/app -COPY --from=sdk /tmp/app /usr/local/bin/ +# switch to user app +USER app +WORKDIR /home/app -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] +ENTRYPOINT ["app"] +CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/Makefile b/Makefile index 698b5028d..f6109ba98 100644 --- a/Makefile +++ b/Makefile @@ -1,59 +1,95 @@ +# Makefile for building and pushing Docker images +SHELL := /bin/bash -# Image URL to use all building/pushing image targets -IMG ?= hobbyfarm/gargantua:dev -SVC ?= usersvc -# Produce CRDs that work back to Kubernetes 1.11 (no version conversion) -CRD_OPTIONS ?= "crd:trivialVersions=true" +# Default values +IMAGE_REGISTRY ?= hobbyfarm +IMAGE_TAG ?= latest +PLATFORMS ?= linux/amd64 +DOCKER_COMMAND ?= $(notdir $(shell command -v docker || command -v podman)) +DOCKER_BUILD_COMMAND ?= buildx build +SERVICE_BASE_PATH ?= $(shell realpath ./v3/services) +SERVICE_DOCKERFILE ?= $(shell realpath ./v3/Dockerfile) +GARGANTUA_DOCKERFILE ?= $(shell realpath ./Dockerfile) +SERVICES ?= -# Get the currently used golang install path (in GOPATH/bin, unless GOBIN is set) -ifeq (,$(shell go env GOBIN)) -GOBIN=$(shell go env GOPATH)/bin +ifeq ($(DOCKER_COMMAND),podman) + DOCKER_BUILD_COMMAND := build + PLATFORM_ARG := else -GOBIN=$(shell go env GOBIN) + PLATFORM_ARG := --platform $(PLATFORMS) endif -all: manager - -# Run tests -test: generate fmt vet - go test ./... -coverprofile cover.out - -# Build manager binary -manager: generate fmt vet - go build -o bin/gargantua main.go - -# Run against the configured Kubernetes cluster in ~/.kube/config -run: generate fmt vet - go run ./main.go +# Validate Docker/Podman installation +ifeq ($(DOCKER_COMMAND),) + $(error Neither "docker" nor "podman" exists on the system) +endif -# Run go fmt against code -fmt: - go fmt ./... +# If no services are specified, get all service directories +ifeq ($(SERVICES),) + SERVICES := gargantua $(shell find $(SERVICE_BASE_PATH) -mindepth 1 -maxdepth 1 -type d -exec basename {} \; | sort) +endif -# Run go vet against code -vet: - go vet ./... +.PHONY: help +help: + @echo "Usage:" + @echo " make docker-setup" + @echo " make docker-build [SERVICES=service1 service2] [IMAGE_TAG=tag] [IMAGE_REGISTRY=registry] [PLATFORMS=os/arch,os/arch] [PUSH=true]" + @echo " make docker-push [SERVICES=service1 service2] [IMAGE_TAG=tag] [IMAGE_REGISTRY=registry] [PLATFORMS=os/arch,os/arch]" + @echo " make generate-client" + @echo " make generate-protos" + @echo " make list-services" + @echo " make help" + @echo "" + @echo "Targets:" + @echo " docker-setup Sets up and configures Docker Buildx for the first time" + @echo " docker-build Build the docker images with multi-platform support" + @echo " docker-push Build and push the docker images with multi-platform support" + @echo " generate-client Generate kubernetes glue code for go" + @echo " generate-protos Generate go code from proto files" + @echo " list-services Prints the available services for building" + @echo " help Prints help" + @echo "" + @echo "Options:" + @echo " SERVICES List of services to build (default: all detected)" + @echo " IMAGE_TAG Tag for the built images (default: latest)" + @echo " IMAGE_REGISTRY Registry for images (default: hobbyfarm)" + @echo " PLATFORMS Comma-separated list of target platforms (default: linux/amd64)" + @echo " PUSH If set to true, push images to the registry (default: false)" -# Generate code -generate: +.PHONY: generate-client +generate-client: ./generate-client.sh -# Build the docker image -docker-build: fmt vet - docker build . -t ${IMG} - -# Push the docker image -docker-push: - docker push ${IMG} +.PHONY: generate-protos +generate-protos: + ./generate-protos.sh -build-svc: - docker build -f ./services/${SVC}/Dockerfile -t ${IMG} bin +.PHONY: docker-setup +docker-setup: + @if [ "$(DOCKER_COMMAND)" = "docker" ]; then \ + docker buildx create --use --name hobbyfarm || true; \ + docker buildx inspect --bootstrap; \ + fi -push-svc: build-svc - docker push ${IMG} +.PHONY: docker-build +docker-build: + @for service in $(SERVICES); do \ + if [ "$$service" = "gargantua" ]; then \ + echo "Building gargantua..."; \ + $(DOCKER_COMMAND) $(DOCKER_BUILD_COMMAND) $(if $(PUSH),--push,--load) $(PLATFORM_ARG) --file $(GARGANTUA_DOCKERFILE) --tag $(IMAGE_REGISTRY)/$$service:$(IMAGE_TAG) .; \ + else \ + echo "Building $$service..."; \ + image_tag=$(IMAGE_REGISTRY)/$${service/%svc/-service}:$(IMAGE_TAG); \ + $(DOCKER_COMMAND) $(DOCKER_BUILD_COMMAND) $(if $(PUSH),--push,--load) $(PLATFORM_ARG) --build-arg SERVICE_NAME=$$service --file $(SERVICE_DOCKERFILE) --tag $$image_tag .; \ + fi; \ + done -build-gargantua: - docker build -t ${IMG} . +.PHONY: docker-push +docker-push: + @make docker-build PUSH=true -push-gargantua: build-gargantua - docker push ${IMG} \ No newline at end of file +.PHONY: list-services +list-services: + @for service in $(SERVICES); do \ + echo "$$service"; \ + done diff --git a/cicd/Dockerfile b/cicd/Dockerfile index 8ead0a631..b5d8e5bdf 100644 --- a/cicd/Dockerfile +++ b/cicd/Dockerfile @@ -1,8 +1,18 @@ ## Should only be used in the context of GitHub Actions pipeline ## If trying to build locally, use Dockerfile-local -FROM alpine:latest +FROM alpine:3.21.2 -COPY app /usr/local/bin/ +# create group and user app +RUN addgroup -S app && adduser -S app -G app -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] +# copy over app binary +COPY app /home/app/app +# make the binary executable +RUN chmod +x /home/app/app && chown -R app:app /home/app/app + +# switch to user app +USER app +WORKDIR /home/app + +ENTRYPOINT ["/home/app/app"] +CMD ["-v=9", "-logtostderr"] diff --git a/docker-compose.yaml b/docker-compose.yaml deleted file mode 100644 index a69298f6c..000000000 --- a/docker-compose.yaml +++ /dev/null @@ -1,37 +0,0 @@ -version: "3.5" - -services: - - garg: - build: - context: ./cicd/docker-local - container_name: hf-garg - environment: - CGO_ENABLED: "0" - CHOKIDAR_USEPOLLING: "${CHOKIDAR_USEPOLLING:-true}" - KUBERNETES_SERVICE_HOST: "${KUBERNETES_SERVICE_HOST:-k3d}" - KUBERNETES_SERVICE_PORT: "${KUBERNETES_SERVICE_PORT:-6443}" - SSH_DEV: "${SSH_DEV:-true}" - SSH_DEV_HOST: "${SSH_DEV_HOST:-k3d}" - SSH_DEV_PORT: "${SSH_DEV_PORT:-30022}" - networks: - - dev - ports: - - "${GARG_PORT:-16210}:8080" - - "${SHELL_PORT:-16211}:8081" - user: ${FIXUID:-1000}:${FIXGID:-1000} - volumes: - - .:/app - - go-cache:/go - - kube-sa:/var/run/secrets/kubernetes.io/serviceaccount - -networks: - dev: - external: true - name: hobbyfarm-dev - -volumes: - go-cache: {} - kube-sa: - external: true - name: hobbyfarm-kube-sa diff --git a/generate-protos.sh b/generate-protos.sh old mode 100644 new mode 100755 diff --git a/v3/Dockerfile b/v3/Dockerfile new file mode 100644 index 000000000..815661409 --- /dev/null +++ b/v3/Dockerfile @@ -0,0 +1,38 @@ +##### BUILD STAGE ##### +# use BUILDPLATFORM to pin to the native platform to prevent emulation from kicking in +FROM --platform=$BUILDPLATFORM golang:1.23.6-alpine3.21 AS build + +# os from --platform linux/amd64 +ARG TARGETOS +# architecture from --platform linux/amd64 +ARG TARGETARCH +ARG SERVICE_NAME + +WORKDIR /app/v3/services/${SERVICE_NAME} +# copy over dependency files and download dependencies +COPY ./v3/services/${SERVICE_NAME}/go.mod . +COPY ./v3/go.mod /app/v3 + +RUN go mod download + +# copy over source files +COPY . /app + +# build the service and output the binary to /tmp/app +RUN CGO_ENABLED=0 GOOS=$TARGETOS GOARCH=$TARGETARCH go build -ldflags="-s -w" -o /tmp/app + +##### RUNTIME STAGE ##### +FROM alpine:3.21.3 + +# create group and user app +RUN addgroup -S app && adduser -S app -G app + +# copy over app binary from build stage +COPY --from=build /tmp/app /usr/local/bin/app + +# switch to user app +USER app +WORKDIR /home/app + +ENTRYPOINT ["app"] +CMD ["-v=9", "-logtostderr"] diff --git a/v3/go.mod b/v3/go.mod index dd66b9c48..cd8bb167f 100644 --- a/v3/go.mod +++ b/v3/go.mod @@ -1,8 +1,8 @@ module github.com/hobbyfarm/gargantua/v3 -go 1.21 +go 1.23.0 -replace k8s.io/client-go => k8s.io/client-go v0.28.2 +replace k8s.io/client-go => k8s.io/client-go v0.32.1 require ( github.com/ebauman/crder v0.1.0 diff --git a/v3/services/accesscodesvc/Dockerfile b/v3/services/accesscodesvc/Dockerfile deleted file mode 100644 index 3013e4948..000000000 --- a/v3/services/accesscodesvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/accesscodesvc - -COPY /v3/services/accesscodesvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/authnsvc/Dockerfile b/v3/services/authnsvc/Dockerfile deleted file mode 100644 index 0eb86192b..000000000 --- a/v3/services/authnsvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/authnsvc - -COPY /v3/services/authnsvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/authrsvc/Dockerfile b/v3/services/authrsvc/Dockerfile deleted file mode 100644 index a5085a99b..000000000 --- a/v3/services/authrsvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/authrsvc - -COPY /v3/services/authrsvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/conversionsvc/Dockerfile b/v3/services/conversionsvc/Dockerfile deleted file mode 100644 index 31402e933..000000000 --- a/v3/services/conversionsvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/conversionsvc - -COPY /v3/services/conversionsvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/costsvc/Dockerfile b/v3/services/costsvc/Dockerfile deleted file mode 100644 index b3a2299d7..000000000 --- a/v3/services/costsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/costsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/costsvc/go.mod b/v3/services/costsvc/go.mod index b61d3ab42..cc62f06c4 100644 --- a/v3/services/costsvc/go.mod +++ b/v3/services/costsvc/go.mod @@ -2,9 +2,9 @@ module github.com/hobbyfarm/gargantua/services/costsvc/v3 replace github.com/hobbyfarm/gargantua/v3 => ../../ -replace k8s.io/client-go => k8s.io/client-go v0.28.2 +replace k8s.io/client-go => k8s.io/client-go v0.32.1 -go 1.21.1 +go 1.23.0 require ( github.com/ebauman/crder v0.1.0 diff --git a/v3/services/coursesvc/Dockerfile b/v3/services/coursesvc/Dockerfile deleted file mode 100644 index 14bd2cfab..000000000 --- a/v3/services/coursesvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/coursesvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/dbconfigsvc/Dockerfile b/v3/services/dbconfigsvc/Dockerfile deleted file mode 100644 index e3e9fe7bc..000000000 --- a/v3/services/dbconfigsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/dbconfigsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/environmentsvc/Dockerfile b/v3/services/environmentsvc/Dockerfile deleted file mode 100644 index 9312e66fb..000000000 --- a/v3/services/environmentsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/environmentsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/progresssvc/Dockerfile b/v3/services/progresssvc/Dockerfile deleted file mode 100644 index 7db8edcbc..000000000 --- a/v3/services/progresssvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/progresssvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/rbacsvc/Dockerfile b/v3/services/rbacsvc/Dockerfile deleted file mode 100644 index 4da93de6b..000000000 --- a/v3/services/rbacsvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/rbacsvc - -COPY /v3/services/rbacsvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/scenariosvc/Dockerfile b/v3/services/scenariosvc/Dockerfile deleted file mode 100644 index 4850468bb..000000000 --- a/v3/services/scenariosvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/scenariosvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/scheduledeventsvc/Dockerfile b/v3/services/scheduledeventsvc/Dockerfile deleted file mode 100644 index 474f32fe8..000000000 --- a/v3/services/scheduledeventsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/scheduledeventsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/scoresvc/Dockerfile b/v3/services/scoresvc/Dockerfile deleted file mode 100644 index 5a8724e7f..000000000 --- a/v3/services/scoresvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/scoresvc - -COPY /v3/services/scoresvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/sessionsvc/Dockerfile b/v3/services/sessionsvc/Dockerfile deleted file mode 100644 index 56b6a3f0c..000000000 --- a/v3/services/sessionsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/sessionsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/settingsvc/Dockerfile b/v3/services/settingsvc/Dockerfile deleted file mode 100644 index ea7c4deef..000000000 --- a/v3/services/settingsvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/settingsvc - -COPY /v3/services/settingsvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/terraformsvc/Dockerfile b/v3/services/terraformsvc/Dockerfile deleted file mode 100644 index d730a3896..000000000 --- a/v3/services/terraformsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/terraformsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/usersvc/Dockerfile b/v3/services/usersvc/Dockerfile deleted file mode 100644 index 85facb619..000000000 --- a/v3/services/usersvc/Dockerfile +++ /dev/null @@ -1,24 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -# Change to the directory of the service. -WORKDIR /app/v3/services/usersvc - -COPY /v3/services/usersvc/go.mod . -COPY /v3/go.mod /app/v3 - -RUN go mod download - -# Copy everything, respecting .dockerignore. -COPY . /app - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/vmclaimsvc/Dockerfile b/v3/services/vmclaimsvc/Dockerfile deleted file mode 100644 index b27420c70..000000000 --- a/v3/services/vmclaimsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/vmclaimsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/vmsetsvc/Dockerfile b/v3/services/vmsetsvc/Dockerfile deleted file mode 100644 index 6c4b2fa36..000000000 --- a/v3/services/vmsetsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/vmsetsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/vmsvc/Dockerfile b/v3/services/vmsvc/Dockerfile deleted file mode 100644 index 4dc6e7b82..000000000 --- a/v3/services/vmsvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/vmsvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file diff --git a/v3/services/vmtemplatesvc/Dockerfile b/v3/services/vmtemplatesvc/Dockerfile deleted file mode 100644 index 9e43da1e5..000000000 --- a/v3/services/vmtemplatesvc/Dockerfile +++ /dev/null @@ -1,22 +0,0 @@ -##### sdk image ##### -FROM golang:1.21.1 AS sdk - -WORKDIR /app - -# Copy everything, respecting .dockerignore. -COPY . . - -# Change to the directory of the service. -WORKDIR /app/v3/services/vmtemplatesvc -RUN go mod download - -# Build the service. The output binary is named "app". -RUN CGO_ENABLED=0 GOOS=linux go build -o /tmp/app - -###### release image ##### -FROM alpine:latest - -COPY --from=sdk /tmp/app /usr/local/bin/ - -ENTRYPOINT ["app"] -CMD ["-v=9", "-logtostderr"] \ No newline at end of file