部署到 Node.js

本頁內容

EmDash 在 Node.js 22.16 或更高版本上運行。本指南使用 SQLite 搭配本地或 S3 相容儲存;libSQL 和 PostgreSQL 在 Node.js 上的運作方式相同 — 請參閱資料庫選項

先決條件

  • Node.js v22.16.0 或更高版本
  • Node.js 託管提供商或 VPS

設定

為 Node.js 部署設定 EmDash:

import { defineConfig } from "astro/config";
import node from "@astrojs/node";
import emdash, { local, s3 } from "emdash/astro";
import { sqlite } from "emdash/db";

export default defineConfig({
	output: "server",
	adapter: node({ mode: "standalone" }),
	integrations: [
		emdash({
			database: sqlite({ url: "file:./data/emdash.db" }),
			storage: local({
				directory: "./data/uploads",
				baseUrl: "/_emdash/api/media/file",
			}),
		}),
	],
});

建置和執行

  1. 建置專案:

    npm run build
  2. 啟動伺服器:

    node ./dist/server/entry.mjs

伺服器預設在 http://localhost:4321 上執行。遷移在第一個請求時套用。如果資料庫為空且設定未完成,您的種子檔案(如果沒有則使用內建預設值)也會在第一個請求時套用。

排程任務

內建排程器僅在 Node.js 處理程序執行時運作。它處理排程發布、外掛任務和一般維護。

在生產環境中保持至少一個 Node.js 處理程序持續執行。當所有處理程序停止或休眠時,排程任務會暫停。

外掛沙箱

市集外掛和 sandboxed: [] 下列出的外掛需要沙箱執行器。在 Node.js 上,執行器是 @emdash-cms/sandbox-workerd,它在 workerd 子處理程序中執行外掛。外掛沙箱介紹了安裝方法、workerd 處理程序的執行方式及其故障模式。

生產儲存

在生產環境中,使用 S3 相容儲存代替本地檔案系統:

import emdash, { s3 } from "emdash/astro";

export default defineConfig({
	integrations: [
		emdash({
			database: sqlite({ url: `file:${process.env.DATABASE_PATH}` }),
			storage: s3({
				endpoint: process.env.S3_ENDPOINT,
				bucket: process.env.S3_BUCKET,
				accessKeyId: process.env.S3_ACCESS_KEY_ID,
				secretAccessKey: process.env.S3_SECRET_ACCESS_KEY,
				publicUrl: process.env.S3_PUBLIC_URL, // 可選的 CDN URL
			}),
		}),
	],
});

Docker

新增 .dockerignore 以保持建置上下文較小:

node_modules
dist
.git

建立 Dockerfile

FROM node:22-alpine AS builder
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build

FROM node:22-alpine
WORKDIR /app
COPY --from=builder /app/dist ./dist
COPY --from=builder /app/node_modules ./node_modules
COPY --from=builder /app/package.json ./

RUN mkdir -p data

ENV HOST=0.0.0.0
ENV PORT=4321

EXPOSE 4321
CMD ["node", "./dist/server/entry.mjs"]

種子檔案在建置時讀取並內嵌到 bundle 中,因此不需要複製到執行階段映像。遷移在部署後的第一個請求時執行;種子僅在資料庫沒有集合且設定未完成時才套用 — 現有資料永遠不會被覆蓋。

建置映像並執行容器:

docker build -t my-emdash-site .
docker run -p 4321:4321 -v emdash-data:/app/data my-emdash-site

Docker Compose 檔案使用具名卷管理同一個容器:

services:
  emdash:
    build: .
    ports:
      - "4321:4321"
    volumes:
      - emdash-data:/app/data
    restart: unless-stopped

volumes:
  emdash-data:

在背景啟動堆疊:

docker compose up -d

環境變數

建議:加密金鑰

EMDASH_ENCRYPTION_KEY 是用於加密外掛密鑰的靜態加密金鑰。該金鑰在啟動時驗證;外掛密鑰加密在啟用後使用它。在每次部署時設定它,這樣密鑰無需後續設定變更即可受到保護。

產生金鑰並將結果新增到您的環境中:

npx emdash secrets generate  # 將結果新增到您的環境中

金鑰由您提供,永遠不會儲存在資料庫中;只儲存加密的密文。將其備份到持久的位置(密碼管理器、KMS 或團隊的密鑰儲存)— 遺失它意味著遺失用它加密的每個密鑰。

可選:穩定值覆寫

EmDash 自動產生預覽 HMAC 密鑰和評論者 IP 雜湊鹽,並在首次使用時將其持久化到資料庫中。以下環境變數將它們固定為您控制的值 — 當單獨的處理程序需要與主網站共享密鑰時很有用。

變數描述
EMDASH_PREVIEW_SECRET自動產生的預覽 HMAC 密鑰的覆寫。
EMDASH_IP_SALT自動產生的評論者 IP 雜湊鹽的覆寫。
EMDASH_AUTH_SECRET可選。如果設定,用作 IP 鹽來源(除非 EMDASH_IP_SALT 也已設定,後者優先),保持已依賴它的安裝的評論者 IP 雜湊穩定。新部署請不要設定。

資料庫和儲存

變數描述範例
DATABASE_PATHSQLite 資料庫路徑/data/emdash.db
HOST伺服器主機0.0.0.0
PORT伺服器連接埠4321
S3_ENDPOINTS3 端點 URLhttps://xxx.r2.cloudflarestorage.com
S3_BUCKETS3 儲存桶名稱my-media-bucket
S3_ACCESS_KEY_IDS3 存取金鑰AKIA...
S3_SECRET_ACCESS_KEYS3 秘密金鑰...
S3_PUBLIC_URL媒體公開 URLhttps://cdn.example.com

持久儲存

SQLite 需要持久的磁碟儲存。確保您的託管平台提供:

  • 掛載的卷或持久磁碟
  • 資料庫目錄的寫入權限
  • 資料庫檔案的備份機制

健康檢查

為負載平衡器新增健康檢查端點:

export const GET = () => {
  return new Response("OK", { status: 200 });
};

設定您的平台檢查 /health 以進行存活探測。