add deploy
This commit is contained in:
@@ -45,9 +45,39 @@ jobs:
|
||||
${{ env.REGISTRY }}/${{ env.IMAGE_PREFIX }}/spacesh-landing:${{ steps.version.outputs.VERSION }}
|
||||
${{ env.REGISTRY }}/${{ env.IMAGE_PREFIX }}/spacesh-landing:latest
|
||||
|
||||
# Push the compose stack to the prod host and roll the landing container.
|
||||
# (DMG is uploaded separately from macOS via `make deploy-dmg`.)
|
||||
deploy:
|
||||
name: Deploy to prod
|
||||
needs: landing
|
||||
runs-on: ubuntu-22.04
|
||||
container: catthehacker/ubuntu:act-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v3
|
||||
- name: Setup SSH
|
||||
run: |
|
||||
which ssh || (apt-get update && apt-get install -y openssh-client)
|
||||
mkdir -p ~/.ssh && chmod 700 ~/.ssh
|
||||
printf '%s\n' "${{ secrets.SSH_KEY }}" > ~/.ssh/id_deploy
|
||||
chmod 600 ~/.ssh/id_deploy
|
||||
ssh-keyscan "${{ secrets.SSH_HOST }}" >> ~/.ssh/known_hosts 2>/dev/null || true
|
||||
- name: Sync compose stack
|
||||
run: |
|
||||
ssh -i ~/.ssh/id_deploy "${{ secrets.SSH_USER }}@${{ secrets.SSH_HOST }}" \
|
||||
"mkdir -p '${{ secrets.SSH_REMOTE_DIR }}/download'"
|
||||
# Pin the exact image CI just pushed so the server pulls the right path/tag.
|
||||
printf 'LANDING_IMAGE=%s/%s/spacesh-landing:%s\n' \
|
||||
"${{ env.REGISTRY }}" "${{ env.IMAGE_PREFIX }}" "${{ needs.landing.outputs.version }}" > .env
|
||||
scp -i ~/.ssh/id_deploy deploy/docker-compose.yaml deploy/proxy.conf .env \
|
||||
"${{ secrets.SSH_USER }}@${{ secrets.SSH_HOST }}:${{ secrets.SSH_REMOTE_DIR }}/"
|
||||
- name: Pull & up
|
||||
run: |
|
||||
ssh -i ~/.ssh/id_deploy "${{ secrets.SSH_USER }}@${{ secrets.SSH_HOST }}" \
|
||||
"cd '${{ secrets.SSH_REMOTE_DIR }}' && docker compose pull && docker compose up -d"
|
||||
|
||||
notify:
|
||||
name: Notify Max
|
||||
needs: landing
|
||||
needs: [landing, deploy]
|
||||
if: always()
|
||||
runs-on: ubuntu-22.04
|
||||
container: catthehacker/ubuntu:act-latest
|
||||
@@ -59,6 +89,12 @@ jobs:
|
||||
failure) line="❌ spacesh-landing — ошибка сборки";;
|
||||
*) line="❔ spacesh-landing — ${{ needs.landing.result }}";;
|
||||
esac
|
||||
case "${{ needs.deploy.result }}" in
|
||||
success) dline="🚀 задеплоен на прод";;
|
||||
failure) dline="❌ деплой упал";;
|
||||
*) dline="❔ деплой — ${{ needs.deploy.result }}";;
|
||||
esac
|
||||
line="$line"$'\n'"$dline"
|
||||
url="${{ gitea.server_url }}/${{ gitea.repository }}/actions/runs/${{ gitea.run_number }}"
|
||||
text=$(printf '**Build landing**\n\n%s\n\n[лог](%s)' "$line" "$url")
|
||||
curl -s -X POST "https://platform-api.max.ru/messages?chat_id=${{ secrets.MAX_CHAT_ID }}" \
|
||||
|
||||
@@ -17,6 +17,13 @@ LANDING_VERSION := $(shell cat landing/VERSION 2>/dev/null || echo 0.0.0)
|
||||
REGISTRY ?= git.realmanual.ru
|
||||
REPO ?= spacesh
|
||||
|
||||
# ---- Prod deploy (SSH) ----
|
||||
SSH_HOST ?= 192.168.8.5
|
||||
SSH_USER ?= deploy
|
||||
SSH_REMOTE_DIR ?= /opt/spacesh
|
||||
SSH_KEY ?= $(HOME)/.ssh/id_rsa
|
||||
SSH_OPTS := -i $(SSH_KEY) -o StrictHostKeyChecking=accept-new
|
||||
|
||||
.DEFAULT_GOAL := help
|
||||
|
||||
.PHONY: help
|
||||
@@ -109,6 +116,20 @@ landing-push: landing-image ## tag & push the landing image to the registry
|
||||
docker push $(REGISTRY)/$(REPO)/$(LANDING_IMAGE):$(LANDING_VERSION)
|
||||
docker push $(REGISTRY)/$(REPO)/$(LANDING_IMAGE):latest
|
||||
|
||||
# ---- Prod deploy ----
|
||||
|
||||
.PHONY: deploy-dmg
|
||||
deploy-dmg: dmg ## upload the universal .dmg to the prod download dir (stable spacesh.dmg)
|
||||
ssh $(SSH_OPTS) $(SSH_USER)@$(SSH_HOST) "mkdir -p $(SSH_REMOTE_DIR)/download"
|
||||
scp $(SSH_OPTS) $(DMG_DIR)/*.dmg "$(SSH_USER)@$(SSH_HOST):$(SSH_REMOTE_DIR)/download/spacesh.dmg"
|
||||
@echo "Uploaded → https://spaceshell.ru/download/spacesh.dmg"
|
||||
|
||||
.PHONY: deploy-stack
|
||||
deploy-stack: ## sync compose+proxy.conf to prod and pull/up (manual; CI does this on push)
|
||||
ssh $(SSH_OPTS) $(SSH_USER)@$(SSH_HOST) "mkdir -p $(SSH_REMOTE_DIR)/download"
|
||||
scp $(SSH_OPTS) deploy/docker-compose.yaml deploy/proxy.conf "$(SSH_USER)@$(SSH_HOST):$(SSH_REMOTE_DIR)/"
|
||||
ssh $(SSH_OPTS) $(SSH_USER)@$(SSH_HOST) "cd $(SSH_REMOTE_DIR) && docker compose pull && docker compose up -d"
|
||||
|
||||
# ---- Clean ----
|
||||
|
||||
.PHONY: clean
|
||||
|
||||
@@ -0,0 +1,31 @@
|
||||
# Deploy — spaceshell.ru
|
||||
|
||||
Front nginx (`proxy`) → landing container, plus `/download/spacesh.dmg`.
|
||||
|
||||
## Layout on the server (`$SSH_REMOTE_DIR`, e.g. `/opt/spacesh`)
|
||||
|
||||
```
|
||||
docker-compose.yaml # synced by CI
|
||||
proxy.conf # synced by CI
|
||||
download/spacesh.dmg # uploaded locally via `make deploy-dmg`
|
||||
```
|
||||
|
||||
## One-time server setup
|
||||
|
||||
```bash
|
||||
# The landing image lives in a private registry — log the server in once:
|
||||
docker login git.realmanual.ru
|
||||
mkdir -p $SSH_REMOTE_DIR/download
|
||||
```
|
||||
|
||||
## What runs where
|
||||
|
||||
- **Landing image + compose deploy** → automatic in `.gitea/workflows/build.yaml`
|
||||
on push to `landing/**`. CI builds/pushes the image, scps `deploy/*` to the
|
||||
server, then `docker compose pull && up -d`.
|
||||
- **DMG** → built on macOS, uploaded by hand: `make deploy-dmg`
|
||||
(sets the stable `download/spacesh.dmg`). Tauri can't build a macOS bundle in CI.
|
||||
|
||||
## Gitea secrets required
|
||||
|
||||
`SSH_HOST`, `SSH_USER`, `SSH_REMOTE_DIR`, `SSH_KEY` (private key, key-based auth).
|
||||
@@ -0,0 +1,32 @@
|
||||
# spacesh prod — front nginx proxies to the landing container and serves the DMG.
|
||||
# Deployed by .gitea/workflows/build.yaml (image + this file); the DMG is uploaded
|
||||
# separately via `make deploy-dmg` (Tauri can't cross-compile a macOS bundle in CI).
|
||||
services:
|
||||
landing:
|
||||
# LANDING_IMAGE is written to .env by the CI deploy job (exact registry path + tag).
|
||||
image: ${LANDING_IMAGE:-git.realmanual.ru/spacesh/spacesh-landing:latest}
|
||||
restart: unless-stopped
|
||||
expose:
|
||||
- "80"
|
||||
|
||||
proxy:
|
||||
image: nginx:1.27-alpine
|
||||
restart: unless-stopped
|
||||
depends_on:
|
||||
- landing
|
||||
ports:
|
||||
- "80:80"
|
||||
volumes:
|
||||
- ./proxy.conf:/etc/nginx/conf.d/default.conf:ro
|
||||
- ./download:/srv/download:ro
|
||||
networks:
|
||||
spaceshell-network:
|
||||
webproxy:
|
||||
ipv4_address: 172.18.0.28
|
||||
|
||||
networks:
|
||||
spaceshell-network:
|
||||
driver: bridge
|
||||
webproxy:
|
||||
name: webproxy
|
||||
external: true
|
||||
@@ -0,0 +1,30 @@
|
||||
# Front nginx for spaceshell.ru — reverse-proxies the landing container and
|
||||
# serves macOS .dmg downloads from the host-mounted ./download volume.
|
||||
upstream landing_upstream {
|
||||
server landing:80;
|
||||
}
|
||||
|
||||
server {
|
||||
listen 80;
|
||||
listen [::]:80;
|
||||
server_name spaceshell.ru www.spaceshell.ru;
|
||||
|
||||
# Stable download URL: /download/spacesh.dmg → ./download/spacesh.dmg on host.
|
||||
location /download/ {
|
||||
alias /srv/download/;
|
||||
autoindex off;
|
||||
default_type application/octet-stream;
|
||||
add_header Content-Disposition "attachment";
|
||||
types {
|
||||
application/x-apple-diskimage dmg;
|
||||
}
|
||||
}
|
||||
|
||||
location / {
|
||||
proxy_pass http://landing_upstream;
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -1098,7 +1098,7 @@
|
||||
<div class="container">
|
||||
<h2 class="cta-title reveal">Готов гонять агентов пачками?</h2>
|
||||
<div class="cta-buttons reveal">
|
||||
<a href="#" class="btn btn-primary btn-large">
|
||||
<a href="/download/spacesh.dmg" class="btn btn-primary btn-large">
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="currentColor">
|
||||
<path d="M8 0a8 8 0 100 16A8 8 0 008 0zm3.5 9l-3 3a.7.7 0 01-1 0l-3-3a.7.7 0 011-1L7 9.5V4a1 1 0 012 0v5.5L10.5 8a.7.7 0 011 1z"/>
|
||||
</svg>
|
||||
|
||||
Reference in New Issue
Block a user