On branch main
new file: main_dc/README.md modified: main_dc/valitovgaziz/package-lock.json modified: main_dc/valitovgaziz/src/components/TheFooter.vue fix 2025 to 2026 into valitovgaziz site
This commit is contained in:
@@ -0,0 +1,223 @@
|
||||
Текущие проблемы
|
||||
1. Деплой в 5 шагов: локальный код → push → SSH → pull → make (ручной, медленный)
|
||||
2. Добавление нового сайта требует правки 7+ файлов: .env, docker-compose.yml, nginx-http.conf, nginx-ssl.conf, switch-config.sh, init-certbot.sh, checkRenewCerts.sh, Makefile — легко забыть что-то
|
||||
3. HTTPS all-or-nothing: если у одного домена нет сертификата — все сайты падают на HTTP
|
||||
4. Certbot: дублирование кода на каждый домен в init-certbot.sh, checkRenewCerts.sh и 5 отдельных renew-скриптов
|
||||
5. Makefile растёт — на каждый сервис 4-5 целей
|
||||
Предложение
|
||||
Фаза 1: CI/CD через GitHub Actions
|
||||
Создать .github/workflows/deploy.yml:
|
||||
name: Deploy
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
paths:
|
||||
- 'main_dc/**'Текущие проблемы
|
||||
1. Деплой в 5 шагов: локальный код → push → SSH → pull → make (ручной, медленный)
|
||||
2. Добавление нового сайта требует правки 7+ файлов: .env, docker-compose.yml, nginx-http.conf, nginx-ssl.conf, switch-config.sh, init-certbot.sh, checkRenewCerts.sh, Makefile — легко забыть что-то
|
||||
3. HTTPS all-or-nothing: если у одного домена нет сертификата — все сайты падают на HTTP
|
||||
4. Certbot: дублирование кода на каждый домен в init-certbot.sh, checkRenewCerts.sh и 5 отдельных renew-скриптов
|
||||
5. Makefile растёт — на каждый сервис 4-5 целей
|
||||
Предложение
|
||||
Фаза 1: CI/CD через GitHub Actions
|
||||
Создать .github/workflows/deploy.yml:
|
||||
name: Deploy
|
||||
on:
|
||||
push:
|
||||
branches: [main]
|
||||
paths:
|
||||
- 'main_dc/**'
|
||||
|
||||
jobs:
|
||||
deploy:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
- name: Deploy via SSH
|
||||
uses: appleboy/ssh-action@v1
|
||||
with:
|
||||
host: ${{ secrets.HOST }}
|
||||
username: ${{ secrets.USER }}
|
||||
key: ${{ secrets.SSH_KEY }}
|
||||
script: |
|
||||
cd /home/valitovgaziz/tp
|
||||
git pull origin main
|
||||
# Определить какие сервисы изменились и пересобрать только их
|
||||
# Или просто: make all
|
||||
Преимущества: push → авто-деплой за ~1 мин, без SSH вручную.
|
||||
Фаза 2: Единый источник истины — sites.yml
|
||||
Ввести файл main_dc/sites.yml со списком всех сайтов:
|
||||
sites:
|
||||
yalarba:
|
||||
domain: yalarba.ru
|
||||
aliases: [www.yalarba.ru]
|
||||
type: spa
|
||||
root: /usr/share/nginx/yalarba/html
|
||||
api: http://api_tp/
|
||||
api_yal: http://api_yal/
|
||||
|
||||
valitovgaziz:
|
||||
domain: valitovgaziz.ru
|
||||
aliases: [www.valitovgaziz.ru]
|
||||
type: container
|
||||
upstream: http://valitovgaziz/
|
||||
api: http://analytics:3000/
|
||||
|
||||
easysite102:
|
||||
domain: easysite102.ru
|
||||
aliases: [www.easysite102.ru]
|
||||
type: container
|
||||
upstream: http://easysite:3000
|
||||
api: http://api_es:8088/
|
||||
|
||||
begushiybashkir:
|
||||
domain: begushiybashkir.ru
|
||||
aliases: [www.begushiybashkir.ru]
|
||||
type: spa
|
||||
root: /usr/share/nginx/begushiybashkir/html
|
||||
api: http://api_bb:8080/
|
||||
Скрипт-генератор (generate-configs.sh) на основе sites.yml создаёт:
|
||||
- nginx-http.conf — HTTP-блоки
|
||||
- nginx-ssl.conf — HTTPS-блоки для каждого домена, каждый независимо проверяет свой сертификат
|
||||
- nginx-partial-ssl.conf — комбинированный: HTTPS где есть серт, HTTP где нет
|
||||
- certbot-domains.txt — список доменов для certbot
|
||||
- .env — переменные окружения
|
||||
Добавление нового сайта: 1 правка в sites.yml → ./generate-configs.sh → git commit.
|
||||
Фаза 3: Умный nginx — per-domain HTTPS
|
||||
Убрать all-or-nothing switch-config.sh. Вместо этого nginx грузит все конфиги через include:
|
||||
/etc/nginx/conf.d/
|
||||
├── 00-http-default.conf # HTTP на 80
|
||||
├── 10-yalarba-ssl.conf # HTTPS, если есть серт
|
||||
├── 20-valitovgaziz-ssl.conf # HTTPS, если есть серт
|
||||
├── 30-easysite102-ssl.conf # HTTPS, если есть серт
|
||||
└── common/ # Общие настройки
|
||||
Каждый файл SSL генерируется с if-проверкой наличия сертификата:
|
||||
server {
|
||||
listen 443 ssl;
|
||||
server_name valitovgaziz.ru www.valitovgaziz.ru;
|
||||
ssl_certificate /etc/letsencrypt/live/valitovgaziz.ru/fullchain.pem;
|
||||
...
|
||||
}
|
||||
А HTTP-сервер делает return 301 https://$host$request_uri только для тех доменов, у кого есть сертификат. Остальные работают по HTTP.
|
||||
Фаза 4: Certbot — один скрипт для всех
|
||||
Вместо 5 renew-скриптов:
|
||||
# /opt/renew-all.sh — единый скрипт
|
||||
certbot renew --webroot -w /var/www/certbot
|
||||
Certbot сам знает все домены, для которых получал сертификаты. --webroot с одним -w работает для всех. Убрать:
|
||||
- renewBegushiyBAshkirLatin.sh, renewBegushiyBashkir.sh, renewEasysite102.sh, renewValitovGazizCert.sh, renewYalarbaCert.sh
|
||||
- Заменить checkRenewCerts.sh на вызов certbot renew
|
||||
Фаза 5: Makefile — авто-детект изменений
|
||||
Оставить базовые цели, но добавить:
|
||||
deploy: git
|
||||
@echo "Detecting changes..."
|
||||
@git diff --name-only HEAD~1 HEAD | grep -o 'main_dc/[^/]*/' | sort -u | while read dir; do \
|
||||
service=$$(basename $$dir); \
|
||||
if grep -q "^ $$service:" docker-compose.yml; then \
|
||||
make stop_$$service build_$$service start_$$service; \
|
||||
fi \
|
||||
done
|
||||
Или ещё проще: GitHub Actions сам определяет какие сервисы изменились и запускает только их make цели.
|
||||
Дорожная карта
|
||||
Шаг Что делаем Эффект
|
||||
1 sites.yml + generate-configs.sh Добавление сайта = 1 файл
|
||||
2 Переход на per-domain HTTPS в nginx Один сайт без серта не ломает другие
|
||||
3 Упрощение certbot: единый certbot renew Удалить 5 скриптов
|
||||
4 GitHub Actions deploy workflow push → авто-деплой
|
||||
5 Makefile: deploy с авто-детектом Быстрый частичный деплой
|
||||
|
||||
jobs:
|
||||
deploy:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
- name: Deploy via SSH
|
||||
uses: appleboy/ssh-action@v1
|
||||
with:
|
||||
host: ${{ secrets.HOST }}
|
||||
username: ${{ secrets.USER }}
|
||||
key: ${{ secrets.SSH_KEY }}
|
||||
script: |
|
||||
cd /home/valitovgaziz/tp
|
||||
git pull origin main
|
||||
# Определить какие сервисы изменились и пересобрать только их
|
||||
# Или просто: make all
|
||||
Преимущества: push → авто-деплой за ~1 мин, без SSH вручную.
|
||||
Фаза 2: Единый источник истины — sites.yml
|
||||
Ввести файл main_dc/sites.yml со списком всех сайтов:
|
||||
sites:
|
||||
yalarba:
|
||||
domain: yalarba.ru
|
||||
aliases: [www.yalarba.ru]
|
||||
type: spa
|
||||
root: /usr/share/nginx/yalarba/html
|
||||
api: http://api_tp/
|
||||
api_yal: http://api_yal/
|
||||
|
||||
valitovgaziz:
|
||||
domain: valitovgaziz.ru
|
||||
aliases: [www.valitovgaziz.ru]
|
||||
type: container
|
||||
upstream: http://valitovgaziz/
|
||||
api: http://analytics:3000/
|
||||
|
||||
easysite102:
|
||||
domain: easysite102.ru
|
||||
aliases: [www.easysite102.ru]
|
||||
type: container
|
||||
upstream: http://easysite:3000
|
||||
api: http://api_es:8088/
|
||||
|
||||
begushiybashkir:
|
||||
domain: begushiybashkir.ru
|
||||
aliases: [www.begushiybashkir.ru]
|
||||
type: spa
|
||||
root: /usr/share/nginx/begushiybashkir/html
|
||||
api: http://api_bb:8080/
|
||||
Скрипт-генератор (generate-configs.sh) на основе sites.yml создаёт:
|
||||
- nginx-http.conf — HTTP-блоки
|
||||
- nginx-ssl.conf — HTTPS-блоки для каждого домена, каждый независимо проверяет свой сертификат
|
||||
- nginx-partial-ssl.conf — комбинированный: HTTPS где есть серт, HTTP где нет
|
||||
- certbot-domains.txt — список доменов для certbot
|
||||
- .env — переменные окружения
|
||||
Добавление нового сайта: 1 правка в sites.yml → ./generate-configs.sh → git commit.
|
||||
Фаза 3: Умный nginx — per-domain HTTPS
|
||||
Убрать all-or-nothing switch-config.sh. Вместо этого nginx грузит все конфиги через include:
|
||||
/etc/nginx/conf.d/
|
||||
├── 00-http-default.conf # HTTP на 80
|
||||
├── 10-yalarba-ssl.conf # HTTPS, если есть серт
|
||||
├── 20-valitovgaziz-ssl.conf # HTTPS, если есть серт
|
||||
├── 30-easysite102-ssl.conf # HTTPS, если есть серт
|
||||
└── common/ # Общие настройки
|
||||
Каждый файл SSL генерируется с if-проверкой наличия сертификата:
|
||||
server {
|
||||
listen 443 ssl;
|
||||
server_name valitovgaziz.ru www.valitovgaziz.ru;
|
||||
ssl_certificate /etc/letsencrypt/live/valitovgaziz.ru/fullchain.pem;
|
||||
...
|
||||
}
|
||||
А HTTP-сервер делает return 301 https://$host$request_uri только для тех доменов, у кого есть сертификат. Остальные работают по HTTP.
|
||||
Фаза 4: Certbot — один скрипт для всех
|
||||
Вместо 5 renew-скриптов:
|
||||
# /opt/renew-all.sh — единый скрипт
|
||||
certbot renew --webroot -w /var/www/certbot
|
||||
Certbot сам знает все домены, для которых получал сертификаты. --webroot с одним -w работает для всех. Убрать:
|
||||
- renewBegushiyBAshkirLatin.sh, renewBegushiyBashkir.sh, renewEasysite102.sh, renewValitovGazizCert.sh, renewYalarbaCert.sh
|
||||
- Заменить checkRenewCerts.sh на вызов certbot renew
|
||||
Фаза 5: Makefile — авто-детект изменений
|
||||
Оставить базовые цели, но добавить:
|
||||
deploy: git
|
||||
@echo "Detecting changes..."
|
||||
@git diff --name-only HEAD~1 HEAD | grep -o 'main_dc/[^/]*/' | sort -u | while read dir; do \
|
||||
service=$$(basename $$dir); \
|
||||
if grep -q "^ $$service:" docker-compose.yml; then \
|
||||
make stop_$$service build_$$service start_$$service; \
|
||||
fi \
|
||||
done
|
||||
Или ещё проще: GitHub Actions сам определяет какие сервисы изменились и запускает только их make цели.
|
||||
Дорожная карта
|
||||
Шаг Что делаем Эффект
|
||||
1 sites.yml + generate-configs.sh Добавление сайта = 1 файл
|
||||
2 Переход на per-domain HTTPS в nginx Один сайт без серта не ломает другие
|
||||
3 Упрощение certbot: единый certbot renew Удалить 5 скриптов
|
||||
4 GitHub Actions deploy workflow push → авто-деплой
|
||||
5 Makefile: deploy с авто-детектом Быстрый частичный деплой
|
||||
Generated
+3
-39
@@ -609,9 +609,6 @@
|
||||
"arm"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"glibc"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -626,9 +623,6 @@
|
||||
"arm"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"musl"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -643,9 +637,6 @@
|
||||
"arm64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"glibc"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -660,9 +651,6 @@
|
||||
"arm64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"musl"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -677,9 +665,6 @@
|
||||
"loong64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"glibc"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -694,9 +679,6 @@
|
||||
"loong64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"musl"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -711,9 +693,6 @@
|
||||
"ppc64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"glibc"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -728,9 +707,6 @@
|
||||
"ppc64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"musl"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -745,9 +721,6 @@
|
||||
"riscv64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"glibc"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -762,9 +735,6 @@
|
||||
"riscv64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"musl"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -779,9 +749,6 @@
|
||||
"s390x"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"glibc"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -796,9 +763,6 @@
|
||||
"x64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"glibc"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -813,9 +777,6 @@
|
||||
"x64"
|
||||
],
|
||||
"dev": true,
|
||||
"libc": [
|
||||
"musl"
|
||||
],
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"os": [
|
||||
@@ -1174,6 +1135,7 @@
|
||||
"integrity": "sha512-QP88BAKvMam/3NxH6vj2o21R6MjxZUAd6nlwAS/pnGvN9IVLocLHxGYIzFhg6fUQ+5th6P4dv4eW9jX3DSIj7A==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"peer": true,
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
},
|
||||
@@ -1286,6 +1248,7 @@
|
||||
"integrity": "sha512-KuOaNhcnGFN2zIPGA7wRmzF+lJA1sea7rHq17aiJ++9lzY1WWG6Jpwqwe1KNbRVPIqHmr8GLYx7jbrQcN/7/ww==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"peer": true,
|
||||
"dependencies": {
|
||||
"esbuild": "^0.27.0",
|
||||
"fdir": "^6.5.0",
|
||||
@@ -1360,6 +1323,7 @@
|
||||
"resolved": "https://registry.npmjs.org/vue/-/vue-3.5.35.tgz",
|
||||
"integrity": "sha512-cx89fnr+0kVGHiNFG6y6s0bdjypJRFNZn6x3WPstNdQR1bi1mbB7h4v5IBGTsPJU3nK1+0Iqj3Zf+hZWMieR4Q==",
|
||||
"license": "MIT",
|
||||
"peer": true,
|
||||
"dependencies": {
|
||||
"@vue/compiler-dom": "3.5.35",
|
||||
"@vue/compiler-sfc": "3.5.35",
|
||||
|
||||
@@ -3,7 +3,7 @@
|
||||
<div class="container footer-content">
|
||||
<div class="footer-info">
|
||||
<p>Уфа · Ufa · Өфө</p>
|
||||
<p>© 2025 Valitov Gaziz</p>
|
||||
<p>© 2026 Valitov Gaziz</p>
|
||||
</div>
|
||||
<div class="footer-links">
|
||||
<a href="https://t.me/valitovgaziz" target="_blank" rel="noopener noreferrer" class="footer-link">
|
||||
|
||||
Reference in New Issue
Block a user