diff --git a/serverinfo/192.168.1.26/README.md b/serverinfo/192.168.1.26/README.md new file mode 100644 index 0000000..dcfa849 --- /dev/null +++ b/serverinfo/192.168.1.26/README.md @@ -0,0 +1,178 @@ +# Server Information: sql@192.168.1.26 + +เอกสารสรุปรายละเอียดสภาพแวดล้อม (Environment), Runtimes (Node, Bun, PM2), ฐานข้อมูล (PostgreSQL, MariaDB), Nginx, และข้อกำหนดสำหรับการเขียน Git `post-receive` hook บนเซิร์ฟเวอร์ `192.168.1.26` + +--- + +## 1. ข้อมูลระบบทั่วไป (System Overview) + +| รายการ | รายละเอียด | +| :--- | :--- | +| **IP Address** | `192.168.1.26` | +| **Hostname** | `sql` | +| **SSH User** | `sql` (`uid=1000`, `gid=1000`) | +| **Home Directory** | `/home/sql` | +| **OS** | Ubuntu 22.04.5 LTS (Jammy Jellyfish) | +| **Kernel** | Linux 5.15.0-191-generic x86_64 | +| **CPU** | 12 vCPUs (QEMU Virtual CPU version 2.5+) | +| **RAM** | Total: **15 GiB** (Used: ~1.7 GiB, Available: ~13 GiB, Swap: 4.0 GiB) | +| **Disk** | `/` (LVM `ubuntu--vg-ubuntu--lv`): **391 GiB** (Used: 44 GiB / 12%, Avail: **331 GiB**) | +| **User Groups** | `sql (1000)`, `adm (4)`, `cdrom (24)`, `sudo (27)`, `dip (30)`, `plugdev (46)`, `lxd (110)` | +| **Sudo Access** | ต้องการ Password (Non-interactive sudo ไม่สามารถรันแบบไร้รหัสผ่านได้) | + +--- + +## 2. สรุป Runtimes & เครื่องมือสำหรับ Post-Receive Hook + +> **ข้อควรระวังสำคัญสำหรับ Post-Receive Hook:** +> เมื่อ Git รัน hook ผ่าน SSH (`non-login non-interactive shell`), ค่า `$PATH` จะถูกจำกัดเป็นค่าเริ่มต้นของระบบ (มักมีแค่ `/usr/bin:/bin`) ทำให้หา `bun` ไม่เจอ +> **ต้อง export PATH เสมอที่ต้นสคริปต์ hook:** +> ```bash +> export PATH="/home/sql/.bun/bin:/usr/local/bin:/usr/bin:/bin:$PATH" +> ``` + +| เครื่องมือ | Version | Path แบบ Absolute | หมายเหตุ | +| :--- | :--- | :--- | :--- | +| **Bun** | `1.3.8` | `/home/sql/.bun/bin/bun` | รันเร็ว เหมาะสำหรับ `bun install`, `bun run build`, และ Elysia/Backend | +| **Node.js** | `v25.2.0` | `/usr/bin/node` | ระบบไม่ได้ใช้ NVM (ลงผ่าน Package Manager ไว้ที่ `/usr/bin/node`) | +| **NPM** | `11.6.2` | `/usr/bin/npm` | | +| **PM2** | `6.0.14` | `/usr/bin/pm2` | มี Systemd Service `pm2-sql.service` เปิดใช้งานอัตโนมัติ (Boot startup) | +| **Git** | `2.34.1` | `/usr/bin/git` | | +| **Python** | `3.10.12` | `/usr/bin/python3` | มี venv อยู่ในบางโปรเจกต์ | + +--- + +## 3. สถานะ PM2 & โปรเซสที่กำลังทำงานอยู่ (PM2 Processes) + +PM2 Service: `pm2-sql` (Active / Enabled on boot) + +| ID | Process Name | Mode | Interpreter | Script / Entry Point | Working Directory (CWD) | Port / Usage | +| :---: | :--- | :---: | :---: | :--- | :--- | :---: | +| **0** | `pm2-logrotate` | module | node | - | - | Auto-rotate logs | +| **1** | `ddc hr backend` | fork | `/home/sql/.bun/bin/bun` | `apps/backend/dist/index.js` | `/home/sql/code/ddc_ops/apps/backend` | **5000** | +| **2** | `aroka-backend` | fork | `none` (Bun directly) | `/home/sql/.bun/bin/bun run ...` | `/home/sql/code/aro/apps/backend` | **4000** | +| **3** | `shop-ddcth` | fork | `node` (v25.2.0) | `apps/shop.ddcth.com/server.js` | `/home/sql/code/ddc_ops/apps/shop.ddcth.com` | **3001** (Next.js Standalone) | +| **4** | `rebrand-dev` | fork | `none` (bash) | `bun run dev -- --port 4545` | `/home/sql/code/rebrand` | **4545** (Vite Dev Server) | +| **5** | `check-order-production` | fork | `bash` | `run_backend.sh` (uvicorn FastAPI) | `/home/sql/code/nick/check-order-production` | **8000** | + +--- + +## 4. ฐานข้อมูล (PostgreSQL & MariaDB) + +### PostgreSQL (Local Instance) +* **Version:** PostgreSQL 14.24 (Ubuntu 14.24-0ubuntu0.22.04.1) +* **Cluster:** `14/main` (Status: `online`) +* **Port:** `5432` (Listen on `127.0.0.1:5432`) +* **Local Connection URL (ผ่านการทดสอบสำเร็จ):** + ```text + postgresql://postgres:password@localhost:5432/postgres + ``` +* **ฐานข้อมูลที่มีอยู่ปัจจุบัน:** + * `arokamwedweb` (Owner: `postgres`) + * `postgres` (Owner: `postgres`) +* **การสร้าง Database ใหม่สำหรับระบบ CMS:** + ```bash + psql 'postgresql://postgres:password@localhost:5432/postgres' -c "CREATE DATABASE homaroma_db;" + ``` + Connection string สำหรับ `.env`: + ```text + DATABASE_URL="postgresql://postgres:password@localhost:5432/homaroma_db?schema=public" + ``` + +### MariaDB / MySQL +* **Version:** 10.6.22-MariaDB +* **Port:** `3306` (Listen on `0.0.0.0:3306`) +* **Status:** Active (running) + +--- + +## 5. แผนผังพอร์ตที่ใช้งานอยู่บน Server (Port Allocation Map) + +ห้ามตั้งพอร์ตซ้ำกับเซอร์วิสเหล่านี้ในการ Deploy: + +| Port | Protocol / Service | Process / Application | +| :---: | :--- | :--- | +| **22** | SSH | OpenSSH Server | +| **80** | HTTP | Nginx Reverse Proxy & Web Server | +| **3001** | HTTP | `shop-ddcth` (Next.js SSR / Standalone) | +| **3306** | MySQL | MariaDB 10.6 | +| **4000** | HTTP | `aroka-backend` (Bun API) | +| **4545** | HTTP | `rebrand-dev` (Vite dev) | +| **5000** | HTTP | `ddc hr backend` (Bun Elysia API) | +| **5432** | PostgreSQL | PostgreSQL 14 | +| **6333 / 6334** | HTTP / gRPC | Qdrant Vector Database | +| **8000** | HTTP | `check-order-production` (FastAPI / Uvicorn) | + +> 💡 **พอร์ตแนะนำสำหรับระบบใหม่บน Server นี้:** +> * Backend API (Elysia/Node): **`3005`** หรือ **`3050`** +> * Website (Next.js SSR): **`3002`** หรือ **`3003`** (พอร์ต `3002` ว่างอยู่) + +--- + +## 6. สิทธิ์และการจัดเก็บไฟล์ (Filesystem Structure & Permissions) + +### 1) Git Bare Repositories +* ตำแหน่งจัดเก็บ: `/home/sql/git/.git` +* Repositories บนเครื่อง: + * `/home/sql/git/bigbike.git` (Symlink: `bigbike.ddcsprocket.com.git`) ⚡ **[สร้างใหม่สำหรับ bigbike.ddcsprocket.com]** + * `/home/sql/git/aro.git` + * `/home/sql/git/ddc_ops.git` + * `/home/sql/git/rebrand.git` + + +### 2) Checked-out Code & Backend Run Dir +* ตำแหน่งจัดเก็บ: `/home/sql/code//` +* ตัวอย่างที่มีอยู่เดิม: + * `/home/sql/code/ddc_ops` + * `/home/sql/code/aro` + * `/home/sql/code/rebrand` + +### 3) Web Root สำหรับ Static Files (Nginx) +* Root: `/var/www/html/` +* **สิทธิ์การเขียน:** + * โฟลเดอร์ `/var/www/html` หลักเป็นของ `root:root` (User `sql` ไม่สามารถ `mkdir` ใต้ `/var/www/html` โดยตรงได้) + * ต้องให้ root สร้างโฟลเดอร์ไว้ล่วงหน้าและตั้งสิทธิ์เป็น `sql:sql` เช่น: + ```bash + sudo mkdir -p /var/www/html/homaroma + sudo chown -R sql:sql /var/www/html/homaroma + ``` + * หรือเลือก Deploy static files ไว้ภายใน `/home/sql/projects/...` แล้วให้ Nginx ชี้เข้ามา (ต้องเปิด permission ให้อ่านได้) + +--- + +## 7. Nginx Virtual Hosts ที่ตั้งค่าไว้ปัจจุบัน + +Nginx รันอยู่ที่พอร์ต `80` โดยมี vhosts ใน `/etc/nginx/sites-enabled/`: +* `admindemo.arokathaimed.com` ➔ `/var/www/html/aroka_admin` +* `demo.arokathaimed.com` ➔ `/var/www/html/arokamedweb` +* `ops.ddcth.com` & Default Server ➔ `/var/www/html/ddc_ops` +* `luckydraw.ddcth.com` ➔ `/var/www/html/luckydraw` +* `shop.ddcsprocket.co.th` ➔ `/var/www/html/shop.ddcth.com` + +--- + +## 8. ข้อสรุปและ Checklist สำหรับสร้าง Post-Receive Hook + +1. **ระบุ Binary Paths ชัดเจน:** + ```bash + BUN="/home/sql/.bun/bin/bun" + PM2="/usr/bin/pm2" + NODE="/usr/bin/node" + export PATH="/home/sql/.bun/bin:/usr/local/bin:/usr/bin:/bin:$PATH" + ``` +2. **สร้าง Git Bare Repo:** + ```bash + mkdir -p /home/sql/git/cms.git + cd /home/sql/git/cms.git + git init --bare + ``` +3. **เตรียม Directory สำหรับ Code:** + ```bash + mkdir -p /home/sql/code/cms + ``` +4. **เตรียม Directory สำหรับ Static Deploy (SPA/Admin):** + ```bash + # ต้องสร้างด้วยสิทธิ์ที่ sql สามารถเขียนได้ + mkdir -p /var/www/html/cms_spa /var/www/html/cms_admin + ``` +5. **สร้างไฟล์ hook ที่ `/home/sql/git/.git/hooks/post-receive` และ `chmod +x`** diff --git a/serverinfo/192.168.1.26/bigbike-post-receive b/serverinfo/192.168.1.26/bigbike-post-receive new file mode 100644 index 0000000..68431ec --- /dev/null +++ b/serverinfo/192.168.1.26/bigbike-post-receive @@ -0,0 +1,110 @@ +#!/bin/bash + +# ============================================================================== +# Bigbike Project (bigbike.ddcsprocket.com) +# Deployment Script (post-receive hook) on sql@192.168.1.26 +# Role: Application Runner (PM2 / Bun / Node) - No local Nginx +# ============================================================================== + +set -e +export PATH="/home/sql/.bun/bin:/usr/local/bin:/usr/bin:/bin:$PATH" + +# 1. PATH CONFIG +GIT_DIR="/home/sql/git/bigbike.git" +WORK_DIR="/home/sql/code/bigbike" +BRANCH="master" +TEMP_DIR="/tmp/bigbike_build_$(date +%s)" + +# 2. RUNTIMES & EXECUTABLES +BUN="/home/sql/.bun/bin/bun" +NODE="/usr/bin/node" +PM2="/usr/bin/pm2" + +# 3. PM2 PROCESS NAMES +PM2_NAME_BACKEND="bigbike-backend" +PM2_NAME_WEBSITE="bigbike-website" + +# 4. ASSIGNED PORTS (Direct forwarded from outer proxy / gateway) +# (Port 3001 is shop-ddcth, 4000 is aroka, 5000 is ddc hr) +BACKEND_PORT=3005 +SSR_PORT=3002 + +# 5. ENVIRONMENT VARIABLES +export PORT="$SSR_PORT" +export BACKEND_PORT="$BACKEND_PORT" +export VITE_API_URL="https://api.bigbike.ddcsprocket.com/api" +export NEXT_PUBLIC_API_URL="https://api.bigbike.ddcsprocket.com/api" + +echo "========================================================" +echo "🚀 [Bigbike] Starting Deployment on 192.168.1.26..." +echo "========================================================" + +# A. Checkout code to Work Directory +mkdir -p "$WORK_DIR" +echo ">>> Checking out branch $BRANCH to $WORK_DIR..." +git --work-tree="$WORK_DIR" --git-dir="$GIT_DIR" checkout -f "$BRANCH" + +cd "$WORK_DIR" + +# B. Install dependencies +if [ -f "package.json" ]; then + echo ">>> Installing dependencies with Bun..." + $BUN install +fi + +# C. Setup Backend (if apps/backend exists) +if [ -d "apps/backend" ]; then + echo ">>> Setting up Backend..." + cd "$WORK_DIR/apps/backend" + + if [ -f "prisma/schema.prisma" ]; then + echo ">>> Generating Prisma Client..." + $BUN x prisma generate + + echo ">>> Auto-updating Database Schema..." + if [ -d "prisma/migrations" ]; then + echo ">>> Running Prisma migrate deploy..." + $BUN x prisma migrate deploy || echo "⚠️ migrate deploy had notices, falling back to db push..." + fi + echo ">>> Syncing schema with db push..." + $BUN x prisma db push --accept-data-loss + fi + + echo ">>> Restarting PM2 process: $PM2_NAME_BACKEND..." + if $PM2 describe "$PM2_NAME_BACKEND" > /dev/null 2>&1; then + $PM2 restart "$PM2_NAME_BACKEND" --update-env + else + echo ">>> Starting $PM2_NAME_BACKEND for the first time on port $BACKEND_PORT..." + PORT=$BACKEND_PORT $PM2 start "$BUN" --name "$PM2_NAME_BACKEND" --cwd "$WORK_DIR/apps/backend" -- run src/index.ts + fi + cd "$WORK_DIR" +fi + +# D. Setup Website SSR (if apps/website exists) +if [ -d "apps/website" ]; then + echo ">>> Building Next.js Website..." + cd "$WORK_DIR/apps/website" + NODE_ENV=production $BUN run build + + echo ">>> Restarting PM2 process: $PM2_NAME_WEBSITE..." + if $PM2 describe "$PM2_NAME_WEBSITE" > /dev/null 2>&1; then + PORT=$SSR_PORT $PM2 restart "$PM2_NAME_WEBSITE" --update-env + else + echo ">>> Starting $PM2_NAME_WEBSITE for the first time on port $SSR_PORT..." + # Check standalone server or standard next start + if [ -f ".next/standalone/server.js" ]; then + PORT=$SSR_PORT $PM2 start "$NODE" --name "$PM2_NAME_WEBSITE" --cwd "$WORK_DIR/apps/website/.next/standalone" -- server.js + else + PORT=$SSR_PORT $PM2 start "$BUN" --name "$PM2_NAME_WEBSITE" --cwd "$WORK_DIR/apps/website" -- run start + fi + fi + cd "$WORK_DIR" +fi + +# E. Save PM2 state +$PM2 save + +echo "========================================================" +echo "✅ [Bigbike] Deployment Finished Successfully!" +echo "========================================================" +$PM2 status diff --git a/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/docs/README.md b/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/docs/README.md new file mode 100644 index 0000000..87386cf --- /dev/null +++ b/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/docs/README.md @@ -0,0 +1,157 @@ +# Bigbike Platform Deployment Guide & System Architecture +### Target Domain: `bigbike.ddcsprocket.com` +### Target Server: `sql@192.168.1.26` + +--- + +## 1. บทบาทของเซิร์ฟเวอร์ (System Architecture & Role) + +* **Server IP:** `192.168.1.26` (Hostname: `sql`, User: `sql`) +* **บทบาท (Role):** **Application Runner เท่านั้น (Node.js / Bun / PM2)** +* **ขอบเขตการทำงาน:** + * รัน API Service (Elysia / Bun) และ Website SSR (Next.js Standalone / Node.js) ภายใต้การควบคุมของ PM2 + * **ไม่ต้องตั้งค่า Nginx บนเครื่องนี้** เนื่องจากระบบมี Gateway / Reverse Proxy ภายนอกทำการ Port-Forward หรือ Proxy ส่ง Traffic เข้ามายังพอร์ตของแต่ละ Service โดยตรง + +``` +[ User Request ] + │ + ▼ +[ External Gateway / Firewall / Nginx Proxy ] + │ + ├── Forward Traffic (Domain: bigbike.ddcsprocket.com) ──► 192.168.1.26:3002 (Next.js SSR) + └── Forward Traffic (Domain: api.bigbike.ddcsprocket.com) ─► 192.168.1.26:3005 (Elysia API) +``` + +--- + +## 2. โครงสร้าง Git Repository & การเชื่อมต่อ (Git Info) + +### ฝั่ง Server (`192.168.1.26`) +| รายการ | ตำแหน่ง Path บน Server | รายละเอียด | +| :--- | :--- | :--- | +| **Bare Repository** | `/home/sql/git/bigbike.git` | จุดรับ Git Push จากเครื่อง Local | +| **Symlink Alias** | `/home/sql/git/bigbike.ddcsprocket.com.git` | ชี้ไปยัง `bigbike.git` | +| **Working Directory** | `/home/sql/code/bigbike` | โฟลเดอร์แตกไฟล์ Source Code และรันโปรเจกต์ | +| **Hook Script** | `/home/sql/git/bigbike.git/hooks/post-receive` | สคริปต์สั่ง Build และ Restart PM2 อัตโนมัติ (`chmod +x`) | + +### ฝั่ง Local (`d:\cms`) +* **Git Remote Name:** `bigbike` +* **Remote URL:** `sql@192.168.1.26:/home/sql/git/bigbike.git` +* **คำสั่ง Deploy:** + ```powershell + git push bigbike master + ``` + +--- + +## 3. Runtimes & สภาพแวดล้อมที่ใช้ในการประมวลผล + +| เครื่องมือ | Version | Path บนเครื่อง 192.168.1.26 | หน้าที่ในไปป์ไลน์ | +| :--- | :--- | :--- | :--- | +| **Bun** | `1.3.8` | `/home/sql/.bun/bin/bun` | รัน `bun install`, `bun run build`, รัน Elysia Backend | +| **Node.js** | `v25.2.0` | `/usr/bin/node` | รัน Next.js Standalone SSR Server | +| **PM2** | `6.0.14` | `/usr/bin/pm2` | Process Manager ควบคุม Service ให้รันตลอดเวลา | +| **PostgreSQL** | `14.24` | `localhost:5432` | ฐานข้อมูล Local | + +> ⚠️ **ข้อควรระวังเรื่อง PATH ใน Post-Receive Hook:** +> SSH non-interactive session จะไม่โหลด `~/.bashrc` อัตโนมัติ ในหัวสคริปต์ `post-receive` ต้อง export PATH เสมอ: +> ```bash +> export PATH="/home/sql/.bun/bin:/usr/local/bin:/usr/bin:/bin:$PATH" +> ``` + +--- + +## 4. แผนผังพอร์ต & การจัดการ PM2 (Process Management) + +### พอร์ตและ Process ของ Bigbike (เปิดใหม่) +| Service | PM2 Process Name | Port | Runtime / Command | CWD | +| :--- | :--- | :---: | :--- | :--- | +| **Backend API** | `bigbike-backend` | **`3005`** | `bun run src/index.ts` | `/home/sql/code/bigbike/apps/backend` | +| **Website (SSR)** | `bigbike-website` | **`3002`** | `node server.js` (.next/standalone) | `/home/sql/code/bigbike/apps/website` | + +### ตารางตรวจสอบพอร์ตเดิมบน Server (เพื่อป้องกันพอร์ตชน) +| Port | Service เดิมที่ใช้งานอยู่ | สถานะ | +| :---: | :--- | :---: | +| **3001** | `shop-ddcth` (Next.js) | ใช้งานอยู่ | +| **3002** | *ว่าง* ➔ **กำหนดให้ `bigbike-website`** | ✅ ใช้งานได้ | +| **3005** | *ว่าง* ➔ **กำหนดให้ `bigbike-backend`** | ✅ ใช้งานได้ | +| **3306** | MariaDB Server | ใช้งานอยู่ | +| **4000** | `aroka-backend` | ใช้งานอยู่ | +| **4545** | `rebrand-dev` (Vite) | ใช้งานอยู่ | +| **5000** | `ddc hr backend` (Bun) | ใช้งานอยู่ | +| **5432** | PostgreSQL 14 Local | ใช้งานอยู่ | +| **6333 / 6334** | Qdrant Vector DB | ใช้งานอยู่ | +| **8000** | `check-order-production` (Python FastAPI) | ใช้งานอยู่ | + +--- + +## 5. การตั้งค่าฐานข้อมูล & ไฟล์ .env (Database & Environment Config) + +### 1) สถานะฐานข้อมูล PostgreSQL +* **สถานะปัจจุบัน:** ✅ **สร้าง Database `bigbike_db` บน `192.168.1.26` เรียบร้อยแล้ว** +* **Host:** `localhost:5432` +* **User:** `postgres` +* **Password:** `password` +* **Connection String:** + ```text + DATABASE_URL="postgresql://postgres:password@localhost:5432/bigbike_db?schema=public" + ``` + +### 2) ตำแหน่งไฟล์ .env ที่ติดตั้งไว้บน Server (`192.168.1.26`) +* **Backend API:** `/home/sql/code/bigbike/apps/backend/.env` + ```env + PORT=3005 + DATABASE_URL="postgresql://postgres:password@localhost:5432/bigbike_db?schema=public" + NODE_ENV=production + APP_URL="https://api.bigbike.ddcsprocket.com" + BACKEND_PUBLIC_URL="https://api.bigbike.ddcsprocket.com" + CORS_ORIGIN="https://admin.bigbike.ddcsprocket.com,https://spa.bigbike.ddcsprocket.com,https://bigbike.ddcsprocket.com,http://localhost:3000,http://localhost:3002" + JWT_SECRET="bigbike-secret-key-prod-2026-ddc" + OMISE_SECRET_KEY="" + ``` +* **Website (Next.js SSR):** `/home/sql/code/bigbike/apps/website/.env` + ```env + PORT=3002 + NODE_ENV=production + NEXT_PUBLIC_API_URL="https://api.bigbike.ddcsprocket.com/api" + ``` +*(ไฟล์ template ถูกสำรองไว้ใน [backend.env](file:///d:/cms/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/backend.env) และ [website.env](file:///d:/cms/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/website.env))* + + +--- + +## 6. วงจรการทำงานของ Post-Receive Hook (Deployment Pipeline) + +เมื่อมีการ `git push bigbike master` สคริปต์ `/home/sql/git/bigbike.git/hooks/post-receive` จะทำงานตามลำดับดังนี้: + +1. **Checkout Source Code:** แตกไฟล์ล่าสุดจาก Git ลงที่ `/home/sql/code/bigbike` +2. **Install Dependencies:** สั่งรัน `$BUN install` ใน root monorepo +3. **Backend Service & Auto Database Migration:** + * รัน `$BUN x prisma generate` (อัปเดต Prisma Client Types) + * รัน `$BUN x prisma migrate deploy` (นำ migration files ใหม่ไป Apply ลง DB อัตโนมัติ) + * รัน `$BUN x prisma db push --accept-data-loss` (ซิงก์ schema เข้า DB ทันที ป้องกันกรณีแก้ schema.prisma โดยไม่ได้รัน migrate dev) + * สั่ง `pm2 restart bigbike-backend --update-env` (หากยังไม่เคยรัน จะสั่ง `pm2 start` บนพอร์ต `3005`) +4. **Website Service (Next.js SSR):** + * บิลด์ Next.js ด้วย `NODE_ENV=production $BUN run build` + * สั่ง `pm2 restart bigbike-website --update-env` (หากยังไม่เคยรัน จะสั่งรัน standalone `server.js` บนพอร์ต `3002`) +5. **Persist State:** สั่ง `pm2 save` เพื่อบันทึกรายชื่อโปรเซส ให้ฟื้นตัวอัตโนมัติเมื่อเซิร์ฟเวอร์รีบูต + +--- + +## 7. คำสั่งที่ใช้ในการตรวจสอบและแก้ไขปัญหา (Runbook & Troubleshooting) + +### ตรวจสอบสถานะและ Logs บน Server: +```bash +# ดูสถานะ PM2 ทั้งหมด +ssh sql@192.168.1.26 "pm2 status" + +# ดู Logs สดของ Backend +ssh sql@192.168.1.26 "pm2 logs bigbike-backend --lines 100" + +# ดู Logs สดของ Website SSR +ssh sql@192.168.1.26 "pm2 logs bigbike-website --lines 100" + +# ทดสอบ Curl พอร์ตภายในเครื่อง +ssh sql@192.168.1.26 "curl -I http://localhost:3005" +ssh sql@192.168.1.26 "curl -I http://localhost:3002" +``` diff --git a/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/git-info/README.md b/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/git-info/README.md new file mode 100644 index 0000000..e11c3a7 --- /dev/null +++ b/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/git-info/README.md @@ -0,0 +1,23 @@ +# Git Configuration for bigbike.ddcsprocket.com + +## Remote Configuration +* **Server:** `192.168.1.26` +* **SSH User:** `sql` +* **Bare Repo (Server):** `/home/sql/git/bigbike.git` +* **Symlink (Server):** `/home/sql/git/bigbike.ddcsprocket.com.git` +* **Working Directory (Server):** `/home/sql/code/bigbike` +* **Hook File (Server):** `/home/sql/git/bigbike.git/hooks/post-receive` + +## Local Git Setup (Machine) +* **Remote Name:** `bigbike` +* **Remote Push URL:** `sql@192.168.1.26:/home/sql/git/bigbike.git` +* **Remote Fetch URL:** `sql@192.168.1.26:/home/sql/git/bigbike.git` + +## Deploy Commands +```powershell +# Deploy branch master +git push bigbike master + +# Dry run test +git push --dry-run bigbike master +``` diff --git a/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/hook/post-receive b/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/hook/post-receive new file mode 100644 index 0000000..68431ec --- /dev/null +++ b/serverinfo/192.168.1.26/bigbike.ddcsprocket.com/hook/post-receive @@ -0,0 +1,110 @@ +#!/bin/bash + +# ============================================================================== +# Bigbike Project (bigbike.ddcsprocket.com) +# Deployment Script (post-receive hook) on sql@192.168.1.26 +# Role: Application Runner (PM2 / Bun / Node) - No local Nginx +# ============================================================================== + +set -e +export PATH="/home/sql/.bun/bin:/usr/local/bin:/usr/bin:/bin:$PATH" + +# 1. PATH CONFIG +GIT_DIR="/home/sql/git/bigbike.git" +WORK_DIR="/home/sql/code/bigbike" +BRANCH="master" +TEMP_DIR="/tmp/bigbike_build_$(date +%s)" + +# 2. RUNTIMES & EXECUTABLES +BUN="/home/sql/.bun/bin/bun" +NODE="/usr/bin/node" +PM2="/usr/bin/pm2" + +# 3. PM2 PROCESS NAMES +PM2_NAME_BACKEND="bigbike-backend" +PM2_NAME_WEBSITE="bigbike-website" + +# 4. ASSIGNED PORTS (Direct forwarded from outer proxy / gateway) +# (Port 3001 is shop-ddcth, 4000 is aroka, 5000 is ddc hr) +BACKEND_PORT=3005 +SSR_PORT=3002 + +# 5. ENVIRONMENT VARIABLES +export PORT="$SSR_PORT" +export BACKEND_PORT="$BACKEND_PORT" +export VITE_API_URL="https://api.bigbike.ddcsprocket.com/api" +export NEXT_PUBLIC_API_URL="https://api.bigbike.ddcsprocket.com/api" + +echo "========================================================" +echo "🚀 [Bigbike] Starting Deployment on 192.168.1.26..." +echo "========================================================" + +# A. Checkout code to Work Directory +mkdir -p "$WORK_DIR" +echo ">>> Checking out branch $BRANCH to $WORK_DIR..." +git --work-tree="$WORK_DIR" --git-dir="$GIT_DIR" checkout -f "$BRANCH" + +cd "$WORK_DIR" + +# B. Install dependencies +if [ -f "package.json" ]; then + echo ">>> Installing dependencies with Bun..." + $BUN install +fi + +# C. Setup Backend (if apps/backend exists) +if [ -d "apps/backend" ]; then + echo ">>> Setting up Backend..." + cd "$WORK_DIR/apps/backend" + + if [ -f "prisma/schema.prisma" ]; then + echo ">>> Generating Prisma Client..." + $BUN x prisma generate + + echo ">>> Auto-updating Database Schema..." + if [ -d "prisma/migrations" ]; then + echo ">>> Running Prisma migrate deploy..." + $BUN x prisma migrate deploy || echo "⚠️ migrate deploy had notices, falling back to db push..." + fi + echo ">>> Syncing schema with db push..." + $BUN x prisma db push --accept-data-loss + fi + + echo ">>> Restarting PM2 process: $PM2_NAME_BACKEND..." + if $PM2 describe "$PM2_NAME_BACKEND" > /dev/null 2>&1; then + $PM2 restart "$PM2_NAME_BACKEND" --update-env + else + echo ">>> Starting $PM2_NAME_BACKEND for the first time on port $BACKEND_PORT..." + PORT=$BACKEND_PORT $PM2 start "$BUN" --name "$PM2_NAME_BACKEND" --cwd "$WORK_DIR/apps/backend" -- run src/index.ts + fi + cd "$WORK_DIR" +fi + +# D. Setup Website SSR (if apps/website exists) +if [ -d "apps/website" ]; then + echo ">>> Building Next.js Website..." + cd "$WORK_DIR/apps/website" + NODE_ENV=production $BUN run build + + echo ">>> Restarting PM2 process: $PM2_NAME_WEBSITE..." + if $PM2 describe "$PM2_NAME_WEBSITE" > /dev/null 2>&1; then + PORT=$SSR_PORT $PM2 restart "$PM2_NAME_WEBSITE" --update-env + else + echo ">>> Starting $PM2_NAME_WEBSITE for the first time on port $SSR_PORT..." + # Check standalone server or standard next start + if [ -f ".next/standalone/server.js" ]; then + PORT=$SSR_PORT $PM2 start "$NODE" --name "$PM2_NAME_WEBSITE" --cwd "$WORK_DIR/apps/website/.next/standalone" -- server.js + else + PORT=$SSR_PORT $PM2 start "$BUN" --name "$PM2_NAME_WEBSITE" --cwd "$WORK_DIR/apps/website" -- run start + fi + fi + cd "$WORK_DIR" +fi + +# E. Save PM2 state +$PM2 save + +echo "========================================================" +echo "✅ [Bigbike] Deployment Finished Successfully!" +echo "========================================================" +$PM2 status diff --git a/serverinfo/192.168.1.26/ecosystem.config.example.js b/serverinfo/192.168.1.26/ecosystem.config.example.js new file mode 100644 index 0000000..edecbaa --- /dev/null +++ b/serverinfo/192.168.1.26/ecosystem.config.example.js @@ -0,0 +1,29 @@ +// PM2 Ecosystem Config for sql@192.168.1.26 +module.exports = { + apps: [ + { + name: 'cms-backend', + script: './src/index.ts', + cwd: '/home/sql/code/cms-api/apps/backend', + interpreter: '/home/sql/.bun/bin/bun', + watch: false, + max_memory_restart: '1G', + env_production: { + NODE_ENV: 'production', + PORT: 3005 + } + }, + { + name: 'cms-website', + script: 'server.js', + cwd: '/home/sql/code/cms-website', + interpreter: '/usr/bin/node', + watch: false, + max_memory_restart: '1G', + env_production: { + NODE_ENV: 'production', + PORT: 3002 + } + } + ] +}; diff --git a/serverinfo/192.168.1.26/post-receive.template b/serverinfo/192.168.1.26/post-receive.template new file mode 100644 index 0000000..efc8133 --- /dev/null +++ b/serverinfo/192.168.1.26/post-receive.template @@ -0,0 +1,149 @@ +#!/bin/bash + +# ============================================================================== +# HomAroma / CMS Project - Post-Receive Hook for sql@192.168.1.26 +# ============================================================================== + +# 1. PATH & ENVIRONMENT +export PATH="/home/sql/.bun/bin:/usr/local/bin:/usr/bin:/bin:$PATH" +set -e + +# 2. TARGET PATHS +# Static Frontend Deployments (Nginx document root) +TARGET_SPA="/var/www/html/cms/spa" +TARGET_ADMIN="/var/www/html/cms/admin" + +# Backend & Next.js Website Working Directories +TARGET_BACKEND="/home/sql/code/cms-api" +TARGET_WEBSITE="/home/sql/code/cms-website" + +# 3. REPOSITORY CONFIG +REPO="/home/sql/git/cms.git" +BRANCH="master" +TEMP_DIR="/tmp/cms_build_$(date +%s)" + +# 4. BINARY PATHS +BUN="/home/sql/.bun/bin/bun" +NODE="/usr/bin/node" +PM2="/usr/bin/pm2" + +# 5. PM2 PROCESS NAMES +PM2_NAME_BACKEND="cms-backend" +PM2_NAME_WEBSITE="cms-website" + +# 6. SERVICE PORTS (Ensure no collision with 3001, 4000, 4545, 5000, 5432, 6333, 8000) +BACKEND_PORT=3005 +SSR_PORT=3002 + +# 7. BUILD ENVIRONMENT VARIABLES +export VITE_API_URL="http://192.168.1.26:${BACKEND_PORT}/api" +export NEXT_PUBLIC_API_URL="http://192.168.1.26:${BACKEND_PORT}/api" + +# ------------------------------------------------------------------------------ +# START DEPLOYMENT +# ------------------------------------------------------------------------------ +echo "------- 🚀 Starting Full Deployment: sql@192.168.1.26 -------" + +# A. Prepare Temp Source from Checkout +echo "Cloning branch $BRANCH to temporary directory: $TEMP_DIR" +mkdir -p "$TEMP_DIR" +git --work-tree="$TEMP_DIR" --git-dir="$REPO" checkout -f "$BRANCH" + +cd "$TEMP_DIR" +echo "Installing monorepo dependencies with Bun..." +$BUN install + +# B. Build & Deploy SPA +if [ -d "apps/spa" ]; then + echo ">>> Building SPA..." + cd apps/spa + $BUN run build + echo "Deploying SPA to $TARGET_SPA..." + mkdir -p "$TARGET_SPA" + rm -rf "$TARGET_SPA"/* + cp -rv dist/* "$TARGET_SPA"/ + cd ../.. +fi + +# C. Build & Deploy Admin Panel +if [ -d "apps/admin" ]; then + echo ">>> Building Admin Panel..." + cd apps/admin + $BUN run build + echo "Deploying Admin Panel to $TARGET_ADMIN..." + mkdir -p "$TARGET_ADMIN" + rm -rf "$TARGET_ADMIN"/* + cp -rv dist/* "$TARGET_ADMIN"/ + cd ../.. +fi + +# D. Deploy & Manage Backend +if [ -d "apps/backend" ]; then + echo ">>> Updating Backend at $TARGET_BACKEND..." + mkdir -p "$TARGET_BACKEND/apps" + mkdir -p "$TARGET_BACKEND/packages" + + rsync -av --delete \ + --exclude='.env' \ + --exclude='public/' \ + --exclude='node_modules/' \ + apps/backend/ "$TARGET_BACKEND/apps/backend/" + + rsync -av packages/ "$TARGET_BACKEND/packages/" + cp package.json bun.lock ecosystem.config.js "$TARGET_BACKEND/" 2>/dev/null || cp package.json bun.lock "$TARGET_BACKEND/" + + cd "$TARGET_BACKEND" + $BUN install + + mkdir -p "$TARGET_BACKEND/apps/backend/public" + + cd "$TARGET_BACKEND/apps/backend" + echo ">>> Generating Prisma Client & Pushing DB..." + $BUN x prisma generate + $BUN x prisma db push --accept-data-loss || echo "Prisma db push skipped or failed" + + echo ">>> Managing PM2 for Backend..." + if $PM2 describe "$PM2_NAME_BACKEND" > /dev/null 2>&1; then + $PM2 restart "$PM2_NAME_BACKEND" --update-env + else + $PM2 start "$BUN" --name "$PM2_NAME_BACKEND" --cwd "$TARGET_BACKEND/apps/backend" -- run src/index.ts + fi +fi + +# E. Deploy & Manage Website (Next.js SSR) +if [ -d "$TEMP_DIR/apps/website" ]; then + echo ">>> Building Website (Next.js SSR)..." + cd "$TEMP_DIR/apps/website" + $BUN run build + + echo ">>> Updating Website at $TARGET_WEBSITE..." + mkdir -p "$TARGET_WEBSITE" + rsync -av --delete \ + --exclude='.env' \ + --exclude='node_modules/' \ + "$TEMP_DIR/apps/website/.next/standalone/" "$TARGET_WEBSITE/" 2>/dev/null || echo "Standalone directory sync" + + if [ -d "$TEMP_DIR/apps/website/.next/static" ]; then + mkdir -p "$TARGET_WEBSITE/.next/static" + cp -rv "$TEMP_DIR/apps/website/.next/static/"* "$TARGET_WEBSITE/.next/static/" + fi + if [ -d "$TEMP_DIR/apps/website/public" ]; then + cp -rv "$TEMP_DIR/apps/website/public" "$TARGET_WEBSITE/" + fi + + echo ">>> Managing PM2 for Website..." + cd "$TARGET_WEBSITE" + PORT=$SSR_PORT + if $PM2 describe "$PM2_NAME_WEBSITE" > /dev/null 2>&1; then + $PM2 restart "$PM2_NAME_WEBSITE" --update-env + else + PORT=$SSR_PORT $PM2 start "$NODE" --name "$PM2_NAME_WEBSITE" -- server.js + fi +fi + +# F. Cleanup & Save PM2 +rm -rf "$TEMP_DIR" +$PM2 save + +echo "===== ✅ Deployment Completed Successfully! =====" +$PM2 list