diff --git a/README.md b/README.md index c423759..abd47f2 100644 --- a/README.md +++ b/README.md @@ -16,30 +16,90 @@ ## 定制项(与上游 Photoview 的差异) - **品牌** — 左上角 FK 书法 logo,页面标题 `Gallery.FuKun.Net` -- **外观** — 纯黑背景 (`#000`),菜单图标改为极简线条 +- **外观** — 纯黑背景 (`#000`),菜单图标改为极简线条,顶栏 64px 高与主站一致 - **字体** — iA Writer Quattro S + Noto Sans SC(与主站 fukun.net 一致) -- **CDN** — 公开原图走 `cdn.fukun.net`,带 token 的鉴权图片自动切 CDN +- **交互** — 点击图片打开侧边栏详情(去掉全屏预览),手机端点遮罩层关闭 - **无 Docker** — Go 二进制 + systemd,SQLite 单文件数据库 - **人脸识别** — 已关闭(`PHOTOVIEW_DISABLE_FACE_RECOGNITION=1`) +- **CDN** — 仅公开原图走 `cdn.fukun.net`;管理界面图片直连(需鉴权 cookie,无法跨域走 CDN) + +--- + +## 服务器 + +| 项目 | 详情 | +|------|------| +| 服务器 | 腾讯云轻量 · 北京七区 | +| 公网 IP | `62.234.90.54` | +| 系统 | Ubuntu 24.04 LTS · 4核4G · SSD 40G + 20G | +| Go | 1.22.2(系统自带)→ 编译时自动下载 toolchain 1.26.0 | +| Node | v22.22.2 | +| Nginx | `/etc/nginx/` · 80/443 | +| SSL | 腾讯云证书 · `/etc/nginx/ssl/` | + +### 架构 + +``` + Internet + │ + ┌────────────────┼────────────────┐ + │ │ │ + fukun.net gallery.fukun.net pwd.fukun.net + (Hugo 博客) (Photoview) (Vaultwarden) + 直接访问 直接访问 直接访问 + │ │ + ┌────┴────┐ ┌────┴────┐ + │ │ │ │ + HTML 静态资源 页面/API /photos/* + 不缓存 加了缓存头 proxy serve 文件 + │ │ │ + │ │ │ + ┌──────┴──────────┴─────────┴──────┐ + │ cdn.fukun.net │ ← 腾讯云 CDN + │ /blog/* → fukun.net │ 只代理静态资源 + │ /gallery/* → gallery...net │ 主站不经过 CDN + └─────────────────────────────────┘ +``` + +`gallery.fukun.net` 由 Nginx 统一接入,按路径分流: + +| 路径 | 行为 | +|------|------| +| `/photos/*` | 直接 serve 原图(CDN 回源口,加 CORS + 缓存头) | +| `/assets/*` | 缓存 30 天(JS/CSS/字体,文件名带 hash) | +| `/*` | 反向代理到 `127.0.0.1:8000`(Photoview) | --- ## 目录结构 +### 服务器(`/home/gallery/`) + ``` /home/gallery/ -├── photoview-src/ # 源码 + 编译产物 +├── photoview-src/ # 源码 + 编译产物(git 管理) │ ├── api/ │ │ ├── .env # 运行时环境变量 │ │ └── photoview # Go 二进制(38MB) │ └── ui/ │ └── dist/ # 前端构建产物 ├── photos/ # 相片库根目录 -└── data/ - ├── photoview.db # SQLite 数据库 - └── media-cache/ # 缩略图缓存 +├── data/ +│ ├── photoview.db # SQLite 数据库 +│ └── media-cache/ # 缩略图缓存 +└── go/ # Go 模块缓存(449MB,运行时不需要) ``` +### 各目录职责 + +| 目录 | 谁创建 | 生命周期 | 备份? | +|------|--------|----------|--------| +| `photoview-src/` | 手动上传 | 持久,更新时重传/`git pull` | 不需要(git 管理) | +| `photos/` | 手动上传 | 持久 | ✅ **核心数据,必须备份** | +| `data/photoview.db` | Photoview 首次启动 | 持久 | ✅ 备份(单文件直接 cp) | +| `data/media-cache/` | Photoview 扫描时 | 可重建 | 可选(丢了能重新生成) | +| `go/` | `go mod download` | 可重建 | 不需要 | + --- ## 本地开发 @@ -62,33 +122,13 @@ npm ci npm run dev # localhost:1234,API 连生产服务器 ``` ---- - -## 部署到服务器 - -```bash -# 构建前端 -scp -r ui/src ui/public ubuntu@62.234.90.54:/tmp/pv-ui/ -ssh ubuntu@62.234.90.54 ' - sudo cp -r /tmp/pv-ui/* /home/gallery/photoview-src/ui/ - sudo chown -R gallery:gallery /home/gallery/photoview-src/ui - sudo -u gallery bash -c "cd /home/gallery/photoview-src/ui && npm ci && npm run build" -' - -# 构建后端 + 重启 -ssh ubuntu@62.234.90.54 ' - cd /home/gallery/photoview-src/api - export PKG_CONFIG_PATH=/usr/local/im7/lib/pkgconfig CGO_ENABLED=1 - sudo -u gallery go build -o photoview . - sudo systemctl restart photoview -' -``` +改完前端后,构建 + 部署到服务器(见下文「部署」)。 --- ## 运行时配置 -**systemd** — `/etc/systemd/system/photoview.service` +### systemd — `/etc/systemd/system/photoview.service` | 环境变量 | 值 | |----------|-----| @@ -102,39 +142,314 @@ ssh ubuntu@62.234.90.54 ' | `PHOTOVIEW_DISABLE_FACE_RECOGNITION` | `1` | | `LD_LIBRARY_PATH` | `/usr/local/im7/lib` | -**Nginx** — `/etc/nginx/sites-enabled/gallery.fukun.net` +### Nginx — `/etc/nginx/sites-enabled/gallery.fukun.net` -- `gallery.fukun.net` + `cdn.fukun.net` → HTTPS → `127.0.0.1:8000` -- `/photos/` → `alias /home/gallery/photos/`(CDN 回源口) -- `/assets/` → 缓存 30 天 +```nginx +server { + listen 80; + server_name gallery.fukun.net cdn.fukun.net; + return 301 https://$host$request_uri; +} -**SSL 证书** — 腾讯云证书,`/etc/nginx/ssl/gallery.fukun.net_*` +server { + listen 443 ssl http2; + server_name gallery.fukun.net cdn.fukun.net; + + ssl_certificate /etc/nginx/ssl/gallery.fukun.net_bundle.crt; + ssl_certificate_key /etc/nginx/ssl/gallery.fukun.net.key; + ssl_protocols TLSv1.2 TLSv1.3; + ssl_ciphers HIGH:!aNULL:!MD5; + + client_max_body_size 4G; + + # 相片直出(CDN 回源) + location /photos/ { + alias /home/gallery/photos/; + add_header Access-Control-Allow-Origin "*" always; + } + + # 静态资源 + location /assets/ { + proxy_pass http://127.0.0.1:8000; + proxy_http_version 1.1; + proxy_set_header Host $host; + expires 30d; + add_header Cache-Control "public, immutable"; + } + + # Photoview + location / { + add_header Access-Control-Allow-Origin "https://gallery.fukun.net" always; + add_header Access-Control-Allow-Methods "GET, OPTIONS" always; + add_header Access-Control-Allow-Credentials "true" always; + + proxy_pass http://127.0.0.1:8000; + proxy_http_version 1.1; + proxy_set_header Upgrade $http_upgrade; + proxy_set_header Connection "upgrade"; + 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; + proxy_read_timeout 86400s; + proxy_send_timeout 86400s; + } +} +``` + +### SSL 证书 + +腾讯云证书,`/etc/nginx/ssl/gallery.fukun.net_bundle.crt` + `gallery.fukun.net.key`。 + +--- + +## 部署(从零或重装) + +### 1. 系统依赖 + +```bash +sudo apt update +sudo apt install -y \ + g++ libheif-dev libdlib-dev libjpeg-dev \ + libblas-dev liblapack-dev libmagic-dev \ + ffmpeg git wget curl + +# exiftool(EXIF 解析,启动必须) +sudo apt install -y exiftool +``` + +### 2. ImageMagick 7(关键) + +> Ubuntu 24.04 只有 IM6,Photoview 的 Go 绑定 `imagick.v3` 依赖 IM7,必须源码编译。 + +```bash +tar xzf ImageMagick-7.1.1-47.tar.gz +cd ImageMagick-7.1.1-47 +./configure --prefix=/usr/local/im7 --with-quantum-depth=16 --disable-docs --disable-static +make -j4 +sudo make install +``` + +### 3. libcblas 兼容 + +> Ubuntu 24.04 把 CBLAS 合并进了 BLAS,但 dlib 的 linker 显式查找 `-lcblas`。 + +```bash +sudo ln -sf /usr/lib/x86_64-linux-gnu/libblas.so /usr/lib/x86_64-linux-gnu/libcblas.so +``` + +### 4. 上传源码 & 构建 + +```bash +# 本地打包上传 +tar --exclude='.git' -czf pv-src.tar.gz . +scp pv-src.tar.gz ubuntu@62.234.90.54:/tmp/ + +# 服务器解压 +sudo mkdir -p /home/gallery/photoview-src +sudo tar -xzf /tmp/pv-src.tar.gz -C /home/gallery/photoview-src +sudo chown -R gallery:gallery /home/gallery/photoview-src +``` + +**构建前端:** + +```bash +sudo -u gallery bash -c " +cd /home/gallery/photoview-src/ui +# REACT_APP_API_ENDPOINT 必须用完整 URL,否则 new URL() 报 Invalid URL +cat > .env << ENDENV +REACT_APP_API_ENDPOINT=https://gallery.fukun.net/api/ +REACT_APP_BUILD_VERSION=2.0.0-manual +REACT_APP_BUILD_DATE=$(date -u +%Y-%m-%d) +REACT_APP_BUILD_COMMIT_SHA=fukun-gallery +ENDENV +npm ci +npm run build +" +``` + +**构建后端:** + +```bash +sudo -u gallery bash -c " +export PKG_CONFIG_PATH=/usr/local/im7/lib/pkgconfig +export CGO_ENABLED=1 +cd /home/gallery/photoview-src/api + +go mod download + +# 修复 go-face(删 -lcblas 避免重复链接) +FACE=\$(find \$(go env GOMODCACHE) -path '*go-face*' -name face.go) +sudo chmod u+w \"\$FACE\" +sed -i 's/-lcblas//g' \"\$FACE\" + +go build -v -o photoview . +" +``` + +### 5. systemd 服务 + +```bash +sudo mkdir -p /home/gallery/{photos,data/media-cache} +sudo chown -R gallery:gallery /home/gallery/data + +sudo tee /etc/systemd/system/photoview.service << 'EOF' +[Unit] +Description=Photoview Gallery Server +After=network.target + +[Service] +Type=simple +User=gallery +Group=gallery +WorkingDirectory=/home/gallery/photoview-src/api +ExecStart=/home/gallery/photoview-src/api/photoview +Restart=on-failure +RestartSec=5 + +NoNewPrivileges=yes +PrivateTmp=yes + +Environment=PHOTOVIEW_DATABASE_DRIVER=sqlite +Environment=PHOTOVIEW_SQLITE_PATH=/home/gallery/data/photoview.db +Environment=PHOTOVIEW_LISTEN_IP=127.0.0.1 +Environment=PHOTOVIEW_LISTEN_PORT=8000 +Environment=PHOTOVIEW_SERVE_UI=1 +Environment=PHOTOVIEW_UI_PATH=/home/gallery/photoview-src/ui/dist +Environment=PHOTOVIEW_MEDIA_CACHE=/home/gallery/data/media-cache +Environment=PHOTOVIEW_DISABLE_FACE_RECOGNITION=1 +Environment=LD_LIBRARY_PATH=/usr/local/im7/lib + +[Install] +WantedBy=multi-user.target +EOF + +sudo systemctl daemon-reload +sudo systemctl enable --now photoview +``` + +验证: + +```bash +curl -s http://127.0.0.1:8000/api/graphql \ + -X POST -H 'Content-Type: application/json' \ + -d '{"query":"{ siteInfo { initialSetup } }"}' +# {"data":{"siteInfo":{"initialSetup":true}}} +``` + +### 6. SSL 证书 & Nginx + +上传证书(`gallery.fukun.net.key` + `gallery.fukun.net_bundle.crt`)到 `/etc/nginx/ssl/`,然后创建上文 Nginx 配置并 reload: + +```bash +sudo nginx -t && sudo nginx -s reload +``` + +--- + +## Ubuntu 24.04 特有问题 + +| 问题 | 原因 | 解决 | +|------|------|------| +| `MagickWand.h: No such file` | 24.04 只有 IM6,Photoview 依赖 IM7 | 源码编译 IM7 到 `/usr/local/im7` | +| `cannot find -lcblas` | 24.04 把 CBLAS 合并进 BLAS | `ln -sf libblas.so libcblas.so` | +| `exiftool not found` → panic | 启动必须有 exiftool | `apt install exiftool` | +| go-face `-lcblas` 重复链接 | go-face 内部也声明了 | `sed -i 's/-lcblas//g'` | +| go module cache 只读 | `go mod download` 文件只读 | `sudo chmod u+w` 后再改 | +| `new URL('/api/graphql')` 报 Invalid URL | 相对路径无法构造 URL | `REACT_APP_API_ENDPOINT` 用完整 URL | + +--- + +## CDN 配置 + +统一加速域名 `cdn.fukun.net`,按路径回源: + +``` +cdn.fukun.net +├── /blog/* → 回源 fukun.net(博客静态资源) +└── /gallery/* → 回源 gallery.fukun.net/photos/(相册原图) +``` + +| 配置项 | 值 | +|--------|-----| +| 加速域名 | `cdn.fukun.net` | +| 回源协议 | HTTPS | +| 回源 HOST | 留空(自动用源站域名) | + +**注意:** CDN 只加速公开的静态文件。管理界面里的图片需要鉴权 cookie,不能走 CDN,仍直连 `gallery.fukun.net`。Hugo 博客嵌入原图时用 `https://cdn.fukun.net/gallery/photos/xxx.jpg`。 --- ## 维护 +### 状态 + ```bash -# 查看状态 sudo systemctl status photoview sudo journalctl -u photoview -f +``` -# 重启 -sudo systemctl restart photoview +### 更新前端 -# 备份数据库 +```bash +scp -r ui/src ui/public ubuntu@62.234.90.54:/tmp/pv-ui/ +ssh ubuntu@62.234.90.54 ' + sudo cp -r /tmp/pv-ui/* /home/gallery/photoview-src/ui/ + sudo chown -R gallery:gallery /home/gallery/photoview-src/ui + sudo -u gallery bash -c "cd /home/gallery/photoview-src/ui && npm ci && npm run build" + sudo systemctl restart photoview +' +``` + +### 更新后端 + +```bash +ssh ubuntu@62.234.90.54 ' + cd /home/gallery/photoview-src/api + export PKG_CONFIG_PATH=/usr/local/im7/lib/pkgconfig CGO_ENABLED=1 + sudo -u gallery go build -o photoview . + sudo systemctl restart photoview +' +``` + +### 备份 + +```bash +# 数据库 sudo cp /home/gallery/data/photoview.db /opt/backup/photoview_$(date +%Y%m%d).db # 上传照片 -scp *.jpg ubuntu@62.234.90.54:/home/gallery/photos/ +scp *.jpg ubuntu@62.234.90.54:/tmp/pv-photos/ +ssh ubuntu@62.234.90.54 'sudo mv /tmp/pv-photos/* /home/gallery/photos/ && sudo chown -R gallery:gallery /home/gallery/photos/' ``` --- +## 端口汇总 + +| 端口 | 用途 | 公网 | +|------|------|------| +| 22 | SSH | ✅ | +| 80/443 | Nginx 全站 | ✅ | +| 8000 | Photoview | ❌ 127.0.0.1 | +| 8080 | Vaultwarden | ❌ 127.0.0.1 | +| 17581 | OpenClaw | ❌ | + +--- + +## 初始化 + +1. 浏览器访问 `https://gallery.fukun.net` +2. 创建管理员账号 +3. **Photo Path** 填 `/home/gallery/photos` +4. 上传相片后,Settings → Scan All + +--- + ## 仓库 ``` ssh://git@fukun.net/data/git-repos/gallery.git ``` -服务器上 `/data/git-repos/gallery.git`(bare),推送到 `master`。 +服务器 `/data/git-repos/gallery.git`(bare),推送到 `master`。