Skip to content

Commit

Permalink
Fix build pipeline and ensure the docker container can build properly
Browse files Browse the repository at this point in the history
  • Loading branch information
karbowiak committed Oct 4, 2024
1 parent 6b5232d commit df3588a
Show file tree
Hide file tree
Showing 10 changed files with 257 additions and 15 deletions.
29 changes: 29 additions & 0 deletions .docker/Dockerfile
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
# Build stage
FROM golang:1.23-alpine AS builder

# Install necessary build tools and WebP libraries
RUN apk add --no-cache gcc musl-dev libwebp-dev

# Set the working directory
WORKDIR /app

# Copy the source code
COPY /src /app

# Build the application
ENV CGO_ENABLED=1
RUN go build -o esi-imageproxy

# Final stage
FROM alpine:latest

RUN apk add --no-cache libwebp

# Set the working directory
WORKDIR /app

# Copy the binary from the builder stage
COPY --from=builder /app/esi-imageproxy .

# Set the command to run the binary
CMD ["./esi-imageproxy"]
15 changes: 15 additions & 0 deletions .github/dependabot.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# To get started with Dependabot version updates, you'll need to specify which
# package ecosystems to update and where the package manifests are located.
# Please see the documentation for all configuration options:
# https://docs.github.com/code-security/dependabot/dependabot-version-updates/configuration-options-for-the-dependabot.yml-file

version: 2
updates:
- package-ecosystem: "github-actions"
directory: "/"
schedule:
interval: "weekly"
- package-ecosystem: "gomod"
directory: "/"
schedule:
interval: "weekly"
76 changes: 76 additions & 0 deletions .github/workflows/pipeline.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
name: Pipeline

on:
push:
branches: ["master"]
tags: ["v*.*.*"]

env:
# Use docker.io for Docker Hub if empty
REGISTRY: ghcr.io
# github.repository as <account>/<repo>
IMAGE_NAME: ${{ github.repository }}

jobs:
build-container:
runs-on: ubuntu-latest
concurrency:
group: ${{ github.ref }}
cancel-in-progress: true
permissions:
contents: read
packages: write
# This is used to complete the identity challenge
# with sigstore/fulcio when running outside of PRs.
id-token: write

steps:
- name: Get short commit hash
id: short_commit
run: echo "::set-output name=hash::$(echo ${GITHUB_SHA::8})"

- name: Checkout repository
uses: actions/checkout@v4

# Set up BuildKit Docker container builder to be able to build
# multi-platform images and export cache
# https:/docker/setup-buildx-action
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@988b5a0280414f521da01fcc63a27aeeb4b104db # v3.6.1

# Login against a Docker registry except on PR
# https:/docker/login-action
- name: Log into registry ${{ env.REGISTRY }}
if: github.event_name != 'pull_request'
uses: docker/login-action@9780b0c442fbb1117ed29e0efdff1e18412f7567 # v3.3.0
with:
registry: ${{ env.REGISTRY }}
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}

# Extract metadata (tags, labels) for Docker
# https:/docker/metadata-action
- name: Extract Docker metadata
id: meta
uses: docker/metadata-action@8e5442c4ef9f78752691e2d8f8d19755c6f78e81 # v5.5.1
with:
images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
tags: |
latest
${{ steps.short_commit.outputs.hash }}
# Build and push Docker image with Buildx (don't push on PR)
# https:/docker/build-push-action
- name: Build and push Docker image
id: build-and-push
uses: docker/build-push-action@4f58ea79222b3b9dc2c8bbdd6debcef730109a75 # v6.9.0
with:
context: .
file: .docker/Dockerfile
push: ${{ github.event_name != 'pull_request' }}
tags: ${{ steps.meta.outputs.tags }}
labels: ${{ steps.meta.outputs.labels }}
platforms: linux/amd64
#platforms: linux/amd64,linux/arm64
cache-from: type=gha
cache-to: type=gha,mode=max
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
.vscode/settings.json
.idea/
.env
.DS_Store
13 changes: 13 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
version: '3.8'

services:
esi-proxy:
image: ghcr.io/eve-kill/esi-imageproxy:latest
ports:
- "9501:9501"
networks:
- proxy

networks:
proxy:
driver: bridge
107 changes: 107 additions & 0 deletions kubernetes.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
apiVersion: apps/v1
kind: Deployment
metadata:
name: esi-imageproxy
labels:
app: esi-imageproxy
spec:
replicas: 3
strategy:
type: RollingUpdate
rollingUpdate:
maxUnavailable: 0
maxSurge: 1
selector:
matchLabels:
app: esi-imageproxy
template:
metadata:
labels:
app: esi-imageproxy
spec:
containers:
- name: esi-imageproxy
image: ghcr.io/eve-kill/esi-imageproxy:latest
imagePullPolicy: Always
ports:
- containerPort: 9501
resources:
requests:
memory: "256Mi"
cpu: "500m"
limits:
memory: "2048Mi"
cpu: "1"
livenessProbe:
httpGet:
path: /healthz
port: 9501
initialDelaySeconds: 30
periodSeconds: 10
readinessProbe:
httpGet:
path: /readyz
port: 9501
initialDelaySeconds: 30
periodSeconds: 10
terminationGracePeriodSeconds: 30
strategy:
type: RollingUpdate
rollingUpdate:
maxUnavailable: 1
maxSurge: 1

---
apiVersion: v1
kind: Service
metadata:
name: esi-imageproxy
spec:
selector:
app: esi-imageproxy
ports:
- protocol: TCP
port: 9501
targetPort: 9501

---
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: esi-imageproxy-ingress
annotations:
cert-manager.io/cluster-issuer: "letsencrypt-prod"
nginx.ingress.kubernetes.io/ssl-redirect: "true"
nginx.ingress.kubernetes.io/proxy-http-version: "1.1"
nginx.ingress.kubernetes.io/proxy-keepalive: "on"
nginx.ingress.kubernetes.io/proxy-keepalive-timeout: "60s"
nginx.ingress.kubernetes.io/proxy-keepalive-requests: "100"
nginx.ingress.kubernetes.io/proxy-connect-timeout: "10s"
nginx.ingress.kubernetes.io/proxy-read-timeout: "15s"
nginx.ingress.kubernetes.io/proxy-send-timeout: "15s"
nginx.ingress.kubernetes.io/proxy-body-size: "0"
nginx.ingress.kubernetes.io/proxy-buffering: "on"
nginx.ingress.kubernetes.io/proxy-buffers-number: "4"
nginx.ingress.kubernetes.io/proxy-buffer-size: "8k"
nginx.ingress.kubernetes.io/proxy-max-temp-file-size: "1024m"
nginx.ingress.kubernetes.io/proxy-request-buffering: "on"
nginx.ingress.kubernetes.io/proxy-response-buffering: "on"
nginx.ingress.kubernetes.io/proxy-gzip: "on"
nginx.ingress.kubernetes.io/proxy-gzip-min-length: "256"
nginx.ingress.kubernetes.io/proxy-gzip-types: "application/json application/javascript text/css text/html text/xml text/plain"
spec:
rules:
- host: your.domain.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: esi-imageproxy
port:
number: 9501
tls:
- hosts:
- your.domain.com
secretName: esi-imageproxy-tls
7 changes: 5 additions & 2 deletions src/go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,12 @@ module github.com/eve-kill/esi-imageproxy
go 1.23.1

require (
github.com/chai2010/webp v1.1.1 // indirect
github.com/kolesa-team/go-webp v1.0.4
github.com/patrickmn/go-cache v2.1.0+incompatible
)

require (
github.com/disintegration/imaging v1.6.2 // indirect
github.com/nfnt/resize v0.0.0-20180221191011-83c6a9932646 // indirect
github.com/patrickmn/go-cache v2.1.0+incompatible // indirect
golang.org/x/image v0.0.0-20211028202545-6944b10bf410 // indirect
)
11 changes: 2 additions & 9 deletions src/go.sum
Original file line number Diff line number Diff line change
@@ -1,14 +1,7 @@
github.com/chai2010/webp v1.1.1 h1:jTRmEccAJ4MGrhFOrPMpNGIJ/eybIgwKpcACsrTEapk=
github.com/chai2010/webp v1.1.1/go.mod h1:0XVwvZWdjjdxpUEIf7b9g9VkHFnInUSYujwqTLEuldU=
github.com/disintegration/imaging v1.6.2 h1:w1LecBlG2Lnp8B3jk5zSuNqd7b4DXhcjwek1ei82L+c=
github.com/disintegration/imaging v1.6.2/go.mod h1:44/5580QXChDfwIclfc/PCwrr44amcmDAg8hxG0Ewe4=
github.com/nfnt/resize v0.0.0-20180221191011-83c6a9932646 h1:zYyBkD/k9seD2A7fsi6Oo2LfFZAehjjQMERAvZLEDnQ=
github.com/kolesa-team/go-webp v1.0.4 h1:wQvU4PLG/X7RS0vAeyhiivhLRoxfLVRlDq4I3frdxIQ=
github.com/kolesa-team/go-webp v1.0.4/go.mod h1:oMvdivD6K+Q5qIIkVC2w4k2ZUnI1H+MyP7inwgWq9aA=
github.com/nfnt/resize v0.0.0-20180221191011-83c6a9932646/go.mod h1:jpp1/29i3P1S/RLdc7JQKbRpFeM1dOBd8T9ki5s+AY8=
github.com/patrickmn/go-cache v2.1.0+incompatible h1:HRMgzkcYKYpi3C8ajMPV8OFXaaRUnok+kx1WdO15EQc=
github.com/patrickmn/go-cache v2.1.0+incompatible/go.mod h1:3Qf8kWWT7OJRJbdiICTKqZju1ZixQ/KpMGzzAfe6+WQ=
golang.org/x/image v0.0.0-20191009234506-e7c1f5e7dbb8/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
golang.org/x/image v0.0.0-20211028202545-6944b10bf410 h1:hTftEOvwiOq2+O8k2D5/Q7COC7k5Qcrgc2TFURJYnvQ=
golang.org/x/image v0.0.0-20211028202545-6944b10bf410/go.mod h1:023OzeP/+EPmXeapQh35lcL3II3LrY8Ic+EFFKVhULM=
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ=
8 changes: 6 additions & 2 deletions src/helpers/image.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,8 @@ import (
"strings"
"time"

"github.com/chai2010/webp"
"github.com/kolesa-team/go-webp/encoder"
"github.com/kolesa-team/go-webp/webp"
)

// CacheOptimizedImages optimizes and caches images in WebP, PNG, and JPEG formats.
Expand All @@ -19,7 +20,10 @@ func CacheOptimizedImages(cache *Cache, cacheKey string, img image.Image, header

// Optimize and cache WebP
webpBuffer := new(bytes.Buffer)
if err := webp.Encode(webpBuffer, img, &webp.Options{Lossless: false, Quality: 80}); err != nil {
options, err := encoder.NewLossyEncoderOptions(encoder.PresetDefault, 80)
if err != nil {
log.Printf("Error creating WebP encoder options: %v", err)
} else if err := webp.Encode(webpBuffer, img, options); err != nil {
log.Printf("Error encoding WebP: %v", err)
} else {
cache.Set(cacheKey+"-webp", CacheItem{
Expand Down
2 changes: 0 additions & 2 deletions src/proxy/esi.go
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,6 @@ func HandleRequest(proxy *httputil.ReverseProxy, cache *helpers.Cache) http.Hand

// Check if the optimized image is in the cache
if _, found := cache.Get(preferredCacheKey); found {
log.Printf("Cache HIT for %s (%s)", r.URL.Path, preferredFormat)
helpers.ServeOptimizedImage(w, r, cache, cacheKey)
return
}
Expand All @@ -85,7 +84,6 @@ func HandleRequest(proxy *httputil.ReverseProxy, cache *helpers.Cache) http.Hand

// Check if the response status is OK
if recorder.status != http.StatusOK {
http.Error(w, "Failed to fetch image", recorder.status)
return
}

Expand Down

0 comments on commit df3588a

Please sign in to comment.