---
title: "在群晖的Docker环境中运行甜糖星愿服务"
source: https://www.boris1993.com/run-tiantang-on-synology-docker.html
date: 2021-01-04
updated: 2026-10-10
tags: [甜糖星愿, 甜糖]
categories: [瞎折腾]
---

# 在群晖的Docker环境中运行甜糖星愿服务

前段时间在网上看到了一个叫“甜糖星愿计划”的东西，声称可以通过贡献闲置带宽来获得积分。正好我有个NAS，正好我的宽带一天从白天闲到黑夜，不如利用起来，少少挣一些零花钱。

需要注意的一点是，本文提到的镜像仅在我的`群晖DS218+`上测试过，虽然镜像中未使用任何群晖限定的依赖，理论上适用于任何x86架构的平台，但并不保证运行效果。而且本文目标平台是x86，如果你拥有ARM平台的机器，那根本不需要废这个劲，你可以直接运行甜糖星愿的可执行程序。

本文提到的操作全部基于Docker，故在按照本文操作前，请先确保你已经拥有足够的知识来使用`Docker`和`docker-compose`。

## 我的网络环境

因为这个镜像相关的一些配置是以我的网络结构为基础的，所以我觉得有必要简单说一下我的网络结构是什么样的。

简单来说，我的网络就是这样子的。虽然网络里还有别的设备，但是因为与本文无关，我就略掉了。

```text
[公网] -- [光猫] -- [群晖]
```

其中光猫负责拨号，所以它也是最外层的一个路由器，光猫的IP地址是`192.168.1.1`，它下面有一个`192.168.1.0/24`的子网，群晖与光猫直连，有一个`192.168.1.0/24`子网下的IP地址。在群晖的Docker中，会有一个`macvlan`驱动的网络，与物理网卡共享同一个子网。甜糖星愿的容器将会接入到这个`macvlan`网络，在接入时我会手动为其分配一个IP地址。

## 安装Docker及配置网络

因为本文是通过Docker来实现的，所以第一步当然是安装Docker。群晖嘛就从套件商店安装，其他平台就用自己平台的方法安装，总之装上Docker就行。安装好Docker之后，进入`控制面板 -- 网络 -- 网络界面`，选择连接公网的接口，如`局域网1`，点击`管理 -- Open vSwitch设置`，勾选`启用 Open vSwitch`。

然后我们需要在Docker里面创建一个`macvlan`驱动的网络，命令如：

```bash
sudo docker network create \
    -d macvlan \
    --subnet=192.168.1.0/24 \
    --gateway=192.168.1.1 \
    -o parent=ovs_eth0 \
    macvlan
```

上面命令中`subnet`的值替换成群晖所在网络的子网，`gateway`指向该子网的网关，`parent`指向要绑定的物理网卡，最后面的`macvlan`是网络名，可以按需修改。

## 准备二进制翻译器

接下来，我们要借助QEMU的力量，放一个幻术。毕竟，甜糖星愿只给了ARM平台的可执行程序，直接在x86平台跑肯定是跑不起来的，所以我们要向内核注册一个翻译器，这样Docker在执行其他平台的机器码时就可以通过这个翻译器将其翻译成x86指令来执行了。是的，我知道这玩意效率不高，我已经体验过了。

首先，克隆这个镜像的源码仓库\[^2\]，找到`resources/qemu-aarch64-static`，或者你直接从GitHub下载qemu-aarch64-static也行，把这个文件放到`$PATH`指定的目录，赋予执行权限。

然后施法吟唱，很简单，就一句话：

```bash
sudo docker run --rm --privileged multiarch/qemu-user-static:register
```

但是，这个幻术在群晖重启之后就会消失，幻术没了，甜糖星愿就起不来。所以我们还得配一个开机后的自启动任务，让群晖帮我们自动吟唱。操作也很简单，首先将本仓库的`set_qemu_user_static.sh`放到一个合适的位置，比如我放到了`/var/services/homes/boris1993/scripts`，然后前往`控制面板 -- 任务计划`，然后按照如下说明新增一个任务计划：

-   任务名称：可自选
-   用户账号：root
-   事件：开机
-   任务设置页面的运行命令：  
    `/var/services/homes/boris1993/scripts/set_qemu_user_static.sh`

如果要看这个脚本的日志的话，在`运行命令`里面把脚本输出重定向到一个文件就可以了。

## 运行镜像

进入本仓库所在目录，或者下载docker-compose.yml到一个合适的目录下，然后稍微编辑一下，以符合你的网络状况。主要要检查的就是`networks.macvlan.ipv4_address`的值，要确保它处在上面创建的那个`macvlan`网络的子网中。

确认无误后，执行`sudo docker-compose up -d`，Docker就会自动拉取镜像，并启动一个名为`tiantang`的容器。

容器内的甜糖星愿在首次启动时会自动退出，这是因为它在自我更新（我就不说这个操作一开始给了我多大的困扰了）。不要怕，容器里面有一个每分钟执行一次的定时任务，在没有发现甜糖星愿的进程时会自动将它启动。

除此之外，我会在容器启动两分钟后，检测甜糖星愿监听了哪些端口，然后通过脚本自动设置路由器上的UPnP规则，这样你就不需要将甜糖星愿容器的IP放到DMZ里，也不需要手动配置端口转发了。当然这个操作的前提是，你的路由器支持UPnP，并且你启用了UPnP，如果没有的话，那你只能手动操作了。或者，如果你不想让脚本自动配置UPnP，或者客观条件下不允许你这么做，那么你可以把`docker-compose.yml`中`SKIP_UPNP_AUTOCONFIG`这一环境变量置为`true`，这样脚本就不会执行了。

在甜糖星愿稳定运行，且端口转发规则也配置成功后，就可以通过手机客户端绑定这个节点了。但是这里有个问题，就是手机与甜糖星愿必须处在同一个子网里才能自动发现，如果因为各种原因没能自动发现，那么你可以在`tiantang`这个容器中打开一个`bash`终端，执行`ttnode_168 -p /data`，在输出中会打印出这个节点的UID，将其复制到任意二维码生成工具中生成一个二维码，然后用手机端扫描这个二维码，即可完成绑定。

在这之后，就没什么我们能做的了。我们就慢慢等着甜糖星愿给你分配任务吧。我是等了大概有两三天才开始跑流量的。如果在配置好UPnP后，手机端仍提示“未配置网络”，那有可能是在配置UPnP的脚本启动时，甜糖星愿尚未打开所有端口，导致UPnP规则不完整。你可以前往路由器的UPnP页面，将页面显示结果与`netstat -nlp | grep qemu`命令的输出做对比，如果不一致的话，重新手动运行`set-port-forwarding.sh`脚本即可。

## 深入了解

如果你不止满足于把它跑起来，还想要了解这个镜像背后的运作方式，那么你可以前往这个镜像的GitHub仓库\[^3\]阅读该镜像相关的源码。在源码中我也写了注释，可以方便你理解我的想法。

## 我的邀请码

如果我的镜像帮到了你，或者我的这篇文章帮到了你，那么如果你愿意的话，你可以在手机客户端的`填写邀请码`处，填上我的邀请码\*\*`804744`\*\*，这样你可以获得15张加成卡，当然我也会得到一些加成。反正互利互惠，我的加成不会从你的身上扣掉，何乐而不为呢？

\[^2\]: tiantang-x86-docker - Docker Hub  
\[^3\]: tiantang-x86-docker - GitHub
