> ## Content Index
> Fetch the complete content index at: https://isoziyuan.com/llms.txt
> Use this file to discover other available public pages before exploring further.

# Docker 部署 WordPress 联盟网站实战：性能优化、内容变现与转化追踪
- URL: https://isoziyuan.com/p/100107/
- Published: 2026-08-27T17:15:54.000Z
- Updated: 2026-08-27T17:15:54.000Z
- Author: Isoziyuan
- Tags: WordPress, Docker, 联盟营销, 建站

## 先明确：网站上线不等于开始赚钱

用 Docker 部署 WordPress 并不困难，真正决定联盟网站能否产生收入的，是后续几个环节能否形成闭环：

1. 选择有真实需求、竞争程度可承受的利基市场；
2. 建立稳定、安全且加载速度足够快的网站；
3. 发布能够帮助用户做购买决策的内容；
4. 合规地插入联盟链接并记录点击；
5. 结合联盟平台的订单数据分析实际转化；
6. 持续更新内容，而不是批量生成低价值页面。

联盟营销通常按照有效销售、注册、试用或其他指定行为结算。新网站前期没有流量和信任，收入可能长期为零，因此不应把 Docker 或 WordPress 理解成“自动赚钱工具”。

更准确地说，Docker 解决的是部署和维护问题，WordPress 解决的是内容管理问题，而盈利仍然依赖选题、流量质量、购买意图和商业匹配。

可以用下面的简化公式判断问题出在哪里：

```text
预估收入 = 有购买意图的访问量
        × 联盟链接点击率
        × 商家页面转化率
        × 单次有效转化佣金

```

如果网站没有精准访问量，仅提高按钮点击率通常不会产生稳定收入。

---

## 一、为什么用 Docker 搭建 WordPress 联盟网站

直接在服务器上安装 PHP、数据库和 Web 服务器也能运行 WordPress，但 Docker 更适合希望长期维护多个利基网站的人。

主要优势包括：

- WordPress、数据库、Redis 和反向代理相互隔离；
- 更换服务器时可以迁移配置文件和数据卷；
- PHP 或数据库升级路径相对清晰；
- 测试环境与生产环境更容易保持一致；
- 可以针对单个网站进行备份、停止和重建；
- 减少不同网站之间的软件版本冲突。

不过，Docker 并不会自动解决以下问题：

- WordPress 插件漏洞；
- 数据库与上传文件备份；
- 域名解析和 HTTPS；
- 页面缓存及图片优化；
- 联盟平台政策合规；
- 内容质量和搜索流量。

因此，本文使用一套相对简单的生产架构：

```text
访问者
  ↓
Caddy（HTTPS、压缩、反向代理）
  ↓
WordPress + Apache
  ├── MariaDB（文章、配置、用户数据）
  └── Redis（对象缓存）

```

MariaDB、Redis 和 WordPress 均不直接暴露到公网，只有 Caddy 对外开放 80、443 端口。

---

## 二、部署前需要准备什么

建议准备以下资源：

- 一台能够运行 Docker 的 Linux 服务器；
- 一个已经注册的域名；
- 可修改域名 DNS 记录的权限；
- 服务器公网 IPv4，或者正确配置的 IPv6；
- 一个用于接收系统通知的管理员邮箱；
- 基础的 SSH 和命令行操作能力。

服务器至少需要为系统、数据库和 PHP 保留合理的内存空间。如果打算安装大量页面构建器、统计插件或图片处理插件，资源消耗会明显增加。不要只根据“最低配置”选择服务器，应观察真实运行时的内存、CPU 和磁盘占用。

以下示例以 Ubuntu 或 Debian 系统为思路。安装 Docker 时应优先按照 Docker 官方文档添加软件源，不要直接执行来源不明的一键安装脚本。

安装完成后检查：

```bash
docker --version
docker compose version

```

创建项目目录：

```bash
sudo mkdir -p /opt/affiliate-wordpress
sudo chown -R "$USER":"$USER" /opt/affiliate-wordpress
cd /opt/affiliate-wordpress

```

最终目录结构如下：

```text
/opt/affiliate-wordpress/
├── compose.yaml
├── .env
└── Caddyfile

```

---

## 三、配置域名、防火墙与服务器时间

先在域名服务商处添加 DNS 记录：

```text
A      example.com       服务器 IPv4
A      www.example.com   服务器 IPv4

```

如果服务器没有正确配置 IPv6，不要随意添加 AAAA 记录，否则部分访问者可能连接失败。

防火墙至少需要允许：

- SSH 端口；
- TCP 80；
- TCP 443；
- 如需 HTTP/3，可根据实际环境放行 UDP 443。

数据库的 3306 端口和 Redis 的 6379 端口不应对公网开放。

确认服务器时间同步正常：

```bash
timedatectl status

```

时间错误可能影响 HTTPS 证书申请、日志分析和定时任务。

---

## 四、使用 Docker Compose 部署 WordPress

### 1\. 创建环境变量文件

在项目目录中创建 `.env`：

```bash
nano .env

```

示例内容：

```dotenv
DOMAIN=example.com

DB_NAME=wordpress
DB_USER=wordpress
DB_PASSWORD=替换为高强度数据库用户密码
DB_ROOT_PASSWORD=替换为另一个高强度根密码

```

密码应随机生成，并避免与 WordPress 管理员密码重复。例如可以使用：

```bash
openssl rand -base64 36

```

限制文件读取权限：

```bash
chmod 600 .env

```

需要注意，Compose 会对某些特殊字符进行变量替换。保存后应运行 `docker compose config` 检查解析结果，避免密码因为 `$` 等字符被意外处理。也可以进一步改用 Docker secrets，但对于单机入门部署，受限权限的 `.env` 更容易维护。

### 2\. 创建 Compose 配置

创建 `compose.yaml`：

```yaml
services:
  database:
    image: mariadb:11.4
    restart: unless-stopped
    environment:
      MARIADB_DATABASE: ${DB_NAME}
      MARIADB_USER: ${DB_USER}
      MARIADB_PASSWORD: ${DB_PASSWORD}
      MARIADB_ROOT_PASSWORD: ${DB_ROOT_PASSWORD}
    volumes:
      - db_data:/var/lib/mysql
    networks:
      - backend
    healthcheck:
      test: ["CMD", "healthcheck.sh", "--connect", "--innodb_initialized"]
      interval: 10s
      timeout: 5s
      retries: 10

  redis:
    image: redis:7-alpine
    restart: unless-stopped
    command: ["redis-server", "--appendonly", "yes"]
    volumes:
      - redis_data:/data
    networks:
      - backend

  wordpress:
    image: wordpress:php8.3-apache
    restart: unless-stopped
    depends_on:
      database:
        condition: service_healthy
    environment:
      WORDPRESS_DB_HOST: database:3306
      WORDPRESS_DB_NAME: ${DB_NAME}
      WORDPRESS_DB_USER: ${DB_USER}
      WORDPRESS_DB_PASSWORD: ${DB_PASSWORD}
      WORDPRESS_CONFIG_EXTRA: |
        define('WP_REDIS_HOST', 'redis');
        define('WP_REDIS_PORT', 6379);
        define('DISABLE_WP_CRON', true);
        define('DISALLOW_FILE_EDIT', true);
        define('WP_POST_REVISIONS', 10);
        define('EMPTY_TRASH_DAYS', 14);
    volumes:
      - wp_data:/var/www/html
    networks:
      - frontend
      - backend

  caddy:
    image: caddy:2-alpine
    restart: unless-stopped
    depends_on:
      - wordpress
    ports:
      - "80:80"
      - "443:443"
      - "443:443/udp"
    environment:
      DOMAIN: ${DOMAIN}
    volumes:
      - ./Caddyfile:/etc/caddy/Caddyfile:ro
      - caddy_data:/data
      - caddy_config:/config
    networks:
      - frontend

networks:
  frontend:
  backend:
    internal: true

volumes:
  db_data:
  redis_data:
  wp_data:
  caddy_data:
  caddy_config:

```

这里使用的是明确版本系列，而不是完全不受控制的 `latest` 标签。正式运营后，不应在没有备份和测试的情况下随意升级主版本。

如果部署时官方镜像已经调整了可用标签，应在 Docker Hub 官方镜像页面核对，而不是盲目替换成第三方镜像。

### 3\. 配置 Caddy

创建 `Caddyfile`：

```caddyfile
{$DOMAIN}, www.{$DOMAIN} {
    encode zstd gzip

    reverse_proxy wordpress:80

    header {
        X-Content-Type-Options nosniff
        Referrer-Policy strict-origin-when-cross-origin
        -Server
    }

    log {
        output stdout
        format json
    }
}

```

Caddy 会在域名解析正确、80 和 443 端口可访问的情况下自动申请并续期 HTTPS 证书。

如果希望将 `www` 永久跳转到不带 `www` 的域名，可以改成：

```caddyfile
www.{$DOMAIN} {
    redir https://{$DOMAIN}{uri} permanent
}

{$DOMAIN} {
    encode zstd gzip
    reverse_proxy wordpress:80

    header {
        X-Content-Type-Options nosniff
        Referrer-Policy strict-origin-when-cross-origin
        -Server
    }

    log {
        output stdout
        format json
    }
}

```

站点正式收录前就应确定主域名形式，避免后期产生重复网址和不必要的重定向。

### 4\. 启动服务

先检查配置：

```bash
docker compose config

```

确认无误后启动：

```bash
docker compose up -d

```

查看状态：

```bash
docker compose ps

```

查看日志：

```bash
docker compose logs -f caddy

```

或者查看 WordPress 日志：

```bash
docker compose logs -f wordpress

```

访问：

```text
https://example.com

```

然后按照页面提示完成 WordPress 初始化。

管理员用户名不要使用 `admin`，密码应独立保存到密码管理器中。管理员邮箱必须能够正常接收重置密码邮件；如果服务器没有邮件发送能力，可以配置可信的 SMTP 服务，但不要把邮箱密码直接写进公开代码或文章。

---

## 五、用真实定时任务替代 WP-Cron

WordPress 默认的 WP-Cron 依靠页面访问触发。新联盟网站访问量较低时，定时发布、缓存清理和插件任务可能延迟；流量较高时，又可能出现重复触发和额外开销。

前面的配置已经加入：

```php
define('DISABLE_WP_CRON', true);

```

因此需要在宿主机添加系统定时任务：

```bash
crontab -e

```

每五分钟执行一次：

```cron
*/5 * * * * cd /opt/affiliate-wordpress && /usr/bin/docker compose exec -T wordpress php /var/www/html/wp-cron.php >/dev/null 2>&1

```

先手动测试：

```bash
cd /opt/affiliate-wordpress
docker compose exec -T wordpress php /var/www/html/wp-cron.php

```

如果 Docker 路径不同，使用下面的命令确认：

```bash
which docker

```

---

## 六、WordPress 初始化后的必要设置

### 固定链接

在后台进入：

```text
设置 → 固定链接

```

通常可选择“文章名”，例如：

```text
https://example.com/best-running-shoes/

```

不建议在网址中堆砌无意义日期、分类层级和关键词。上线后也不要频繁改变固定链接，否则必须配置 301 重定向。

### 时区与站点语言

进入：

```text
设置 → 常规

```

设置正确时区。不要只依赖服务器 UTC 时间，否则定时发布、统计日期和日志对照容易混乱。

### 搜索引擎可见性

建站期间可以暂时阻止搜索引擎索引，但正式发布前必须检查：

```text
设置 → 阅读 → 建议搜索引擎不索引本站点

```

如果该选项一直被勾选，网站可能长期无法正常进入搜索结果。

### 用户权限

日常发布内容可使用“编辑”或“作者”账号，管理员账号只用于升级、插件配置和系统维护。

不要与外包写手共享管理员密码。合作终止后，应及时删除账号或降低权限。

---

## 七、联盟网站应该安装哪些插件

插件不是越多越好。每个插件都可能增加 PHP 执行时间、数据库查询、前端脚本或安全风险。

建议按功能选择，而不是堆叠同类插件。

### 基础功能类别

| 功能         | 是否建议     | 注意事项             |
| ---------- | -------- | ---------------- |
| SEO 与站点地图  | 建议       | 同类插件只保留一个        |
| 页面缓存       | 建议       | 根据服务器架构选择        |
| Redis 对象缓存 | 访问量增加后建议 | 需与 Redis 服务连接    |
| 图片压缩与格式转换  | 建议       | 检查原图备份和兼容性       |
| 备份         | 必须       | 备份必须复制到服务器之外     |
| 安全登录保护     | 建议       | 不要依赖隐藏登录地址代替安全措施 |
| 统计与点击追踪    | 按需       | 注意隐私和 Cookie 合规  |
| 链接管理       | 按联盟政策使用  | 部分项目禁止链接伪装       |
| 页面构建器      | 谨慎       | 可能明显增加资源和前端体积    |

### 启用 Redis 对象缓存

部署中的 Redis 只是服务端组件，还需要 WordPress 插件将对象缓存接入 Redis。

安装具有持续维护记录的 Redis 对象缓存插件后，在插件页面检查：

```text
Redis 主机：redis
Redis 端口：6379
连接状态：已连接

```

Redis 对象缓存主要减少重复数据库查询，不等于完整页面缓存。两者解决的问题不同，可以配合使用。

不应把 Redis 端口映射到公网。如果确实需要跨服务器连接，应启用认证、网络访问控制和加密，不能沿用本文的内部网络配置。

---

## 八、WordPress 性能优化的正确顺序

联盟内容常包含产品图片、比较表格、按钮、分析脚本和广告代码，很容易影响移动端速度。优化应先处理最大的瓶颈，而不是一次安装多个“加速插件”。

### 1\. 先测量再优化

可以观察：

- 首字节时间；
- 最大内容绘制时间；
- 页面布局偏移；
- 交互响应；
- 页面请求数；
- JavaScript 总体积；
- 图片大小；
- PHP 和数据库资源占用。

实验室测试只能用于发现问题，真实用户数据更能反映读者使用体验。不要为了追求单次测速满分而破坏统计、表格或购买按钮。

### 2\. 选择轻量主题

联盟网站最核心的页面通常是：

- 产品评测；
- 多产品对比；
- 使用教程；
- 替代方案；
- 常见问题；
- 优惠或价格说明。

这些内容并不一定需要复杂页面构建器。原生区块编辑器配合轻量主题，通常更容易控制 HTML 结构和前端体积。

### 3\. 只使用一个页面缓存方案

页面缓存会把动态生成结果保存为静态响应，从而降低 PHP 和数据库压力。

避免同时启用多个全页缓存插件。重复缓存可能导致：

- 登录状态异常；
- 更新文章后旧页面无法刷新；
- 联盟链接参数被错误缓存；
- 移动端与桌面端页面混淆；
- 购物或表单页面失效。

如果网站包含登录、会员、购物车或个性化内容，需要把相关路径排除在缓存之外。

### 4\. 优化图片

上传前应：

- 裁剪到实际显示尺寸；
- 删除不必要的元数据；
- 压缩文件；
- 在兼容条件下使用 WebP 或 AVIF；
- 为首屏关键图片保留正确尺寸；
- 对非首屏图片使用延迟加载；
- 为图片填写有意义的替代文本。

不要把原始相机照片直接上传后仅依赖 CSS 缩小。

产品图片还涉及版权。应使用自己拍摄、获得授权或联盟项目明确允许使用的素材，并遵守商家关于图片、商标和价格展示的规则。

### 5\. 减少第三方脚本

常见第三方脚本包括：

- 统计工具；
- 热力图；
- 在线客服；
- 广告代码；
- 社交分享；
- A/B 测试；
- 嵌入视频；
- 多个联盟平台的小组件。

每增加一个第三方脚本，都可能增加连接、阻塞和隐私风险。应定期删除没有实际决策价值的工具。

### 6\. 清理插件而不是只停用

停用插件仍可能留下数据库表、定时任务和配置。删除前先备份，并确认插件卸载逻辑是否会删除需要保留的数据。

可以检查容器资源：

```bash
docker stats

```

查看各卷占用：

```bash
docker system df -v

```

不要随意执行带有 `--volumes` 的全局清理命令，否则可能删除仍需要的数据。

---

## 九、如何选择更可能盈利的利基市场

“热门”不等于适合新站。新手应寻找需求明确、内容可以持续产出、商业路径清晰的细分领域。

### 评估四个维度

#### 1\. 是否存在购买前问题

例如用户在购买前会搜索：

- A 和 B 有什么区别；
- 某产品是否适合某类人；
- 某软件能否解决特定问题；
- 某工具有哪些限制；
- 某产品的替代方案；
- 如何选择规格、尺寸或套餐。

这类问题比泛泛的“十大热门产品”更容易体现真实购买意图。

#### 2\. 是否有多个可替代商家

如果整个网站只依赖一个联盟项目，一旦对方调整佣金、审核政策、追踪周期或地区支持，收入可能大幅变化。

理想情况是同一主题下存在：

- 多家商家；
- 多种产品；
- 不同变现方式；
- 自有邮件订阅或工具页面；
- 可扩展的相邻主题。

#### 3\. 是否能提供实际经验

搜索引擎和读者都不缺少改写产品参数的页面。更有价值的内容包括：

- 实际使用过程；
- 原始测试数据；
- 自己拍摄的图片；
- 明确的优缺点；
- 不适合购买的人群；
- 长期使用后的问题；
- 与替代产品的真实差异。

如果没有测试产品，不应伪装成亲自使用。可以写研究型内容，但必须说明信息来源和评估方法。

#### 4\. 风险是否可控

医疗、金融、法律、安全等主题可能直接影响用户的重要决策。缺乏专业资质和审核能力的新手，不适合仅为了高佣金进入这些领域。

此外，还应检查商标、广告规范、地域限制和联盟项目的推广政策。

---

## 十、设计能产生转化而不是诱导点击的内容

高转化内容的目标不是让所有人点击，而是帮助合适的用户做出正确选择。

### 产品评测结构

一篇可信的评测可以包含：

1. 产品适合谁；
2. 不适合谁；
3. 测试或研究方法；
4. 核心功能；
5. 实际优点；
6. 明确缺点；
7. 使用成本和限制；
8. 替代选择；
9. 最终建议；
10. 联盟关系披露。

不要把“缺点”写成伪装优点，例如“功能太强大”。真实限制反而有助于筛选用户，减少无效点击。

### 对比文章结构

对比页面应先定义比较标准，例如：

- 总成本；
- 使用难度；
- 核心功能；
- 适用人群；
- 售后支持；
- 数据迁移；
- 退款条件；
- 地区可用性。

不要仅根据佣金高低推荐获胜者。短期可能提高点击，长期会损害品牌信任。

### 链接出现位置

联盟链接可以放在：

- 产品首次明确出现的位置；
- 对比表格中的操作列；
- 优缺点之后；
- 最终建议部分；
- 适合某类用户的场景说明之后。

按钮文字应描述用户下一步，例如：

```text
查看官方功能说明
查看当前可用套餐
前往商家页面了解详情

```

避免使用虚假的倒计时、库存警告或未经核实的“最低价”。

价格、优惠和产品功能可能变化。如果无法通过联盟平台允许的接口及时更新，不要写“永久最低价”或长期固定价格，可以引导用户到商家页面核实当前信息。

---

## 十一、联盟链接的正确标记与披露

联盟关系披露应清晰、容易看到，不能只藏在网站底部或冗长的隐私政策中。

文章开头可以使用类似表述：

> 本文包含联盟链接。如果你通过这些链接购买，我们可能获得佣金，但不会因此额外提高你的支付价格。推荐结论基于本文所说明的评估标准。

具体措辞应根据网站经营地、读者所在地区及联盟平台要求调整。涉及特定司法管辖区时，应咨询专业人士。

联盟链接可以添加：

```html
<a
  href="https://merchant.example/affiliate-url"
  rel="sponsored nofollow noopener"
  target="_blank"
>
  查看商家页面
</a>

```

其中：

- `sponsored` 表示这是商业或付费关系链接；
- `nofollow` 可作为补充关系标记；
- `noopener` 用于降低新窗口打开时的安全风险。

`target="_blank"` 并非必须。移动端打开大量新标签可能影响体验，应根据实际测试决定。

### 不要默认隐藏或改写所有联盟链接

部分联盟项目禁止以下行为：

- 链接伪装；
- 未经允许的短链接；
- 修改追踪参数；
- 在指定渠道之外投放；
- 自动跳转；
- 使用商标域名；
- 在邮件、PDF 或应用内放置链接；
- 展示未经接口更新的价格。

因此，在使用 `/go/product` 一类重定向链接前，必须先阅读对应联盟项目条款。不能因为某个链接管理插件支持重定向，就推断联盟平台允许使用。

---

## 十二、自建网站如何做转化追踪

转化追踪需要先区分三个概念：

| 数据      | 网站能否直接记录 | 含义          |
| ------- | -------- | ----------- |
| 文章浏览    | 可以       | 用户访问了内容页面   |
| 联盟链接点击  | 可以       | 用户离开网站前往商家  |
| 商家订单或注册 | 通常不能直接记录 | 需要联盟平台回传或报表 |

网站记录到一次点击，不代表已经获得佣金。用户可能没有购买、订单可能被取消、归因可能落到其他渠道，或者平台最终判定转化无效。

因此，联盟链接点击只能视为“微转化”。

### 方案一：通过统计工具记录联盟链接点击

可以使用 GA4、Matomo 或其他符合自身隐私要求的分析工具。

如果使用 Google Tag Manager，可创建点击触发器，按以下条件识别联盟链接：

- 链接包含指定联盟域名；
- 链接 CSS 类为 `affiliate-link`；
- 元素存在特定数据属性。

建议为链接增加统一标记：

```html
<a
  class="affiliate-link"
  data-merchant="merchant-a"
  data-placement="comparison-table"
  href="https://merchant.example/affiliate-url"
  rel="sponsored nofollow noopener"
>
  查看详情
</a>

```

可记录以下事件参数：

```text
事件名称：affiliate_click
merchant：merchant-a
placement：comparison-table
page_path：当前文章路径

```

不要把完整联盟网址、邮箱地址、姓名或其他个人信息作为分析参数发送。

如果页面已经正确加载 `gtag`，也可以通过前端代码记录事件：

```html
<script>
document.addEventListener('click', function (event) {
  const link = event.target.closest('a.affiliate-link');
  if (!link || typeof window.gtag !== 'function') return;

  window.gtag('event', 'affiliate_click', {
    merchant: link.dataset.merchant || 'unknown',
    placement: link.dataset.placement || 'unknown',
    transport_type: 'beacon'
  });
});
</script>

```

这段代码只负责发送点击事件，不修改联盟网址。可以通过子主题或受控的代码管理方式加载，避免直接修改父主题文件。

在发布前用浏览器调试工具和统计平台的实时调试功能验证，不要假设事件已经成功上报。

### 方案二：使用 Matomo 记录事件

如果选择自托管 Matomo，并且页面已经加载其追踪代码，可以使用：

```html
<script>
document.addEventListener('click', function (event) {
  const link = event.target.closest('a.affiliate-link');
  if (!link || !window._paq) return;

  window._paq.push([
    'trackEvent',
    'Affiliate',
    'Click',
    (link.dataset.merchant || 'unknown') + ':' +
    (link.dataset.placement || 'unknown')
  ]);
});
</script>

```

自托管并不等于自动合规。仍需维护 Matomo、限制数据保留时间、控制访问权限，并根据适用法律处理 Cookie 同意和隐私说明。

### 方案三：使用联盟平台的 SubID

部分联盟平台允许在链接中添加 SubID、Campaign ID、Click Reference 或其他追踪字段，字段名称和规则由平台决定。

可以为不同文章或按钮分配内部编号，例如：

```text
review-a-top
review-a-table
comparison-b-final

```

然后在联盟报表中观察哪个位置产生了实际订单。

不要直接把文章标题、用户名、邮箱或其他个人信息填入 SubID。内部编号既便于归因，也能降低数据泄露风险。

### 方案四：服务器到服务器回传

部分联盟网络支持 postback、webhook 或 API，用于把订单状态回传到站点或分析系统。只有平台明确提供这些能力时才能实施。

标准流程通常是：

```text
用户点击链接
  ↓
网站或联盟平台生成点击标识
  ↓
点击标识随链接进入商家
  ↓
用户完成有效转化
  ↓
联盟平台通过受保护接口回传结果
  ↓
系统把订单与原点击关联

```

实施时必须确认：

- 回传接口的认证方式；
- 签名验证；
- 重放攻击防护；
- 允许的来源；
- 订单状态变化；
- 退款与撤销处理；
- 数据保存周期；
- 是否允许把数据发送给第三方分析服务。

不要创建一个任何人都能调用的公开“转化成功”网址，否则数据极易被伪造。由于不同平台的字段和签名方式不同，不存在安全可靠的通用 postback 示例，应严格使用目标平台的官方文档。

---

## 十三、建立能够指导优化的数据看板

至少按页面、商家和链接位置记录以下指标：

| 指标      | 计算方式              | 用途        |
| ------- | ----------------- | --------- |
| 页面访问量   | 统计工具              | 判断内容曝光    |
| 联盟链接点击数 | 点击事件              | 判断行动意愿    |
| 点击率     | 点击数 ÷ 页面访问量       | 判断内容与按钮匹配 |
| 有效转化数   | 联盟平台报表            | 判断商业效果    |
| 商家转化率   | 有效转化数 ÷ 联盟点击数     | 判断流量与商家匹配 |
| 确认佣金    | 联盟平台最终数据          | 判断真实收益    |
| 每次点击收益  | 确认佣金 ÷ 联盟点击数      | 比较商家质量    |
| 每千次访问收益 | 确认佣金 ÷ 访问量 × 1000 | 比较页面商业价值  |

不要只看点击率。例如：

- 点击率高、订单少：可能是推荐不匹配，或商家页面转化差；
- 点击率低、订单率高：流量质量好，但行动入口不清晰；
- 访问量高、收入低：关键词可能只有信息需求；
- 订单多、撤销多：需要检查受众匹配、产品质量或平台规则；
- 移动端点击明显低：可能是表格溢出、按钮被遮挡或页面加载过慢。

联盟平台的最终确认数据通常比网站自报点击更接近真实收入。做月度分析时，应把待审核、已确认、已拒绝和已退款状态分开。

---

## 十四、内容与转化的测试方法

测试应围绕明确假设，而不是随意改颜色。

可以测试：

- 对比表格放在文章前部还是中部；
- 按钮写“立即购买”还是“查看官方详情”；
- 先展示推荐结论还是先解释评估标准；
- 增加“不适合谁”是否减少无效点击；
- 产品截图是否提高有效转化；
- 移动端表格改为卡片后是否提高可用性。

一次尽量只改一个主要变量，并保留足够观察周期。小流量网站很难得出可靠的 A/B 测试结论，过早依赖统计显著性可能导致错误判断。

对于流量较少的新站，更实际的方法是：

1. 检查用户是否能快速理解推荐结论；
2. 修复移动端显示问题；
3. 删除无关弹窗；
4. 补充真实证据；
5. 更新失效信息；
6. 将高意图页面链接到相关评测；
7. 再观察点击和联盟平台订单变化。

---

## 十五、备份：必须同时保存数据库和文件

Docker 数据卷不是备份。服务器磁盘损坏、误删卷或账号被入侵时，本地数据卷可能一起丢失。

WordPress 至少需要备份：

- MariaDB 数据库；
- `wp-content/uploads` 上传文件；
- 主题和自定义代码；
- 插件配置；
- `compose.yaml`；
- `Caddyfile`；
- 环境变量或恢复所需密钥。

### 导出数据库

创建备份目录：

```bash
mkdir -p /opt/affiliate-wordpress/backups
chmod 700 /opt/affiliate-wordpress/backups

```

执行数据库导出：

```bash
cd /opt/affiliate-wordpress

docker compose exec -T database \
  mariadb-dump \
  -u root \
  -p"${DB_ROOT_PASSWORD}" \
  --single-transaction \
  --routines \
  --triggers \
  "${DB_NAME}" \
  | gzip > "backups/db-$(date +%F-%H%M).sql.gz"

```

由于交互式 Shell 不会自动读取 `.env` 变量，可先安全地加载变量，或把备份过程写成权限受控的脚本。不要把密码直接写入可被其他用户读取的定时任务。

也可以使用：

```bash
docker compose exec -T database sh -c \
  'mariadb-dump -u root -p"$MARIADB_ROOT_PASSWORD" --single-transaction "$MARIADB_DATABASE"' \
  | gzip > "backups/db-$(date +%F-%H%M).sql.gz"

```

### 备份 WordPress 文件卷

```bash
docker run --rm \
  -v affiliate-wordpress_wp_data:/source:ro \
  -v /opt/affiliate-wordpress/backups:/backup \
  alpine \
  sh -c 'tar -czf /backup/wp-data-$(date +%F-%H%M).tar.gz -C /source .'

```

实际卷名前缀取决于 Compose 项目名称，可先查询：

```bash
docker volume ls

```

备份完成后，应加密并复制到另一台服务器或对象存储中。至少定期执行一次恢复演练，因为“生成了备份文件”不等于“可以成功恢复”。

---

## 十六、安全维护与升级流程

### 日常安全措施

- WordPress 管理员启用多因素认证；
- 使用独立强密码；
- 限制管理员账号数量；
- 删除不用的主题和插件；
- 只从可信来源安装代码；
- 定期查看登录与系统日志；
- 不把数据库和 Redis 暴露到公网；
- 保持宿主机安全更新；
- 配置异地备份；
- 不在后台文本编辑器直接修改生产代码。

`DISALLOW_FILE_EDIT` 已禁用后台主题和插件文件编辑器，但不会阻止管理员安装插件。若希望完全禁止后台更新和安装，需要进一步评估文件修改策略，并建立可控的部署流程。

### 镜像升级

查看当前服务：

```bash
docker compose ps

```

更新前先备份，然后拉取新镜像：

```bash
docker compose pull

```

重建容器：

```bash
docker compose up -d

```

查看日志：

```bash
docker compose logs --since=10m

```

检查：

- 首页和文章页；
- WordPress 后台；
- HTTPS；
- 图片；
- 联盟链接；
- 点击事件；
- Redis 连接；
- 定时任务；
- 表单和邮件。

数据库、PHP 或 WordPress 跨主版本升级时，应先在测试环境验证插件和主题兼容性，不要把生产站当测试站。

---

## 十七、常见故障排查

### HTTPS 证书申请失败

检查：

```bash
docker compose logs caddy

```

常见原因：

- DNS 尚未生效；
- A 或 AAAA 记录指向错误；
- 80、443 端口未开放；
- 云平台安全组未放行；
- 服务器已有其他程序占用端口；
- 经过代理服务但代理配置错误。

查看端口：

```bash
sudo ss -lntup | grep -E ':80|:443'

```

### WordPress 无法连接数据库

查看：

```bash
docker compose logs database
docker compose logs wordpress

```

检查 `.env` 中数据库名、用户和密码是否一致。如果数据库卷已经初始化，后来仅修改 `.env`，MariaDB 不一定会自动重建已有用户密码。

不要为了省事直接删除数据库卷。应先备份，并使用数据库管理命令正确修改账号。

### 上传文件大小受限

上传限制可能同时来自：

- PHP；
- Apache；
- WordPress；
- 反向代理；
- 插件。

不要只修改其中一个值。大文件更适合通过受控的服务器方式上传，且应限制不必要的媒体体积。

### 修改文章后页面仍显示旧内容

依次检查：

1. WordPress 页面缓存；
2. Redis 对象缓存；
3. CDN 缓存；
4. 浏览器缓存；
5. Caddy 是否配置了额外缓存；
6. 是否访问了不同主域名。

不要同时点击多个缓存插件的“全部清除”后就停止排查，应确认具体是哪一层返回了旧响应。

### 后台出现重定向循环

检查 WordPress 地址与站点地址是否都是正确的 HTTPS 主域名。还要确认：

- Caddy 正确转发协议；
- 没有多个插件重复强制 HTTPS；
- CDN 的 SSL 模式没有形成循环；
- `www` 与非 `www` 跳转规则没有相互冲突。

---

## 十八、新手可执行的 90 天运营计划

### 第 1—2 周：确定领域与基础设施

- 筛选一个足够具体的利基市场；
- 检查多个联盟项目是否可申请；
- 阅读推广渠道、链接和商标政策；
- 部署 WordPress；
- 完成 HTTPS、备份、统计和安全设置；
- 设计文章模板和联盟披露。

### 第 3—6 周：建立主题内容集群

优先完成：

- 一篇核心购买指南；
- 两到三篇产品评测；
- 一到两篇对比文章；
- 数篇解决具体问题的教程；
- 关于我们、联系、隐私政策和联盟披露页面。

内容之间通过自然的内部链接关联，但不要在每篇文章里机械地重复相同锚文本。

### 第 7—10 周：验证用户行为

检查：

- 哪些页面开始获得展示和访问；
- 哪些按钮被点击；
- 移动端是否可正常阅读表格；
- 联盟参数是否保留；
- 商家报表是否能识别 SubID；
- 用户常见问题能否形成新内容；
- 是否存在失效链接。

此阶段不要根据少量数据承诺收入，也不要为了追求点击加入夸大描述。

### 第 11—13 周：优化已有资产

- 更新最有潜力的文章；
- 补充实测图片和证据；
- 改进标题和搜索摘要；
- 优化页面加载速度；
- 合并重复内容；
- 修复失效链接；
- 比较不同商家的实际转化；
- 记录确认佣金而非只记录预估佣金。

新手最常见的问题是不断发布新文章，却从不更新已经有展示和点击的页面。对已有潜力页面进行迭代，通常比无计划扩张更有效。

---

## 十九、上线检查清单

### 技术部分

- \[ \] 域名解析正确；
- \[ \] HTTPS 正常并可自动续期；
- \[ \] MariaDB 和 Redis 未暴露公网；
- \[ \] WordPress 后台使用强密码和多因素认证；
- \[ \] 系统定时任务能够执行 WP-Cron；
- \[ \] 数据库和文件都有异地备份；
- \[ \] 已测试恢复流程；
- \[ \] 页面缓存与 Redis 工作正常；
- \[ \] 移动端无明显布局溢出；
- \[ \] 404、重定向和主域名设置正确。

### 内容部分

- \[ \] 文章说明评估或测试方法；
- \[ \] 不冒充实际使用经验；
- \[ \] 优点和缺点均有依据；
- \[ \] 图片拥有合法使用权；
- \[ \] 价格与优惠信息可核实；
- \[ \] 内容包含明确适用和不适用人群；
- \[ \] 联盟关系披露清晰可见。

### 追踪部分

- \[ \] 联盟链接保留正确参数；
- \[ \] 点击事件在统计工具中可见；
- \[ \] 不发送个人信息；
- \[ \] SubID 使用内部编号；
- \[ \] 网站点击与平台报表分开统计；
- \[ \] 退款、拒绝和待确认佣金分别处理；
- \[ \] Cookie 与分析工具符合适用的隐私要求。

### 商业部分

- \[ \] 已阅读每个联盟项目条款；
- \[ \] 没有未经允许进行链接伪装；
- \[ \] 没有使用虚假倒计时或库存信息；
- \[ \] 没有承诺无法核实的最低价格；
- \[ \] 不依赖单一商家；
- \[ \] 推荐结论不以佣金高低作为唯一依据。

---

## 结语

一套可靠的 Docker WordPress 架构，能够降低服务器迁移、环境冲突和日常维护的难度，但它只是联盟网站的基础设施。

真正可持续的流程应该是：

```text
选择细分需求
→ 发布可信内容
→ 吸引有购买意图的访问者
→ 合规展示联盟链接
→ 记录站内点击
→ 对照联盟平台真实订单
→ 优化内容与商家匹配
→ 持续维护安全、速度和信息准确性

```

新站不应把目标设定为“安装完成后快速变现”，而应先验证三个问题：

1. 用户是否真的需要这类内容；
2. 内容是否足以影响购买决策；
3. 点击是否能在联盟平台形成有效转化。

当技术部署、内容质量和转化数据能够相互验证时，WordPress 联盟网站才从一个普通博客，逐渐变成可维护、可分析的网络业务资产。