ในสถาปัตยกรรมระบบแบบแยกส่วน (Decoupled Architecture) การแยกบริการฐานข้อมูลออกมาทำงานเป็นอิสระจากเว็บแอปพลิเคชัน (เช่น การแยกแอปพลิเคชันออกจาก MariaDB) เป็นแนวทางปฏิบัติที่ดีที่สุด (Best Practice) เพื่อเพิ่มความยืดหยุ่นในการบริหารจัดการ การสำรองข้อมูล และการแชร์ฐานข้อมูลร่วมกันระหว่างหลายโปรเจกต์
บทความนี้จะสรุปแนวทางการสร้าง MariaDB Container โดยใช้รูปแบบ Sidecar Pattern ซึ่งหมายถึงการรันฐานข้อมูลในคอนเทนเนอร์ที่ถูกควบคุมและเชื่อมต่อผ่าน Docker Network กลางชื่อ magi เพื่อให้ทุกเซอร์วิสสามารถเข้าถึงฐานข้อมูลได้อย่างเป็นระเบียบและปลอดภัย
1. โครงสร้างโปรเจกต์และการจัดระเบียบ (Project Structure)
การจัดระเบียบไฟล์ในรูปแบบ Sidecar จะช่วยให้เราสามารถรวมไฟล์คอนฟิกและสคริปต์เริ่มต้นทั้งหมดไว้ในที่เดียว โดยโครงสร้างไดเรกทอรีที่แนะนำคือ:
BASH / Shell
/Users/common/Docker/</code>
├── .env <-- ตัวแปรสภาพแวดล้อมส่วนกลาง (Credentials, Network Name)
└── db_mariadb_13/
├── build.sh <-- สคริปต์เตรียมระบบและสร้าง init script
├── docker-compose.yml
├── init-scripts/ <-- ไดเรกทอรีสำหรับ Mount เข้าไปใน Container
│ └── 01-init-security.sql
└── data/ <-- Bind Mount สำหรับเก็บข้อมูลดิบ (Persistence)
2. การกำหนดค่าตัวแปรสภาพแวดล้อม (.env)
ไฟล์ .env ทำหน้าที่เป็นแหล่งรวมความลับ (Secrets) และค่าคอนฟิกส่วนกลาง เพื่อให้สามารถนำไปใช้ได้ทั้งใน docker-compose.yml และสคริปต์อื่นๆ:
BASH / Shell
# .env file</code>
NETWORK_NAME=magi
MARIADB_ROOT_PASSWORD=super_secret_root
MARIADB_DATABASE=central_db
MARIADB_USER=app_service
MARIADB_PASSWORD=secure_app_pw
3. การสร้างสคริปต์เริ่มต้นด้วย PostgreSQL Syntax (01-init-security.sql)
แม้ว่าเราจะใช้ MariaDB Container แต่เพื่อรักษามาตรฐานความปลอดภัยและสอดคล้องกับ Best Practices ของ PostgreSQL เราจะใช้ไวยากรณ์ SQL ที่เน้นการกำหนดสิทธิ์ (Role Management) ในสคริปต์เริ่มต้น 01-init-security.sql:
SQL
-- 1. สร้าง Role สำหรับแอปพลิเคชัน (Best Practice)</code>
CREATE ROLE app_service WITH LOGIN PASSWORD 'secure_app_pw';
-- 2. สร้างฐานข้อมูลหลัก (ถ้ายังไม่มี)</code>
CREATE DATABASE central_db OWNER app_service;
-- 3. กำหนดสิทธิ์การเชื่อมต่อให้ Role ที่สร้างขึ้น</code>
GRANT CONNECT ON DATABASE central_db TO app_service;
-- 4. สร้างตารางตัวอย่างเพื่อทดสอบการเชื่อมต่อ</code>
CREATE TABLE IF NOT EXISTS user_data (
id SERIAL PRIMARY KEY,
username VARCHAR(50) UNIQUE NOT NULL,
created_at TIMESTAMP WITH TIME ZONE DEFAULT NOW()
);
4. การเรียกใช้งานด้วย Docker Compose
เราจะใช้ docker-compose.yml เพื่อกำหนดบริการ โดยให้คอนเทนเนอร์ MariaDB เชื่อมต่อกับ Network magi และ Mount สคริปต์เริ่มต้นเข้าไป:
YAML
version: '3.8'</code>
services:
mariadb:
image: mariadb:10.6
container_name: central_mariadb
environment:
MARIADB_ROOT_PASSWORD: ${MARIADB_ROOT_PASSWORD}
MARIADB_DATABASE: ${MARIADB_DATABASE}
MARIADB_USER: ${MARIADB_USER}
MARIADB_PASSWORD: ${MARIADB_PASSWORD}
volumes:
- ./data:/var/lib/mysql
- ./init-scripts:/docker-entrypoint-initdb.d # Mount init scripts
networks:
- magi
networks:
magi:
external: true # ต้องสร้าง Network นี้ก่อนด้วยคำสั่ง 'docker network create magi'
บทสรุป
การใช้ Sidecar Pattern ในการจัดการ MariaDB Container ผ่าน Docker Network กลาง magi ทำให้ระบบของเรามีฐานข้อมูลที่ถูกแยกส่วน (Decoupled) อย่างสมบูรณ์ การใช้สคริปต์เริ่มต้นที่กำหนดสิทธิ์อย่างละเอียด (เช่น การใช้ไวยากรณ์ PG) ทำให้มั่นใจได้ว่าฐานข้อมูลมีความปลอดภัยและพร้อมใช้งานสำหรับบริการต่างๆ ที่รันอยู่บน Network เดียวกัน ซึ่งเป็นแนวทางที่ยกระดับความมั่นคงและประสิทธิภาพของสถาปัตยกรรมระบบให้เป็นระดับ Senior Architect อย่างแท้จริง