Files
cabutan-bertuah-koipb/DEPLOYMENT.md
2026-06-24 20:35:01 +08:00

6.6 KiB
Raw Blame History

DEPLOYMENT.md — Sistem MAT KOIPB (Docker · Ubuntu Server)

Panduan deploy aplikasi Kehadiran & Cabutan Bertuah MAT KOIPB menggunakan Docker pada server Ubuntu. Stack: Nginx + PHP 8.4-FPM (Laravel) + MariaDB 11 — semua dalam container, tiada pemasangan PHP/DB pada host.

Kenapa MariaDB, bukan MySQL 8? Imej mysql:8 (Oracle Linux) memerlukan CPU aras x86-64-v2 dan akan crash (Fatal glibc error: CPU does not support x86-64-v2) pada CPU/VM lama atau jenis CPU VM generik (qemu64/kvm64). MariaDB serasi penuh dengan Laravel (DB_CONNECTION=mysql kekal) dan berjalan pada CPU lama.

UI guna CDN + CSS statik (public/css/koipb.css) — tiada langkah build Node/Vite.


Keperluan Server

Komponen Minimum Disyorkan
OS Ubuntu 22.04 LTS Ubuntu 24.04 LTS
CPU 2 core 4 core
RAM 2 GB 4 GB
Storage 10 GB 20 GB
Docker 24.x Latest stable
Docker Compose 2.x Latest stable

Untuk 150200 peserta, server kecil sudah memadai.


Struktur Fail Docker

/srv/koipb/
├── .env.docker                # disalin dari .env.docker.example (JANGAN commit)
├── .env.docker.example        # templat
├── Dockerfile                 # imej PHP-FPM (Laravel)
├── docker-compose.yml         # dev (nginx + app + mysql)
├── docker-compose.prod.yml    # override production
├── docker/
│   ├── entrypoint.sh          # wait-db, composer, key:generate, migrate, seed, cache
│   ├── nginx/default.conf
│   └── php/{php.ini, php-dev.ini, php-prod.ini}
└── ... (kod Laravel)

Langkah Deployment Pertama Kali

1. Persediaan server

sudo apt update && sudo apt upgrade -y
curl -fsSL https://get.docker.com | sh
sudo usermod -aG docker $USER
newgrp docker
docker --version && docker compose version

2. Dapatkan kod

sudo mkdir -p /srv/koipb && sudo chown $USER:$USER /srv/koipb
cd /srv/koipb
git clone <repo-url> .

3. Konfigurasi environment

cp .env.docker.example .env.docker
nano .env.docker

Guna nama fail .env.docker (bukan .env) supaya tidak berlanggar dengan .env tempatan untuk php artisan serve.

Wajib tukar:

Pemboleh ubah Nota
APP_KEY Biar kosong — entrypoint jana automatik kali pertama
APP_URL cth https://mat.koipb.gov.my
APP_PORT Port loopback unik (cth 8009) — host nginx reverse-proxy ke sini. Elak langgar projek lain (spr2026=8007, taklimat=8008)
DB_PASSWORD dan MYSQL_PASSWORD password user koipbmesti sama
MYSQL_ROOT_PASSWORD password root MySQL container
SEED_DEMO true = isi 200 anggota + 21 hadiah contoh; false = data kosong (import sendiri)

DB_HOST/MYSQL_* jangan diubah namanya. MYSQL_USER mesti koipb (BUKAN root — MySQL menolaknya).

# Letak logo sebenar (kalau belum):
cp /path/ke/logo.jpg public/images/logo-koipb.jpg

5. Bina & jalankan (production)

docker compose --env-file .env.docker \
  -f docker-compose.yml -f docker-compose.prod.yml up -d --build

Entrypoint akan automatik: tunggu MySQL → composer install → key:generatemigrate --force → seed peranan/pengguna (+ demo jika SEED_DEMO=true) → cache config/route/view.

Semak:

docker compose ps
docker compose logs -f app        # tunggu "✅ Aplikasi bersedia."

Buka http://<IP-server> (atau APP_URL).


Login Default

Kata laluan semua: passwordWAJIB tukar selepas log masuk pertama (atau ubah dalam RoleUserSeeder sebelum deploy).

Peranan E-mel
Admin admin@koipb.test
Petugas Kaunter kaunter@koipb.test
Petugas Cabutan cabutan@koipb.test

Operasi Harian

# Status / log
docker compose ps
docker compose logs -f app

# Masuk shell artisan
docker compose exec app php artisan <command>

# Backup database (penting sebelum & selepas event!)
docker compose exec mysql sh -c 'mysqldump -u root -p"$MYSQL_ROOT_PASSWORD" koipb_mat' > backup-$(date +%F-%H%M).sql

# Restore
cat backup.sql | docker compose exec -T mysql sh -c 'mysql -u root -p"$MYSQL_ROOT_PASSWORD" koipb_mat'

# Henti / mula semula
docker compose --env-file .env.docker -f docker-compose.yml -f docker-compose.prod.yml down
docker compose --env-file .env.docker -f docker-compose.yml -f docker-compose.prod.yml up -d

Data MySQL kekal dalam named volume koipb_db_data walaupun container dipadam. docker compose down (tanpa -v) tidak memadam data. Jangan guna down -v semasa event.


Kemaskini Versi (Redeploy)

cd /srv/koipb
git pull
docker compose --env-file .env.docker -f docker-compose.yml -f docker-compose.prod.yml up -d --build
# Entrypoint akan migrate + cache semula automatik.

Reverse Proxy + HTTPS (host nginx)

Server ini sudah ada host nginx yang dedah domain awam dan proksi ke port loopback setiap projek (spr2026 → 8007, taklimat → 8008). KOIPB guna 8009 (APP_PORT=8009, diikat 127.0.0.1:8009:80).

Tambah vhost host nginx (cth /etc/nginx/sites-available/koipb.conf):

server {
    server_name mat.koipb.gov.my;
    location / {
        proxy_pass         http://127.0.0.1:8009;
        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;
    }
}

Kemudian:

sudo ln -s /etc/nginx/sites-available/koipb.conf /etc/nginx/sites-enabled/
sudo nginx -t && sudo systemctl reload nginx
sudo certbot --nginx -d mat.koipb.gov.my      # HTTPS

Penyelesaian Masalah

Masalah Tindakan
address already in use (port) Port APP_PORT dah diguna projek lain. Tukar ke port loopback bebas dalam .env.docker (cth 8009) & up semula
MySQL CPU does not support x86-64-v2 Guna mariadb:11.4 (sudah ditetapkan), bukan mysql:8
app asyik restart docker compose logs app — biasanya DB belum sedia, .env.docker salah, atau cache bootstrap/cache/config.php basi
419 Page Expired / log masuk gagal APP_KEY kosong — docker compose exec app php artisan key:generate --force lalu docker compose restart app
502 Bad Gateway container app belum naik / belum siap composer install; tunggu log "Aplikasi bersedia"
Tukar .env tak berkesan docker compose exec app php artisan config:clear dan restart
Reset data untuk event baharu Log masuk admin → Tetapan & Reset, atau docker compose exec app php artisan migrate:fresh --seed --force