diff --git a/.dockerignore b/.dockerignore new file mode 100644 index 0000000..19fb0fb --- /dev/null +++ b/.dockerignore @@ -0,0 +1,5 @@ +.git +.worktrees +dist +node_modules +*.log diff --git a/.woodpecker/build-image.yaml b/.woodpecker/build-image.yaml new file mode 100644 index 0000000..bc8e058 --- /dev/null +++ b/.woodpecker/build-image.yaml @@ -0,0 +1,100 @@ +# 文字马赛克静态站镜像构建流水线 +# 触发:push 到 main 自动运行,也支持手动运行。 +# 镜像:registry.mattuy.top/text-mosaic: + +when: + - event: push + branch: main + - event: manual + +variables: + - ¬ify_image registry.gitlab.com/gitlab-ci-utils/curl-jq:4.0.2 + - &small_resources + requests: + cpu: "10m" + memory: "32Mi" + limits: + cpu: "200m" + memory: "128Mi" + - ¬ify_script | + case "$NOTIFY_EVENT" in + started) EMOJI="🚀"; TEXT="静态站镜像构建开始" ;; + success) EMOJI="✅"; TEXT="静态站镜像构建成功" ;; + failure) EMOJI="❌"; TEXT="静态站镜像构建失败" ;; + *) EMOJI="❓"; TEXT="$NOTIFY_EVENT" ;; + esac + COMMIT_SHORT=$(printf '%s' "$CI_COMMIT_SHA" | cut -c1-7) + COMMIT_SUBJECT=$(printf '%s' "$CI_COMMIT_MESSAGE" | head -1) + TITLE="$EMOJI [text-mosaic] $TEXT" + CONTENT="分支: $CI_COMMIT_BRANCH + 提交: $COMMIT_SHORT \"$COMMIT_SUBJECT\" + 作者: $CI_COMMIT_AUTHOR + 详情: $CI_PIPELINE_URL" + PAYLOAD=$(jq -n -c \ + --arg source 'text-mosaic' \ + --arg title "$TITLE" \ + --arg content "$CONTENT" \ + --arg priority "${NOTIFY_PRIORITY:-}" \ + '{source: $source, title: $title, content: $content} + (if $priority == "" then {} else {priority: $priority} end)') + curl -sS --fail-with-body --show-error -X POST -H 'content-type: application/json' \ + -d "$PAYLOAD" \ + http://mattuy-api.mattuy-house.svc/api/notification/notify + +steps: + notify-start: + image: *notify_image + environment: + NOTIFY_EVENT: started + NOTIFY_PRIORITY: silent + backend_options: + kubernetes: + resources: *small_resources + commands: + - *notify_script + failure: ignore + + build-and-push: + image: moby/buildkit:v0.28.1 + backend_options: + kubernetes: + resources: + requests: + cpu: "100m" + memory: "128Mi" + limits: + cpu: "1000m" + memory: "1Gi" + commands: + - >- + buildctl --addr tcp://buildkitd.mattuy-house.svc:1234 build + --frontend dockerfile.v0 + --local context=. + --local dockerfile=. + --output type=image,\"name=registry.mattuy.top/text-mosaic:${CI_COMMIT_SHA:0:7}\",push=true,registry.insecure=true + --export-cache type=s3,mode=max,bucket=buildcache,region=us-east-1,endpoint_url=https://io-lan.mattuy.top,use_path_style=true,name=text-mosaic + --import-cache type=s3,bucket=buildcache,region=us-east-1,endpoint_url=https://io-lan.mattuy.top,use_path_style=true,name=text-mosaic + + notify-success: + image: *notify_image + environment: + NOTIFY_EVENT: success + NOTIFY_PRIORITY: low + backend_options: + kubernetes: + resources: *small_resources + commands: + - *notify_script + failure: ignore + + notify-failure: + image: *notify_image + environment: + NOTIFY_EVENT: failure + backend_options: + kubernetes: + resources: *small_resources + commands: + - *notify_script + when: + - status: failure + failure: ignore diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..279fae9 --- /dev/null +++ b/Dockerfile @@ -0,0 +1,16 @@ +FROM oven/bun:1.3.11-alpine AS build + +WORKDIR /app + +COPY package.json index.html tsconfig.json ./ +COPY scripts ./scripts +COPY src ./src + +RUN bun run build + +FROM nginxinc/nginx-unprivileged:1.29.4-alpine + +COPY nginx.conf /etc/nginx/conf.d/default.conf +COPY --from=build /app/dist /usr/share/nginx/html + +EXPOSE 8080 diff --git a/nginx.conf b/nginx.conf new file mode 100644 index 0000000..59b4d34 --- /dev/null +++ b/nginx.conf @@ -0,0 +1,28 @@ +server { + listen 8080; + server_name _; + absolute_redirect off; + port_in_redirect off; + + root /usr/share/nginx/html; + index index.html; + + location = /healthz { + access_log off; + default_type text/plain; + return 200 "ok\n"; + } + + location = /index.html { + add_header Cache-Control "no-cache, must-revalidate"; + } + + location ~* \.(?:css|js)$ { + try_files $uri =404; + add_header Cache-Control "public, max-age=31536000, immutable"; + } + + location / { + try_files $uri $uri/ /index.html; + } +}