0. 为什么不直接使用 Memos 内置的 S3 存储?

Memos 内置的 S3存储 通过 Presigned URLs 生成资源链接,这种方式有很多好处,但是最大的问题是访问资源的时候,没办法通过 CDN 缓存。可能有恶意刷 B类 操作的风险。

rclone 是一个可以将网盘、对象存储等 挂载到本地文件系统的工具

  1. 通过 rclone 将 Cloudflare R2 挂载到本地 Memos 容器上
  2. 将 Memo 设置为 本地文件系统 ,实际上还是将资源存到 R2 上
  3. rclone 可以设置缓存,不会频繁访问 R2

这样设置之后,可能是目前最完美的方案,相当于使用我们的服务器,为 R2 套了一层 CDN,且不用将 R2 公开,只有我们的服务器可以访问 R2。

Memos 内置 S3R2 + Rclone 挂载
资源访问方式Presigned URL(5天刷新动态链接)静态文件路径(通过本地挂载映射)
CDN 兼容性❌ 无法缓存(每次直接请求 R2)✅ 完美支持(固定路径可被 CDN 缓存)
存储桶安全性✅ 存储桶不需公开访问权限✅ 存储桶完全私有(仅服务器可访问)
防恶意刷流量❌ 高风险(Presigned URL 无法套CDN)✅ 高防御(CDN + Rclone 缓存双重防护)
R2 API 请求量⚠️ 高(每次资源访问都调用 API)✅ 低(rclone 缓存减少 API 调用)
架构复杂度✅ 简单(原生集成)⚠️ 需配置 rclone 挂载

1. 准备工作

1.1 安装 FUSE 支持

sudo apt-get updatesudo apt-get -y install fuse3

1.2 创建必要目录

sudo mkdir -p /var/lib/docker-plugins/rclone/configsudo mkdir -p /var/lib/docker-plugins/rclone/cache

1.3 安装 rclone 管理插件

安装 rclone Docker 插件
docker plugin install rclone/docker-volume-rclone:amd64 \  --alias rclone \  --grant-all-permissions \  args="-v --allow-other"
验证安装
docker plugin list

2. 配置 Cloudflare R2

2.1 创建 rclone 配置文件

创建配置文件(路径不可改):
sudo nano /var/lib/docker-plugins/rclone/config/rclone.conf
添加以下内容(替换实际的 R2 凭据):
[r2]type = s3provider = Cloudflareaccess_key_id = YOUR_R2_ACCESS_KEYsecret_access_key = YOUR_R2_SECRET_KEYregion = autoendpoint = https://YOUR_ACCOUNT_ID.r2.cloudflarestorage.comacl = private

2.2 设置文件权限

sudo chmod 600 /var/lib/docker-plugins/rclone/config/rclone.conf

3. 更新 Docker Compose 配置

3.1 修改 docker-compose.yml

version: '3.8'services:  memos:    image: neosmemo/memos:stable    container_name: memos    restart: unless-stopped    ports:      - "5230:5230"    volumes:      - ./.memos:/var/opt/memos      - memos-assets:/var/opt/memos/assets    depends_on:      - volume-check    healthcheck:      test: ["CMD", "ls", "/var/opt/memos/assets"]      interval: 30s      timeout: 10s      retries: 3      start_period: 15s  # 用于确保卷正确挂载的检查服务  volume-check:    image: busybox    command: |      sh -c "        echo 'Checking rclone mount...'        ls -la /mnt/assets || exit 1        echo 'Mount check passed'      "    volumes:      - memos-assets:/mnt/assets    restart: "no"volumes:  memos-assets:    driver: rclone    driver_opts:      remote: 'r2:memos/assets'      allow_other: 'true'      vfs_cache_mode: 'full'      vfs_cache_max_age: '24h'      vfs_cache_max_size: '1G'      poll_interval: 0

3.2 高级配置选项说明

  • vfs-cache-mode=full: 启用完整的 VFS 缓存,提高读写性能
  • vfs-cache-max-age=24h: 缓存文件最大保存时间
  • vfs-cache-max-size=1G: 缓存最大大小
  • poll_interval=0: 检查远程更改的间隔,设置为0表示不检查,减少A类操作次数
  • allow-other=true: 允许其他用户访问挂载点

4. 启动服务

4.1 启动容器组

# 确保在 docker-compose.yml 目录中docker-compose up -d

4.2 检查服务状态

# 查看服务状态docker-compose ps# 查看卷挂载状态docker volume ls# 检查 memos 容器中的挂载docker exec memos ls -la /var/opt/memos/assets

5. 验证和测试

5.1 测试挂载功能

# 在容器中创建测试文件docker exec memos touch /var/opt/memos/assets/test.txt# 检查文件是否存在于 R2 存储桶中 ( 网页上看看 )docker exec memos ls -la /var/opt/memos/assets/

5.2 监控日志

# 查看 memos 容器日志docker-compose logs -f memos# 查看 rclone 插件日志sudo journalctl -u docker -f | grep rclone

6. 备份和维护

6.1 定期备份配置

# 备份 rclone 配置sudo cp /var/lib/docker-plugins/rclone/config/rclone.conf /backup/rclone.conf.backup# 备份 docker-compose 配置cp docker-compose.yml docker-compose.yml.backup

6.2 更新插件

# 停止相关服务docker-compose down# 更新插件docker plugin rm rclonedocker plugin install rclone/docker-volume-rclone:amd64 --alias rclone --grant-all-permissions args="-v --allow-other"# 重新启动服务docker-compose up -d