415 lines
7.7 KiB
Markdown
415 lines
7.7 KiB
Markdown
# Deploy Production
|
|
|
|
Panduan ini untuk deploy production dengan asumsi:
|
|
|
|
- domain `abelbirdnest.id`
|
|
- reverse proxy `nginx`
|
|
- aplikasi Next.js di port `3007`
|
|
- database `PostgreSQL`
|
|
- source code dari git `https://git.iptek.co/wirabasalamah/AbelBirdNest-Stock.git`
|
|
- user service khusus `abelbirdnest`
|
|
- repo berada di:
|
|
`/var/www/abelbirdnest-web/AbelBirdNest-Stock`
|
|
|
|
## 1. Persiapan Server
|
|
|
|
Install:
|
|
|
|
- Node.js LTS
|
|
- npm
|
|
- PostgreSQL
|
|
- nginx
|
|
- certbot
|
|
|
|
Direktori aplikasi:
|
|
|
|
```bash
|
|
/var/www/abelbirdnest-web
|
|
```
|
|
|
|
## 2. Buat User OS Khusus Aplikasi
|
|
|
|
```bash
|
|
sudo useradd -r -m -d /var/www/abelbirdnest-web -s /bin/bash abelbirdnest
|
|
sudo mkdir -p /var/www/abelbirdnest-web
|
|
sudo chown -R abelbirdnest:abelbirdnest /var/www/abelbirdnest-web
|
|
```
|
|
|
|
Masuk sebagai user aplikasi:
|
|
|
|
```bash
|
|
sudo -u abelbirdnest -H bash
|
|
cd /var/www/abelbirdnest-web
|
|
```
|
|
|
|
## 3. Clone Repo
|
|
|
|
Clone normal:
|
|
|
|
```bash
|
|
git clone https://git.iptek.co/wirabasalamah/AbelBirdNest-Stock.git
|
|
cd /var/www/abelbirdnest-web/AbelBirdNest-Stock
|
|
```
|
|
|
|
Catatan:
|
|
|
|
- panduan ini mengikuti struktur clone normal di atas
|
|
- jadi `WorkingDirectory`, `.env.production`, dan semua perintah memakai path:
|
|
`/var/www/abelbirdnest-web/AbelBirdNest-Stock`
|
|
|
|
## 4. Siapkan Environment Production
|
|
|
|
Salin file contoh:
|
|
|
|
```bash
|
|
cp .env.production.example .env.production
|
|
```
|
|
|
|
Isi minimal:
|
|
|
|
```env
|
|
NODE_ENV=production
|
|
PORT=3007
|
|
APP_URL=https://abelbirdnest.id
|
|
DATABASE_URL=postgresql://abelbirdnest_app:password@127.0.0.1:5432/abelbirdnest_prod?schema=public
|
|
AUTH_SECRET=ganti-dengan-random-string-panjang
|
|
AUTH_BOOTSTRAP=false
|
|
SMTP_HOST=...
|
|
SMTP_PORT=465
|
|
SMTP_SECURE=true
|
|
SMTP_USER=...
|
|
SMTP_PASSWORD=...
|
|
SMTP_FROM=...
|
|
```
|
|
|
|
Catatan:
|
|
|
|
- `AUTH_BOOTSTRAP=false` wajib di production
|
|
- akun default dev tidak akan aktif
|
|
- `AUTH_SECRET` harus random dan panjang
|
|
|
|
## 5. Inisialisasi PostgreSQL
|
|
|
|
Masuk sebagai superuser PostgreSQL:
|
|
|
|
```bash
|
|
sudo -u postgres psql
|
|
```
|
|
|
|
Buat user database:
|
|
|
|
```sql
|
|
CREATE USER abelbirdnest_app WITH PASSWORD 'ganti-dengan-password-yang-kuat';
|
|
```
|
|
|
|
Buat database:
|
|
|
|
```sql
|
|
CREATE DATABASE abelbirdnest_prod OWNER abelbirdnest_app;
|
|
ALTER DATABASE abelbirdnest_prod OWNER TO abelbirdnest_app;
|
|
REVOKE ALL ON DATABASE abelbirdnest_prod FROM PUBLIC;
|
|
GRANT ALL PRIVILEGES ON DATABASE abelbirdnest_prod TO abelbirdnest_app;
|
|
```
|
|
|
|
Keluar:
|
|
|
|
```sql
|
|
\q
|
|
```
|
|
|
|
Tes koneksi:
|
|
|
|
```bash
|
|
psql "postgresql://abelbirdnest_app:ganti-dengan-password-yang-kuat@127.0.0.1:5432/abelbirdnest_prod"
|
|
```
|
|
|
|
Catatan:
|
|
|
|
- untuk `psql`, jangan pakai `?schema=public`
|
|
- untuk `DATABASE_URL` Prisma, tetap pakai `?schema=public`
|
|
|
|
## 6. Install Dependency dan Buat Tabel
|
|
|
|
Masih sebagai user `abelbirdnest`:
|
|
|
|
```bash
|
|
cd /var/www/abelbirdnest-web/AbelBirdNest-Stock
|
|
npm install
|
|
npm run prisma:generate
|
|
```
|
|
|
|
Load env production ke shell saat menjalankan command manual:
|
|
|
|
```bash
|
|
set -a
|
|
source .env.production
|
|
set +a
|
|
```
|
|
|
|
Jalankan migration:
|
|
|
|
```bash
|
|
npm run prisma:migrate:deploy
|
|
```
|
|
|
|
Opsional cek status:
|
|
|
|
```bash
|
|
npx prisma migrate status
|
|
```
|
|
|
|
## 7. Seed Data Awal
|
|
|
|
Untuk fresh database:
|
|
|
|
```bash
|
|
cd /var/www/abelbirdnest-web/AbelBirdNest-Stock
|
|
set -a
|
|
source .env.production
|
|
set +a
|
|
|
|
npm run seed:banks
|
|
npm run seed:currencies
|
|
```
|
|
|
|
### Khusus Grade
|
|
|
|
`seed:grades` butuh file `Grade.xls`.
|
|
|
|
Buat folder data:
|
|
|
|
```bash
|
|
mkdir -p scripts/data
|
|
```
|
|
|
|
Upload file `Grade.xls` ke:
|
|
|
|
```bash
|
|
/var/www/abelbirdnest-web/AbelBirdNest-Stock/scripts/data/Grade.xls
|
|
```
|
|
|
|
Lalu jalankan:
|
|
|
|
```bash
|
|
cd /var/www/abelbirdnest-web/AbelBirdNest-Stock
|
|
set -a
|
|
source .env.production
|
|
set +a
|
|
|
|
npm run seed:grades
|
|
```
|
|
|
|
Alternatif jika file ada di lokasi lain:
|
|
|
|
```bash
|
|
node scripts/seed-grades-from-xls.mjs /path/ke/Grade.xls
|
|
```
|
|
|
|
## 8. Buat User Pertama di PostgreSQL
|
|
|
|
Karena `AUTH_BOOTSTRAP=false`, Anda harus buat user login pertama sendiri.
|
|
|
|
### 8.1 Generate Hash Password
|
|
|
|
Ganti password contoh ini:
|
|
|
|
```bash
|
|
node -e 'const {randomBytes,scryptSync}=require("crypto"); const p="GantiPasswordKuat123!"; const salt=randomBytes(16).toString("hex"); const derived=scryptSync(p,salt,64).toString("hex"); console.log(`${salt}:${derived}`)'
|
|
```
|
|
|
|
Simpan output hash-nya.
|
|
|
|
### 8.2 Masuk ke PostgreSQL
|
|
|
|
```bash
|
|
psql "postgresql://abelbirdnest_app:password@127.0.0.1:5432/abelbirdnest_prod"
|
|
```
|
|
|
|
### 8.3 Pastikan Role `SYSTEM_ADMIN` Ada
|
|
|
|
```sql
|
|
INSERT INTO roles (code, name, created_at, updated_at)
|
|
VALUES ('SYSTEM_ADMIN', 'System Admin', NOW(), NOW())
|
|
ON CONFLICT (code) DO UPDATE
|
|
SET name = EXCLUDED.name,
|
|
updated_at = NOW();
|
|
```
|
|
|
|
### 8.4 Buat User Pertama
|
|
|
|
Ganti:
|
|
|
|
- `Nama Anda`
|
|
- `superadmin`
|
|
- `superadmin@abelbirdnest.id`
|
|
- `HASH_HASIL_LANGKAH_8_1`
|
|
|
|
```sql
|
|
INSERT INTO users (
|
|
role_id,
|
|
name,
|
|
username,
|
|
email,
|
|
email_verified_at,
|
|
phone,
|
|
password_hash,
|
|
status,
|
|
created_at,
|
|
updated_at
|
|
)
|
|
SELECT
|
|
r.id,
|
|
'Nama Anda',
|
|
'superadmin',
|
|
'superadmin@abelbirdnest.id',
|
|
NOW(),
|
|
NULL,
|
|
'HASH_HASIL_LANGKAH_8_1',
|
|
'ACTIVE',
|
|
NOW(),
|
|
NOW()
|
|
FROM roles r
|
|
WHERE r.code = 'SYSTEM_ADMIN'
|
|
ON CONFLICT (email) DO UPDATE
|
|
SET role_id = EXCLUDED.role_id,
|
|
name = EXCLUDED.name,
|
|
username = EXCLUDED.username,
|
|
email_verified_at = EXCLUDED.email_verified_at,
|
|
password_hash = EXCLUDED.password_hash,
|
|
status = EXCLUDED.status,
|
|
updated_at = NOW();
|
|
```
|
|
|
|
Verifikasi:
|
|
|
|
```sql
|
|
SELECT u.id, u.name, u.username, u.email, u.status, r.code AS role
|
|
FROM users u
|
|
JOIN roles r ON r.id = u.role_id
|
|
WHERE u.email = 'superadmin@abelbirdnest.id';
|
|
```
|
|
|
|
## 9. Build Production
|
|
|
|
```bash
|
|
cd /var/www/abelbirdnest-web/AbelBirdNest-Stock
|
|
set -a
|
|
source .env.production
|
|
set +a
|
|
|
|
npm run build
|
|
```
|
|
|
|
## 10. Jalankan App dengan systemd
|
|
|
|
File service repo sudah disiapkan untuk struktur subfolder ini:
|
|
|
|
```bash
|
|
deploy/systemd/abelbirdnest-web.service
|
|
```
|
|
|
|
Pasang:
|
|
|
|
```bash
|
|
sudo cp /var/www/abelbirdnest-web/AbelBirdNest-Stock/deploy/systemd/abelbirdnest-web.service /etc/systemd/system/
|
|
sudo chown -R abelbirdnest:abelbirdnest /var/www/abelbirdnest-web/AbelBirdNest-Stock
|
|
sudo systemctl daemon-reload
|
|
sudo systemctl enable abelbirdnest-web
|
|
sudo systemctl restart abelbirdnest-web
|
|
sudo systemctl status abelbirdnest-web
|
|
```
|
|
|
|
Verifikasi port:
|
|
|
|
```bash
|
|
ss -ltnp | grep 3007
|
|
curl http://127.0.0.1:3007/api/v1/health
|
|
```
|
|
|
|
Kalau service gagal, cek:
|
|
|
|
```bash
|
|
sudo systemctl cat abelbirdnest-web
|
|
sudo journalctl -u abelbirdnest-web -n 100 --no-pager
|
|
which npm
|
|
```
|
|
|
|
## 11. Pasang Nginx Tahap 1: HTTP Dulu
|
|
|
|
Jangan langsung pakai config HTTPS sebelum sertifikat ada.
|
|
|
|
Pakai file ini dulu:
|
|
|
|
```bash
|
|
deploy/nginx/abelbirdnest.id.http.conf
|
|
```
|
|
|
|
Pasang:
|
|
|
|
```bash
|
|
sudo cp /var/www/abelbirdnest-web/AbelBirdNest-Stock/deploy/nginx/abelbirdnest.id.http.conf /etc/nginx/sites-available/abelbirdnest.id.conf
|
|
sudo ln -sf /etc/nginx/sites-available/abelbirdnest.id.conf /etc/nginx/sites-enabled/abelbirdnest.id.conf
|
|
sudo nginx -t
|
|
sudo systemctl reload nginx
|
|
```
|
|
|
|
Tes:
|
|
|
|
```bash
|
|
curl http://abelbirdnest.id/api/v1/health
|
|
```
|
|
|
|
## 12. Buat Sertifikat SSL
|
|
|
|
Setelah HTTP sudah hidup:
|
|
|
|
```bash
|
|
sudo certbot --nginx -d abelbirdnest.id -d www.abelbirdnest.id
|
|
```
|
|
|
|
## 13. Ganti ke Config HTTPS Final
|
|
|
|
Setelah sertifikat berhasil dibuat, baru pakai config final:
|
|
|
|
```bash
|
|
sudo cp /var/www/abelbirdnest-web/AbelBirdNest-Stock/deploy/nginx/abelbirdnest.id.conf /etc/nginx/sites-available/abelbirdnest.id.conf
|
|
sudo nginx -t
|
|
sudo systemctl reload nginx
|
|
```
|
|
|
|
Verifikasi:
|
|
|
|
```bash
|
|
curl https://abelbirdnest.id/api/v1/health
|
|
```
|
|
|
|
## 14. Update Deployment Berikutnya
|
|
|
|
```bash
|
|
cd /var/www/abelbirdnest-web/AbelBirdNest-Stock
|
|
git pull origin main
|
|
|
|
set -a
|
|
source .env.production
|
|
set +a
|
|
|
|
npm install
|
|
npm run prisma:generate
|
|
npm run prisma:migrate:deploy
|
|
npm run build
|
|
sudo systemctl restart abelbirdnest-web
|
|
sudo systemctl status abelbirdnest-web
|
|
```
|
|
|
|
## 15. Smoke Test Setelah Live
|
|
|
|
Cek minimal:
|
|
|
|
- login dengan user `SYSTEM_ADMIN`
|
|
- dashboard terbuka
|
|
- health check OK
|
|
- buat master `bank`, `currency`, `grade` tampil
|
|
- buat transaksi sederhana
|
|
- logout/login ulang
|
|
- email reset/verifikasi jika SMTP sudah aktif
|