Files
frontend-miniapp/docs/deployment/guide-whaoyue-nginx-ssl.md
lyf d07d68af0a
Some checks are pending
CI / verify (push) Waiting to run
docs: 更新导览站点端口与证书部署说明
2026-07-22 20:17:53 +08:00

719 lines
24 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# guide.whaoyue.com 静态站点部署说明
## 1. 部署目标
- 域名:`guide.whaoyue.com`
- 服务器备注:自然博物馆-测试服务器
- 公网 IP`1.92.206.90`
- SSH 用户:`root`
- 系统Huawei Cloud EulerOS 2.0 aarch64
- 部署内容Nginx 静态测试页面 + Lets Encrypt HTTPS 证书
- 页面地址:<https://guide.whaoyue.com:4433/>
- 首次部署日期2026-06-08
- 端口调整日期2026-07-22
> 当前公网 HTTPS 入口是 `4433`,访问地址必须显式携带端口。`https://guide.whaoyue.com/` 使用默认 `443`,不再是当前入口。
## 2. 当前部署拓扑
服务器已安装系统级 Nginx 包。Docker Nginx 容器内仍监听标准 `80/443`,宿主机公网映射已调整为 `8888/4433`
```text
公网用户
-> guide.whaoyue.com
-> 1.92.206.90:8888/4433
-> Docker 容器 nginx-server
-> 宿主机 8888 -> 容器 80
-> 宿主机 4433 -> 容器 443
-> /dmdata/nginx/html/guide/index.html
```
Docker Nginx 容器:
```bash
docker ps --format "table {{.Names}}\t{{.Image}}\t{{.Ports}}\t{{.Status}}"
```
当前端口映射:
| 宿主机端口 | 容器端口 | 用途 |
| --- | --- | --- |
| `8888` | `80` | HTTP 入口,跳转到 `https://guide.whaoyue.com:4433/` |
| `4433` | `443` | HTTPS 静态站点和反向代理 |
| `7080` | `7080` | 既有服务,端口调整时必须保留 |
| `7081` | `7081` | 既有服务,端口调整时必须保留 |
关键挂载:
| 宿主机路径 | 容器路径 | 用途 |
| --- | --- | --- |
| `/dmdata/nginx/conf.d` | `/etc/nginx/conf.d` | Nginx 站点配置 |
| `/dmdata/nginx/html` | `/usr/share/nginx/html` | 静态页面 |
| `/dmdata/nginx/ssl` | `/etc/nginx/ssl` | SSL 证书 |
| `/dmdata/nginx/logs` | `/var/log/nginx` | 访问日志和错误日志 |
## 3. 静态页面
静态测试页路径:
```bash
/dmdata/nginx/html/guide/index.html
```
页面用途:
- 验证域名解析
- 验证 Nginx 静态站点
- 验证 HTTP 到 HTTPS 跳转
- 验证 Lets Encrypt 证书
如需替换正式页面,将构建后的静态文件发布到:
```bash
/dmdata/nginx/html/guide/
```
## 4. Nginx 配置
站点配置文件:
```bash
/dmdata/nginx/conf.d/guide.whaoyue.com.conf
```
配置行为:
- `http://guide.whaoyue.com:8888/` 自动跳转到 `https://guide.whaoyue.com:4433/`
- `/.well-known/acme-challenge/` 路径仍保留,但 Lets Encrypt HTTP-01 不会验证 `8888`,续期限制见第 5 节
- `https://guide.whaoyue.com:4433/` 返回静态页面
- `https://guide.whaoyue.com:4433/app-api/` 反向代理到宿主机 `48080/yudao-server/app-api/`
- `https://guide.whaoyue.com:4433/h5-sdk` 配置为反向代理到宿主机 `3001`2026-07-22 公网抽查为 `502`,当前不可作为可用能力
- `https://guide.whaoyue.com:4433/museum-assets/``/minio/museum-assets/` 反向代理到 MinIO
- 静态资源设置 30 天缓存
### 4.1 H5 SDK 与后端代理规则
H5 页面运行在 HTTPS 下,前端运行时代码不能直接请求:
```text
http://1.92.206.90:3001/app-api/...
http://1.92.206.90:9000/museum-assets/...
```
否则浏览器会拦截 mixed content表现为 SDK 后端接口请求失败或 3D 模型资源 `Failed to fetch`
前端 H5 构建环境应使用同源路径:
```dotenv
VITE_DATA_SOURCE_MODE=sdk
VITE_API_BASE_URL=/app-api
VITE_SGS_API_BASE_URL=/app-api
VITE_SGS_MAP_ID=1
VITE_SGS_SDK_SCRIPT_URL=/static/sgs-map-sdk/index.global.js
VITE_SGS_H5_ENGINE_URL=/h5-sdk
VITE_SGS_SDK_ORIGIN=https://guide.whaoyue.com:4433
```
`VITE_SGS_H5_ENGINE_URL=/h5-sdk` 仅在 H5 SDK 上游恢复后可用2026-07-22 公网响应为 `502`
Nginx 容器内的 `443 ssl` server 中必须包含以下代理规则。宿主机 `4433` 通过 Docker 映射进入容器 `443`
```nginx
location ^~ /app-api/ {
proxy_pass http://172.17.0.1:48080/yudao-server/app-api/;
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_http_version 1.1;
proxy_set_header Connection "";
proxy_connect_timeout 60s;
proxy_read_timeout 120s;
proxy_send_timeout 120s;
}
location ^~ /h5-sdk {
proxy_pass http://172.17.0.1:3001/h5-sdk;
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_http_version 1.1;
proxy_set_header Connection "";
proxy_connect_timeout 60s;
proxy_read_timeout 120s;
proxy_send_timeout 120s;
}
location ^~ /minio/museum-assets/ {
proxy_pass http://172.17.0.1:9000/museum-assets/;
proxy_set_header Host 172.17.0.1:9000;
expires 30d;
add_header Cache-Control "public";
}
location ^~ /museum-assets/ {
proxy_pass http://172.17.0.1:9000/museum-assets/;
proxy_set_header Host 172.17.0.1:9000;
expires 30d;
add_header Cache-Control "public";
}
```
每次修改后检查并重载:
```bash
docker exec nginx-server nginx -t
docker exec nginx-server nginx -s reload
```
检查配置:
```bash
docker exec nginx-server nginx -t
```
重载配置:
```bash
docker exec nginx-server nginx -s reload
```
重启容器:
```bash
docker restart nginx-server
```
### 4.2 Docker 端口映射
当前容器没有 compose 管理,端口映射保存在容器启动参数中。检查当前值:
```bash
docker inspect nginx-server --format '{{json .HostConfig.PortBindings}}'
```
期望结果包含:
```text
宿主机 8888 -> 容器 80
宿主机 4433 -> 容器 443
宿主机 7080 -> 容器 7080
宿主机 7081 -> 容器 7081
```
需要重建容器时,先保存检查信息并保留旧容器用于回滚:
```bash
ts=$(date +%Y%m%d%H%M%S)
docker inspect nginx-server \
> "/dmdata/nginx/backups/nginx-server-inspect-before-port-change-${ts}.json"
docker stop nginx-server
docker rename nginx-server "nginx-server-before-port-change-${ts}"
docker run -d \
--name nginx-server \
--restart unless-stopped \
-p 8888:80 \
-p 4433:443 \
-p 7080:7080 \
-p 7081:7081 \
-v /dmdata/nginx/conf.d:/etc/nginx/conf.d:ro \
-v /dmdata/nginx/ssl:/etc/nginx/ssl:ro \
-v /dmdata/nginx/html:/usr/share/nginx/html:ro \
-v /dmdata/nginx/logs:/var/log/nginx \
arm64v8/nginx:stable-alpine
```
服务器防火墙必须持久化放行新端口:
```bash
firewall-cmd --permanent --add-port=8888/tcp
firewall-cmd --permanent --add-port=4433/tcp
firewall-cmd --reload
```
启动后先执行 `nginx -t` 和第 6 节公网验证。全部通过后再删除已停止的旧容器。
## 5. SSL 证书
证书客户端:`acme.sh`
证书颁发机构Lets Encrypt
证书路径:
```bash
/dmdata/nginx/ssl/guide.whaoyue.com/fullchain.pem
/dmdata/nginx/ssl/guide.whaoyue.com/privkey.pem
```
证书信息:
```text
Subject: CN = guide.whaoyue.com
Issuer: Let's Encrypt YR2
Not Before: 2026-06-07 15:33:10 GMT
Not After: 2026-09-05 15:33:09 GMT
```
查看证书:
```bash
openssl x509 -in /dmdata/nginx/ssl/guide.whaoyue.com/fullchain.pem -noout -subject -issuer -dates
```
自动续期:
```bash
crontab -l | grep acme
```
当前续期任务:
```text
11 7 * * * "/root/.acme.sh"/acme.sh --cron --home "/root/.acme.sh" > /dev/null
```
当前证书配置使用 Webroot HTTP-01
```text
Le_Webroot='/dmdata/nginx/html/guide'
```
Lets Encrypt HTTP-01 固定验证公网 `80`,不会访问 `8888`。因此改为 `8888/4433`cron 存在不代表证书能够自动续期。必须在证书到期前完成以下任一方案:
1. 续期窗口临时恢复安全组、防火墙和 Docker 的公网 `80 -> 容器 80` 映射,续期完成后再关闭。
2.`acme.sh` 迁移为 DNS-01并配置可用的 DNS API 凭据。
当前证书到期时间为 `2026-09-05 15:33:09 GMT`,迁移或续期测试应提前完成。
`acme.sh` 已配置证书安装后的 reload 命令:
```bash
docker exec nginx-server nginx -s reload
```
满足公网 `80` 可验证或已迁移 DNS-01 后,才可执行手动续期测试:
```bash
/root/.acme.sh/acme.sh --cron --home /root/.acme.sh --force
```
测试后必须重新检查证书到期时间,并从公网验证 `4433`
```bash
openssl x509 -in /dmdata/nginx/ssl/guide.whaoyue.com/fullchain.pem -noout -dates
curl -I https://guide.whaoyue.com:4433/
```
## 6. 部署步骤复盘
1. 确认 DNS
```powershell
Resolve-DnsName guide.whaoyue.com -Type A
```
结果应指向:
```text
1.92.206.90
```
2. 确认公网端口:
```powershell
Test-NetConnection guide.whaoyue.com -Port 8888
Test-NetConnection guide.whaoyue.com -Port 4433
```
3. 创建静态测试页:
```bash
mkdir -p /dmdata/nginx/html/guide/.well-known/acme-challenge
```
4. 写入 Nginx 站点配置:
```bash
/dmdata/nginx/conf.d/guide.whaoyue.com.conf
```
5. 申请证书(以下是 2026-06-08 使用公网 `80` 完成首次签发的历史命令;当前端口映射下不可直接用于 HTTP-01 续期):
```bash
/root/.acme.sh/acme.sh --set-default-ca --server letsencrypt
/root/.acme.sh/acme.sh --issue --server letsencrypt -d guide.whaoyue.com -w /dmdata/nginx/html/guide --keylength 2048
```
6. 安装证书:
```bash
/root/.acme.sh/acme.sh --install-cert -d guide.whaoyue.com \
--key-file /dmdata/nginx/ssl/guide.whaoyue.com/privkey.pem \
--fullchain-file /dmdata/nginx/ssl/guide.whaoyue.com/fullchain.pem \
--reloadcmd "docker exec nginx-server nginx -s reload"
```
7. 验证访问:
```powershell
curl.exe -I http://guide.whaoyue.com:8888/
curl.exe -I https://guide.whaoyue.com:4433/
curl.exe -I https://guide.whaoyue.com:4433/app-api/gis/sdk/maps/1/manifest
curl.exe -I https://guide.whaoyue.com:4433/h5-sdk
curl.exe -I https://guide.whaoyue.com:4433/static/sgs-map-sdk/index.global.js
curl.exe -I https://guide.whaoyue.com:4433/museum-assets/optimized/20260617/draco_EXTERIOR.glb_1781708354536.glb
curl.exe -I https://guide.whaoyue.com:4433/minio/museum-assets/sgs-map/glb/1/V20260624104338_8f086/models/L1_draco.glb
```
期望结果:
```text
HTTP 301 -> https://guide.whaoyue.com:4433/
HTTPS 200 OK
/app-api/... 200 application/json
/h5-sdk 当前为 502修复上游或移除废弃规则前不得记为通过
/static/sgs-map-sdk/index.global.js 200 application/javascript
模型 GLB 200 model/gltf-binary
```
## 7. 已处理的问题
本节中的无端口 URL、404 和 Mixed Content 文本是端口调整前的历史故障原文;当前复测命令统一使用 `8888/4433`
### 7.1 Docker Nginx 配置校验失败
容器内 `nginx -t` 曾失败,原因是 Linux Docker 容器无法解析 `host.docker.internal`
处理方式:
-`/dmdata/nginx/conf.d/https.conf` 中的 `host.docker.internal` 代理目标改为 Docker 默认网关 `172.17.0.1`
- 重新执行 `docker exec nginx-server nginx -t`
- 配置校验通过后 reload Nginx
### 7.2 公网端口调整为 8888/4433
系统级 Nginx 已安装,但站点继续由 `nginx-server` 容器承载。2026-07-22 将宿主机映射从 `80:80``443:443` 调整为 `8888:80``4433:443`,并保留 `7080/7081` 映射。Nginx 容器内仍监听标准 `80/443`
HTTP server 的跳转目标必须显式包含新 HTTPS 端口:
```nginx
return 301 https://$host:4433$request_uri;
```
### 7.3 H5 SDK 接口请求混合内容
现象:
```text
Request URL http://1.92.206.90:3001/app-api/gis/sdk/maps/1/manifest
Referrer Policy strict-origin-when-cross-origin
```
页面实际运行在 `https://guide.whaoyue.com:4433/`,但构建产物中固化了 HTTP 后端地址,浏览器会拦截 mixed content 请求。若 Nginx 未配置 `/app-api/` 代理,改成同源路径后还会被 SPA 回退到 `index.html`
处理方式:
- 前端构建环境改为同源 `/app-api``/h5-sdk``/static/sgs-map-sdk/index.global.js`
- Nginx 增加 `/app-api/``/h5-sdk` 代理到宿主机 `3001`
- 重新构建并部署 H5 包
- 扫描构建产物,确认运行时代码不再包含 `1.92.206.90:3001`
验证:
```powershell
curl.exe -I https://guide.whaoyue.com:4433/app-api/gis/sdk/maps/1/manifest
curl.exe -I https://guide.whaoyue.com:4433/h5-sdk
curl.exe -I https://guide.whaoyue.com:4433/static/sgs-map-sdk/index.global.js
```
### 7.4 SDK 模型资源请求混合内容
现象:
- SDK 接口已经返回 `200 JSON`
- 页面仍提示 `3D 模型加载失败``Failed to fetch`
- 后端 bundle 中部分 `modelUrl``http://1.92.206.90:9000/museum-assets/...`
原因:
HTTPS 页面加载 HTTP MinIO 模型资源会被浏览器拦截;另外后端也可能返回 `/minio/museum-assets/...`,如果 Nginx 未配置该前缀,会落入 SPA 回退并返回 `index.html`
处理方式:
- Nginx 同时配置 `/museum-assets/``/minio/museum-assets/` 到 MinIO
- 前端对已知 `http://1.92.206.90:9000/museum-assets/...` 模型地址改写为同源 `/museum-assets/...`
- 重新构建并部署 H5 包
验证:
```powershell
curl.exe -I https://guide.whaoyue.com:4433/museum-assets/optimized/20260617/draco_EXTERIOR.glb_1781708354536.glb
curl.exe -I https://guide.whaoyue.com:4433/minio/museum-assets/sgs-map/glb/1/V20260624104338_8f086/models/L1_draco.glb
```
期望均返回:
```text
HTTP/1.1 200 OK
Content-Type: model/gltf-binary
```
### 7.5 展厅图标与占位图静态资源 404
现象:
```text
GET https://guide.whaoyue.com/static/icons/halls/biology.jpg 404
GET https://guide.whaoyue.com/static/icons/halls/evolution.jpg 404
GET https://guide.whaoyue.com/static/icons/halls/dinosaur.jpg 404
GET https://guide.whaoyue.com/static/icons/halls/earth.jpg 404
GET https://guide.whaoyue.com/static/icons/halls/human.jpg 404
GET https://guide.whaoyue.com/static/icons/halls/homeland.jpg 404
GET https://guide.whaoyue.com/static/icons/halls/universe.jpg 404
GET https://guide.whaoyue.com/static/exhibit-placeholder.jpg 404
```
原因:
- 源码目录存在 `static/icons/halls/*.jpg`,但 H5 构建后的补充复制脚本只复制了 `nav-assets``guide-data``sgs-map-sdk``three`,没有稳定复制 `static/icons`
- 页面与音频播放器中曾使用 `/static/exhibit-placeholder.jpg``/static/hall-placeholder.jpg` 作为兜底图,但静态目录里没有对应文件。
- 旧浏览器缓存的 chunk 可能仍请求旧占位图路径,因此即使新代码改用 SVG 兜底,也需要保留兼容文件。
处理方式:
- 更新 `frontend-miniapp/scripts/copy-h5-nav-assets.cjs`,将 `static/icons` 纳入 H5 构建产物复制清单。
- 新代码兜底图改为已存在且会随包发布的:
- `/static/icons/marker-exhibit.svg`
- `/static/icons/marker-hall.svg`
- 同时补充兼容文件:
- `/static/exhibit-placeholder.jpg`
- `/static/hall-placeholder.jpg`
- 重新执行 `pnpm type-check``pnpm build:h5` 并部署 H5 包。
验证:
```powershell
curl.exe -I https://guide.whaoyue.com:4433/static/icons/halls/biology.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/icons/halls/evolution.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/icons/halls/dinosaur.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/icons/halls/earth.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/icons/halls/human.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/icons/halls/homeland.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/icons/halls/universe.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/exhibit-placeholder.jpg
curl.exe -I https://guide.whaoyue.com:4433/static/hall-placeholder.jpg
```
期望返回:
```text
HTTP/1.1 200 OK
Content-Type: image/jpeg
```
其中 SVG 兜底图验证:
```powershell
curl.exe -I https://guide.whaoyue.com:4433/static/icons/marker-exhibit.svg
curl.exe -I https://guide.whaoyue.com:4433/static/icons/marker-hall.svg
```
期望返回:
```text
HTTP/1.1 200 OK
Content-Type: image/svg+xml
```
### 7.6 TTS 语音播放 Mixed Content
现象:
```text
Mixed Content: The page at 'https://guide.whaoyue.com/#/pages/exhibit/detail?id=715805000000000009&tab=explain'
was loaded over HTTPS, but requested an insecure audio file
'http://1.92.206.90:9000/tts-audio/audio/2026/06/30/947228d3e5174f3697f22cceac30075e.mp3'.
This request has been blocked; the content must be served over HTTPS.
详情音频不可播放: 音频加载失败,当前提供图文讲解。
H5 音频播放被拦截或失败: NotSupportedError: Failed to load because no supported source was found.
```
原因:
- 页面运行在 HTTPS 下,但后端语音播放接口返回的 `playUrl` 指向 `http://1.92.206.90:9000/tts-audio/...`
- 浏览器不会把 IP 地址 HTTP 音频自动升级为 HTTPS因此音频请求被 mixed content 策略拦截。
- 服务器 Nginx 已配置 `/tts-audio/` 到 MinIO 的 HTTPS 同源代理,因此核心修复点是前端 URL 归一化,而不是新增代理。
当前 Nginx 代理规则应包含:
```nginx
location ^~ /tts-audio/ {
proxy_pass http://172.17.0.1:9000/tts-audio/;
proxy_set_header Host 172.17.0.1:9000;
proxy_http_version 1.1;
proxy_set_header Connection "";
proxy_set_header Range $http_range;
proxy_set_header If-Range $http_if_range;
add_header Access-Control-Allow-Origin "*" always;
add_header Access-Control-Allow-Methods "GET, HEAD, OPTIONS" always;
add_header Access-Control-Allow-Headers "Range, Origin, Accept, Content-Type" always;
add_header Access-Control-Expose-Headers "Content-Length, Content-Range, Accept-Ranges" always;
add_header Cache-Control "public, max-age=604800" always;
}
```
处理方式:
- 更新前端统一公共 URL 归一化逻辑 `normalizeSameOriginPublicUrl`
- `http://1.92.206.90:9000/museum-assets/...` -> `/museum-assets/...`
- `http://1.92.206.90:9000/tts-audio/...` -> `/tts-audio/...`
- `http://47.120.48.148:19000/nhm/audio/...` -> `/nhm/audio/...`
- 确认 `AudioPlayInfoRepository`、后端讲解数据 adapter、静态导览 adapter 均通过该统一方法处理音频 URL。
- 重新构建并部署 H5 包。
- 扫描线上运行时代码,确认不再包含 `http://1.92.206.90:9000/tts-audio` 或其他 MinIO HTTP 直连。
验证时不要复用已经删除的历史 MinIO 对象。先从当前播放信息接口取得 `playUrl`
```powershell
curl.exe "https://guide.whaoyue.com:4433/app-api/gis/guide/audio/play-info?targetType=STOP&targetId=865546638960193536&lang=zh-CN"
curl.exe -I https://guide.whaoyue.com:4433/minio/museum-assets/tts-audio/audio/2026/07/17/63058096489b4f4aa516fb07fe4a1144.mp3
```
期望返回:
```text
HTTP/1.1 200 OK
Content-Type: audio/mpeg
Accept-Ranges: bytes
```
线上运行时代码扫描:
```bash
grep -R 'http://1\.92\.206\.90:9000/tts-audio\|http://1\.92\.206\.90:9000' \
-n /dmdata/nginx/html/guide/assets /dmdata/nginx/html/guide/index.html || true
```
期望无输出。
## 8. 回滚方式
配置备份目录:
```bash
/dmdata/nginx/backups/20260608002938
/dmdata/nginx/backups/20260608003215
/dmdata/nginx/backups/guide.whaoyue.com.conf-before-port-change-20260722175845
/dmdata/nginx/backups/nginx-server-inspect-before-port-change-20260722175845.json
```
回滚配置示例:
```bash
cp -a /dmdata/nginx/backups/20260608003215/conf.d/* /dmdata/nginx/conf.d/
docker exec nginx-server nginx -t
docker exec nginx-server nginx -s reload
```
如需回滚 2026-07-22 的端口调整,应根据检查快照重建容器为 `80:80``443:443``7080:7080``7081:7081`,同时恢复站点配置中的标准 HTTPS 跳转。执行前必须再次备份当前容器检查信息和站点配置。
如需移除本域名站点:
```bash
rm -f /dmdata/nginx/conf.d/guide.whaoyue.com.conf
docker exec nginx-server nginx -t
docker exec nginx-server nginx -s reload
```
## 9. 运行维护检查清单
日常检查:
```bash
docker ps --filter name=nginx-server
docker exec nginx-server nginx -t
curl -I http://guide.whaoyue.com:8888/
curl -I https://guide.whaoyue.com:4433/
curl -I https://guide.whaoyue.com:4433/app-api/gis/sdk/maps/1/manifest
curl -I https://guide.whaoyue.com:4433/h5-sdk
curl -I https://guide.whaoyue.com:4433/static/sgs-map-sdk/index.global.js
curl -I https://guide.whaoyue.com:4433/minio/museum-assets/sgs-map/glb/1/V20260624104338_8f086/models/L1_draco.glb
curl -I https://guide.whaoyue.com:4433/minio/museum-assets/tts-audio/audio/2026/07/17/63058096489b4f4aa516fb07fe4a1144.mp3
curl -I https://guide.whaoyue.com:4433/static/icons/halls/biology.jpg
curl -I https://guide.whaoyue.com:4433/static/exhibit-placeholder.jpg
```
查看日志:
```bash
tail -f /dmdata/nginx/logs/guide-http-access.log
tail -f /dmdata/nginx/logs/guide-https-access.log
tail -f /dmdata/nginx/logs/guide-https-error.log
```
证书检查:
```bash
/root/.acme.sh/acme.sh --list
openssl x509 -in /dmdata/nginx/ssl/guide.whaoyue.com/fullchain.pem -noout -subject -issuer -dates
```
## 10. 验收记录
2026-06-08 验收结果:
| 检查项 | 结果 | 证据 |
| --- | --- | --- |
| DNS A 记录 | 通过 | `guide.whaoyue.com -> 1.92.206.90` |
| 80 端口公网连通 | 通过 | `Test-NetConnection guide.whaoyue.com -Port 80 = True` |
| 443 端口公网连通 | 通过 | `Test-NetConnection guide.whaoyue.com -Port 443 = True` |
| HTTP 跳转 | 通过 | `HTTP/1.1 301 Moved Permanently` |
| HTTPS 静态页 | 通过 | `HTTP/1.1 200 OK` |
| Nginx 配置 | 通过 | `nginx: configuration file /etc/nginx/nginx.conf test is successful` |
| SSL 证书 | 通过 | `CN = guide.whaoyue.com`, Lets Encrypt |
| 自动续期 | 通过 | `acme.sh` cron 已存在 |
2026-06-26 SDK 后端与模型资源修复验收:
| 检查项 | 结果 | 证据 |
| --- | --- | --- |
| SDK manifest 同源接口 | 通过 | `/app-api/gis/sdk/maps/1/manifest -> 200 application/json` |
| H5 SDK 基座 | 通过 | `/h5-sdk -> 200 text/html` |
| SDK 脚本 | 通过 | `/static/sgs-map-sdk/index.global.js -> 200 application/javascript` |
| MinIO `/museum-assets/` 模型 | 通过 | `draco_EXTERIOR.glb_1781708354536.glb -> 200 model/gltf-binary` |
| MinIO `/minio/museum-assets/` 模型 | 通过 | `L1_draco.glb -> 200 model/gltf-binary` |
| 混合内容引用 | 通过 | H5 运行时代码无 `1.92.206.90:3001``1.92.206.90:9000` |
2026-06-30 静态图标、占位图与 TTS 音频修复验收:
| 检查项 | 结果 | 证据 |
| --- | --- | --- |
| 展厅图标资源 | 通过 | `/static/icons/halls/biology.jpg` 等展厅图标 -> `200 image/jpeg` |
| 展品占位图兼容资源 | 通过 | `/static/exhibit-placeholder.jpg -> 200 image/jpeg` |
| 展厅占位图兼容资源 | 通过 | `/static/hall-placeholder.jpg -> 200 image/jpeg` |
| SVG 兜底图资源 | 通过 | `/static/icons/marker-exhibit.svg -> 200 image/svg+xml` |
| TTS 音频 HTTPS 代理 | 通过 | `/tts-audio/audio/2026/06/30/947228d3e5174f3697f22cceac30075e.mp3 -> 200 audio/mpeg` |
| TTS CORS/Range 响应 | 通过 | 响应包含 `Access-Control-Allow-Origin: *``Accept-Ranges: bytes` |
| 混合内容引用 | 通过 | H5 运行时代码无 `http://1.92.206.90:9000/tts-audio`、无 `http://1.92.206.90:9000` |
2026-07-22 公网端口调整验收:
| 检查项 | 结果 | 证据 |
| --- | --- | --- |
| Docker HTTP 映射 | 通过 | `0.0.0.0:8888 -> 80/tcp` |
| Docker HTTPS 映射 | 通过 | `0.0.0.0:4433 -> 443/tcp` |
| 既有端口保留 | 通过 | `7080/7081 -> 7080/7081` |
| 8888 端口公网连通 | 通过 | `http://guide.whaoyue.com:8888/ -> 301` |
| HTTP 跳转目标 | 通过 | `Location: https://guide.whaoyue.com:4433/` |
| 4433 首页 | 通过 | `https://guide.whaoyue.com:4433/ -> 200` |
| 4433 API 代理 | 通过 | `/app-api/gis/hall/list -> 200 application/json` |
| 域名校验文件 | 通过 | `/gpL0svkeao.txt -> 200 text/plain` |
| 当前语音对象 | 通过 | 播放信息返回的 `/minio/museum-assets/tts-audio/...mp3 -> 200 audio/mpeg` |
| H5 SDK 基座 | 阻塞 | `/h5-sdk -> 502`,不得沿用 2026-06-26 的 200 结论 |
| Nginx 配置 | 通过 | `nginx: configuration file /etc/nginx/nginx.conf test is successful` |
| 证书续期 | 待处理 | 当前 Webroot HTTP-01 不能通过公网 `8888` 完成验证,需恢复 `80` 或迁移 DNS-01 |