从零搭建微信小程序后端:域名、备案、HTTPS 证书与 Nginx(以 perfecttools.top 为例)
从零搭建微信小程序后端:域名、备案、HTTPS 证书与 Nginx(以 perfecttools.top 为例)
一、背景
微信小程序强制要求所有网络请求通过 HTTPS 协议,且服务器域名必须完成 ICP 备案。对于刚接触的开发者,从注册域名、DNS 解析、备案、申请 SSL 证书,到配置 Nginx 反向代理后端服务,最后在小程序后台设置合法域名,整个链路节点多且跨平台。
本文以华为云 Ubuntu 服务器 + 腾讯云注册的perfecttools.top域名为例,详细记录完整部署流程。特别使用acme.sh工具申请和管理 Let’s Encrypt 免费证书,并实现自动续期。同时,借助子域名划分不同功能模块(如api.perfecttools.top、admin.perfecttools.top),让整体架构更清晰易维护。
二、发展
早期微信小程序对 HTTPS 的严格要求增加了部署门槛,但 Let’s Encrypt 等免费证书的出现大幅降低了成本。acme.sh作为纯 Shell 实现的 ACME 客户端,安装零依赖、配置简单、自动续期稳定,成为很多运维人员的首选。Nginx 凭借其高性能和灵活的代理能力,一直是 SSL 终结和反向代理的事实标准。如今,这套组合已成为个人开发者和小型团队快速上线小程序的标配方案。
三、目的
本文将以一个微信小程序 demo 为主线,串联以下完整流程:
- 在腾讯云注册域名
perfecttools.top并划分子域名 - 配置 DNS 解析,将不同子域名指向华为云服务器
- 提交 ICP 备案
- 在华为云 ECS 上安装 Nginx 并部署后端服务
- 使用acme.sh申请免费 SSL 证书并配置自动续期
- 配置 Nginx 启用 HTTPS 并按子域名反向代理到对应后端模块
- 在小程序后台配置合法域名,并通过
wx.request进行接口调用 - 验证整条链路
四、核心概念与架构
4.1 核心术语
- 子域名:在主域名前添加前缀,用于划分不同服务模块,如
api.perfecttools.top提供 API,admin.perfecttools.top提供管理后台。 - A 记录:DNS 中将域名指向 IPv4 地址的记录。
- ICP 备案:中国大陆境内提供 Web 服务的网站必须完成工信部备案。
- ACME 协议:自动化证书管理环境协议,Let’s Encrypt 使用该协议验证域名所有权并签发证书。
- acme.sh:一款轻量 Shell 脚本,支持多种 DNS API 自动完成域名验证,实现证书自动申请和续期。
- Nginx 反向代理:将 HTTPS 请求解密后转发给后端应用,并将响应加密返回客户端。
- SSL 终结:在 Nginx 层面处理 SSL 加密和解密,后端服务只需处理 HTTP。
4.2 整体架构图
4.3 核心业务流程
Q&A
Q1:为什么小程序必须使用 HTTPS?
A:微信要求所有网络请求加密传输,防止中间人攻击和数据泄露,保护用户隐私。
Q2:acme.sh 与 Certbot 的主要区别?
A:acme.sh 无需 root 权限,零系统依赖,对 DNS API 的支持更丰富,配置更轻量,尤其适合自动化场景。
五、详细操作步骤
5.1 域名申请与子域名规划
在腾讯云注册perfecttools.top,并规划以下子域名:
| 子域名 | 功能 | 后端端口 | 说明 |
|---|---|---|---|
api.perfecttools.top | API 接口 | 8080 | 小程序调用的主接口 |
admin.perfecttools.top | 管理后台 | 8081 | 内部管理界面 |
static.perfecttools.top | 静态资源 | - | 直接由 Nginx 返回 |
@(根域名) | 官网首页 | - | 静态页面 |
5.2 DNS 解析
在腾讯云 DNS 解析控制台添加 A 记录:
- 主机记录:
api,类型 A,值:华为云服务器公网 IP - 主机记录:
admin,类型 A,值:同上 - 主机记录:
static,类型 A,值:同上 - 主机记录:
@,类型 A,值:同上
待解析生效后,可通过ping api.perfecttools.top验证。
5.3 ICP 备案
在腾讯云备案系统提交备案信息,填写网站名称、用途等,上传身份证件。一般需 15~20 个工作日。备案通过后会获得备案号,需要在网站底部展示。
5.4 服务器环境搭建(华为云 Ubuntu 20.04)
# 更新系统sudoaptupdate&&sudoaptupgrade-y# 安装 Nginxsudoaptinstallnginx-y# 开放防火墙端口sudoufw allow'Nginx Full'# 华为云安全组需同时放行 80 和 443 端口# 启动 Nginxsudosystemctlenablenginxsudosystemctl start nginx5.5 部署后端服务示例
假设我们有两个 Spring Boot 服务:
api-service.jar监听 8080admin-service.jar监听 8081
为每个服务创建 systemd 管理文件:
# /etc/systemd/system/api-service.service[Unit]Description=API ServiceAfter=network.target[Service]ExecStart=/usr/bin/java-jar/opt/apps/api-service.jarUser=www-dataRestart=always[Install]WantedBy=multi-user.target类似地创建admin-service.service,然后启动:
sudosystemctl daemon-reloadsudosystemctlenableapi-service admin-servicesudosystemctl start api-service admin-service5.6 使用 acme.sh 申请 SSL 证书
安装 acme.sh
curlhttps://get.acme.sh|sh-semail=your-email@example.comsource~/.bashrc配置 DNS API(以腾讯云为例)
acme.sh 支持数百个 DNS 服务商的 API 自动验证。对于腾讯云,需要设置DNSPod API Token(腾讯云 DNSPod 与腾讯云账户互通)。
exportDP_Id="你的DNSPod ID"exportDP_Key="你的DNSPod Token"申请泛域名证书(推荐一次申请覆盖所有子域名)
acme.sh--issue--dnsdns_dp-dperfecttools.top-d'*.perfecttools.top'dns_dp是 acme.sh 内置的腾讯云 DNSPod 接口。完成后证书保存在~/.acme.sh/perfecttools.top_ecc/目录(默认使用 ECC 密钥)。
安装证书到 Nginx 使用的目录
sudomkdir-p/etc/nginx/ssl/perfecttools.top acme.sh --install-cert-dperfecttools.top-d'*.perfecttools.top'\--key-file /etc/nginx/ssl/perfecttools.top/privkey.pem\--fullchain-file /etc/nginx/ssl/perfecttools.top/fullchain.pem\--reloadcmd"sudo systemctl reload nginx"该命令将证书复制到/etc/nginx/ssl/目录,并在证书更新时自动重载 Nginx。
自动续期
acme.sh 安装时已自动添加 cron 任务,每天检查证书有效期,到期前 60 天自动续期。可通过以下命令查看:
crontab-l|grepacme.sh5.7 Nginx 配置 HTTPS 与反向代理
编辑/etc/nginx/sites-available/perfecttools.top:
# HTTP 跳转到 HTTPS server { listen 80; server_name perfecttools.top *.perfecttools.top; return 301 https://$host$request_uri; } # API 子域名 server { listen 443 ssl http2; server_name api.perfecttools.top; ssl_certificate /etc/nginx/ssl/perfecttools.top/fullchain.pem; ssl_certificate_key /etc/nginx/ssl/perfecttools.top/privkey.pem; ssl_trusted_certificate /etc/nginx/ssl/perfecttools.top/fullchain.pem; ssl_protocols TLSv1.2 TLSv1.3; ssl_ciphers HIGH:!aNULL:!MD5; ssl_prefer_server_ciphers on; location / { proxy_pass http://127.0.0.1:8080; 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 https; } } # Admin 管理后台 server { listen 443 ssl http2; server_name admin.perfecttools.top; # 复用相同证书(因为泛域名证书已覆盖) ssl_certificate /etc/nginx/ssl/perfecttools.top/fullchain.pem; ssl_certificate_key /etc/nginx/ssl/perfecttools.top/privkey.pem; ssl_trusted_certificate /etc/nginx/ssl/perfecttools.top/fullchain.pem; ssl_protocols TLSv1.2 TLSv1.3; ssl_ciphers HIGH:!aNULL:!MD5; ssl_prefer_server_ciphers on; location / { proxy_pass http://127.0.0.1:8081; 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 https; } } # 根域名静态页面 server { listen 443 ssl http2; server_name perfecttools.top; ssl_certificate /etc/nginx/ssl/perfecttools.top/fullchain.pem; ssl_certificate_key /etc/nginx/ssl/perfecttools.top/privkey.pem; ssl_trusted_certificate /etc/nginx/ssl/perfecttools.top/fullchain.pem; ssl_protocols TLSv1.2 TLSv1.3; ssl_ciphers HIGH:!aNULL:!MD5; root /var/www/html; index index.html; }启用站点并重载 Nginx:
sudoln-s/etc/nginx/sites-available/perfecttools.top /etc/nginx/sites-enabled/sudonginx-t&&sudosystemctl reload nginx5.8 微信小程序配置
小程序后台设置合法域名
登录微信公众平台 -> 开发 -> 开发管理 -> 服务器域名,在request 合法域名中添加:
https://api.perfecttools.top(每月可修改 5 次,且必须为备案域名)
小程序端调用示例
// 在小程序的 app.js 或页面逻辑中wx.request({url:'https://api.perfecttools.top/greeting',method:'GET',success(res){console.log('服务器返回:',res.data);},fail(err){console.error('请求失败',err);}})后端提供测试接口
@RestControllerpublicclassGreetingController{@GetMapping("/greeting")publicStringgreeting(){return"Hello from API service!";}}使用微信开发者工具编译预览,即可看到请求成功返回数据。
5.9 验证全链路
- 浏览器直接访问
https://api.perfecttools.top/greeting,应显示 JSON 或字符串。 - 使用
curl -v https://api.perfecttools.top/greeting检查 SSL 握手是否成功。 - 检查
acme.sh状态:acme.sh --list列出所有证书和到期时间。 - 在微信开发者工具中查看 Network 面板,确认请求地址为合法域名且无证书错误。
六、高性能设计
6.1 HTTP/2 支持
Nginx 配置中已添加http2,多路复用减少延迟。
6.2 Gzip 压缩
gzip on; gzip_types text/plain application/json; gzip_min_length 1000;6.3 会话缓存与 OCSP 装订
ssl_session_cache shared:SSL:10m; ssl_session_timeout 10m; ssl_stapling on; ssl_stapling_verify on; resolver 8.8.8.8 114.114.114.114 valid=300s;6.4 缓冲区调优
proxy_buffer_size 16k; proxy_buffers 4 64k; proxy_busy_buffers_size 128k;七、可靠性与安全性
7.1 acme.sh 自动续期保障
acme.sh 的 cron 任务默认每天 0 点检查,到期前自动续期并执行--reloadcmd。若担心漏续,可监控证书到期时间(如通过acme.sh --list输出解析)。
7.2 强制 HTTPS 与 HSTS
在 SSL server 块中添加:
add_header Strict-Transport-Security "max-age=63072000" always;7.3 权限控制
- SSL 私钥目录
ssl/权限设置为 700,文件 600。 - 后端应用与 Nginx 通过 127.0.0.1 通信,不暴露公网端口。
7.4 限制访问频率
limit_req_zone $binary_remote_addr zone=api_limit:10m rate=20r/s; server { location / { limit_req zone=api_limit burst=50 nodelay; # ... } }八、进阶:多模块与扩展
8.1 增加新子域名的步骤
- DNS 添加对应 A 记录。
- 如果需要独立证书,可单独用 acme.sh 申请;但因为已有泛域名证书,直接复用即可。
- 在 Nginx 中新增
server块,配置代理或静态目录。 - 重载 Nginx。
8.2 动态路由与 Nacos 集成
若后端采用微服务框架,Nginx 可以仅作为 API 网关的统一入口,再通过 Spring Cloud Gateway 将请求路由到不同微服务,实现更精细的控制。
九、生产环境最佳实践
- 备份与恢复:定期备份
/etc/letsencrypt/或 acme.sh 的证书目录,以及 Nginx 配置文件。 - 日志集中管理:接入 ELK 或云日志服务,监控 Nginx 访问和错误日志。
- 自动化部署:使用 CI/CD 工具更新后端 jar 包后自动重启 systemd 服务。
- 监控告警:配置 UptimeRobot 探测 API 接口可用性,设置证书到期前 30 天邮件提醒(通过 acme.sh 的
--renew-hook脚本实现)。 - 安全更新:定期
sudo apt update && sudo apt upgrade更新系统及 Nginx 版本。
十、总结与推荐阅读
从域名注册、备案、DNS 解析,到 acme.sh 自动申请泛域名 SSL 证书,再到 Nginx 反向代理后端服务,最后在小程序后台完成域名绑定,整个过程虽然涉及多个平台,但每一步都有章可循。利用泛域名证书和 acme.sh 的自动续期,可以大大降低运维负担;通过子域名划分不同功能模块,让架构更清晰,也为未来扩展留足了空间。
【额外内容】
小程序备案、ICP备案等国家审批时候,同时只能有一个提交审批另一个会被立即打回。
推荐阅读:
- acme.sh 官方 Wiki
- Let’s Encrypt 官方文档
- Nginx 入门指南
- 微信小程序网络请求详解