Skip to content

Commit 5e2afcf

Browse files
committed
post: taskwarrior
1 parent 88b7007 commit 5e2afcf

File tree

47 files changed

+54157
-280
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

47 files changed

+54157
-280
lines changed

content/posts/2025-12-18_python-distilled-04.md

Lines changed: 395 additions & 0 deletions
Large diffs are not rendered by default.
Lines changed: 216 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,216 @@
1+
+++
2+
date = '2025-12-27T8:00:00+08:00'
3+
draft = false
4+
title = 'Taskwarrior Server Config Guide'
5+
tags = ['Tools']
6+
+++
7+
8+
# Taskwarrior 3.x 同步服务器配置指南
9+
10+
本文介绍如何使用 Docker 部署 taskchampion-sync-server,为 Taskwarrior 3.x 提供跨设备同步功能。
11+
12+
## 背景知识
13+
14+
Taskwarrior 是一款强大的命令行任务管理工具。从 3.0 版本开始,官方不再支持 taskd 服务器,改用新的 taskchampion-sync-server。
15+
16+
与 taskd 相比,新同步服务器的优势:
17+
18+
- 无需手动配置 SSL 证书
19+
- 无需预先创建用户账户
20+
- 客户端数据端到端加密
21+
- 部署和维护更简单
22+
23+
## 服务器端配置
24+
25+
### 使用 Docker 部署
26+
27+
创建数据目录并启动容器:
28+
29+
```bash
30+
sudo mkdir -p /var/lib/taskchampion-sync-server
31+
sudo chmod 777 /var/lib/taskchampion-sync-server
32+
33+
docker run -d \
34+
--name taskchampion \
35+
-p 53589:8080 \
36+
-e RUST_LOG=info \
37+
-v taskchampion-data:/var/lib/taskchampion-sync-server \
38+
--restart unless-stopped \
39+
ghcr.io/gothenburgbitfactory/taskchampion-sync-server:main
40+
```
41+
42+
**端口说明**:容器内部使用 8080,映射到宿主机的 53589(可自定义)。
43+
44+
### 配置防火墙
45+
46+
确保服务器防火墙开放相应端口。以常见的云服务器防火墙为例:
47+
48+
- 类型:入站
49+
- 行动:允许
50+
- 协议:TCP
51+
- 目的端口:53589
52+
53+
### 验证服务运行
54+
55+
```bash
56+
docker ps | grep taskchampion
57+
docker logs taskchampion
58+
```
59+
60+
正常运行时应看到:
61+
62+
```
63+
[INFO] Serving on port 8080
64+
[INFO] starting service: "actix-web-service-0.0.0.0:8080"
65+
```
66+
67+
## 客户端配置
68+
69+
### 生成配置信息
70+
71+
```bash
72+
# 生成唯一的客户端 ID
73+
CLIENT_ID=$(uuidgen)
74+
echo "Client ID: $CLIENT_ID"
75+
76+
# 生成加密密钥
77+
ENCRYPTION_SECRET=$(openssl rand -base64 32)
78+
echo "Encryption Secret: $ENCRYPTION_SECRET"
79+
```
80+
81+
**重要提示**:请妥善保存这两个值,多设备同步时需要使用相同的配置。
82+
83+
### 配置 Taskwarrior
84+
85+
```bash
86+
# 设置服务器地址
87+
task config sync.server.url http://你的服务器IP:53589
88+
89+
# 设置客户端 ID
90+
task config sync.server.client_id $CLIENT_ID
91+
92+
# 设置加密密钥
93+
task config sync.encryption_secret "$ENCRYPTION_SECRET"
94+
```
95+
96+
### 首次同步
97+
98+
```bash
99+
task sync
100+
```
101+
102+
成功时会显示:
103+
104+
```
105+
Syncing with sync server at http://你的服务器IP:53589
106+
Success!
107+
```
108+
109+
## 日常使用
110+
111+
### 同步任务
112+
113+
```bash
114+
# 手动同步
115+
task sync
116+
117+
# 添加任务后自动同步(可选)
118+
echo 'sync.on=all' >> ~/.taskrc
119+
```
120+
121+
### 监控服务
122+
123+
查看服务器实时日志:
124+
125+
```bash
126+
docker logs -f taskchampion
127+
```
128+
129+
每次同步都会产生类似记录:
130+
131+
```
132+
[INFO] 客户端IP "GET /v1/client/get-child-version/..." 200
133+
[INFO] 客户端IP "POST /v1/client/add-version/..." 200
134+
```
135+
136+
### 多设备同步
137+
138+
在其他设备上使用**相同的配置**
139+
140+
- 相同的 `sync.server.url`
141+
- 相同的 `sync.server.client_id`
142+
- 相同的 `sync.encryption_secret`
143+
144+
这样所有设备将共享同一份任务数据。
145+
146+
## 常见问题
147+
148+
### Docker 权限问题
149+
150+
如果遇到 "permission denied" 错误:
151+
152+
```bash
153+
# 将用户添加到 docker 组
154+
sudo usermod -aG docker $USER
155+
156+
# 完全退出并重新登录 SSH
157+
exit
158+
159+
# 如果还不行,清理 SSH 连接缓存
160+
ssh -o "ControlPath=none" 服务器地址
161+
```
162+
163+
### 容器数据持久化
164+
165+
推荐使用 Docker 命名卷(如上面的 `taskchampion-data`),Docker 会自动处理权限问题。
166+
167+
如果需要访问数据库文件:
168+
169+
```bash
170+
# 查看数据卷位置
171+
docker volume inspect taskchampion-data
172+
173+
# 进入容器
174+
docker exec -it taskchampion sh
175+
```
176+
177+
### 查看同步日志
178+
179+
启用详细日志可以帮助诊断问题:
180+
181+
```bash
182+
docker run -d \
183+
--name taskchampion \
184+
-e RUST_LOG=debug \
185+
...其他参数
186+
```
187+
188+
日志级别:`error` < `warn` < `info` < `debug` < `trace`
189+
190+
## 安全建议
191+
192+
虽然数据在客户端加密,但仍建议:
193+
194+
1. 使用防火墙限制访问来源 IP
195+
2. 配置反向代理添加 HTTPS(如 Nginx + Let's Encrypt)
196+
3. 定期备份数据卷:
197+
198+
```bash
199+
docker run --rm \
200+
-v taskchampion-data:/data \
201+
-v $(pwd):/backup \
202+
alpine tar czf /backup/taskchampion-backup.tar.gz /data
203+
```
204+
205+
## 总结
206+
207+
taskchampion-sync-server 为 Taskwarrior 3.x 提供了简洁高效的同步方案。相比旧的 taskd,配置过程大幅简化,日常维护也更轻松。配合 Docker 部署,几分钟即可搭建完成。
208+
209+
关键配置要点:
210+
211+
- 服务器使用 Docker 部署,注意端口映射
212+
- 客户端需要三个配置项:服务器地址、客户端 ID、加密密钥
213+
- 多设备使用相同的客户端 ID 和加密密钥
214+
- 数据端到端加密,服务器无法读取明文
215+
216+
现在你可以在任何设备上使用 `task sync` 保持任务列表同步了。

public/archives/index.html

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -51,10 +51,13 @@
5151
<span class="max-w-[4rem] md:max-w-none truncate">Home</span></a></li><li class="flex items-center gap-1 md:gap-2 min-w-0"><span class="text-muted-foreground/50 flex-shrink-0"><svg class="h-4 w-4" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 5l7 7-7 7"/></svg>
5252
</span><span class="text-foreground flex items-center gap-0.5 md:gap-1 font-medium min-w-0 flex-shrink-0"><svg class="h-4 w-4" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 8h14M5 8a2 2 0 110-4h14a2 2 0 110 4M5 8v10a2 2 0 002 2h10a2 2 0 002-2V8m-9 4h4"/></svg>
5353
<span class="max-w-[3rem] md:max-w-none truncate">Archives</span></span></li></ol></nav><header class=mb-8><div class="mb-4 flex items-center gap-3"><svg class="h-6 w-6" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M5 8h14M5 8a2 2 0 110-4h14a2 2 0 110 4M5 8v10a2 2 0 002 2h10a2 2 0 002-2V8m-9 4h4"/></svg><h1 class="text-foreground text-3xl font-bold">Archives</h1></div><p class="text-muted-foreground mb-6">Browse all articles in chronological order and discover what interests you.</p><div class="text-muted-foreground flex items-center gap-4 text-sm"><div class="flex items-center gap-1"><svg class="h-4 w-4" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M9 12h6m-6 4h6m2 5H7a2 2 0 01-2-2V5a2 2 0 012-2h5.586a1 1 0 01.707.293l5.414 5.414a1 1 0 01.293.707V19a2 2 0 01-2 2z"/></svg>
54-
<span>90 posts total</span></div><div class="flex items-center gap-1"><svg class="h-4 w-4" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg>
55-
<span>Timeline view</span></div></div></header><div class=relative><div class="bg-border absolute top-0 bottom-0 left-4 w-0.5"></div><div class=mb-12><div class="relative mb-8 flex items-center"><div class="bg-primary absolute left-0 z-10 flex h-8 w-8 items-center justify-center rounded-full"><svg class="h-4 w-4 text-primary-foreground" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg></div><div class=ml-12><h2 class="text-foreground text-2xl font-bold">2025</h2><p class="text-muted-foreground text-sm">88
56-
posts</p></div></div><div class="relative mb-8"><div class="relative mb-4 flex items-center"><div class="bg-accent border-background absolute left-2 z-10 h-4 w-4 rounded-full border-2"></div><div class=ml-12><h3 class="text-foreground text-lg font-semibold">December 2025</h3><p class="text-muted-foreground text-xs">8
57-
posts</p></div></div><div class="ml-12 space-y-3"><article class="group bg-card border-border hover:bg-accent/50 rounded-lg border p-4 transition-all duration-300"><div class="flex items-center justify-between gap-4"><div class="min-w-0 flex-1"><h4 class="text-foreground group-hover:text-primary mb-3 font-medium transition-colors duration-200"><a href=/posts/python-pep-683-immoral-objects/ class=block>Python PEP 683: Immoral Objects</a></h4><div class="text-muted-foreground flex items-center gap-4 text-xs"><div class="flex items-center gap-1"><svg class="h-3 w-3" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg>
54+
<span>91 posts total</span></div><div class="flex items-center gap-1"><svg class="h-4 w-4" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg>
55+
<span>Timeline view</span></div></div></header><div class=relative><div class="bg-border absolute top-0 bottom-0 left-4 w-0.5"></div><div class=mb-12><div class="relative mb-8 flex items-center"><div class="bg-primary absolute left-0 z-10 flex h-8 w-8 items-center justify-center rounded-full"><svg class="h-4 w-4 text-primary-foreground" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg></div><div class=ml-12><h2 class="text-foreground text-2xl font-bold">2025</h2><p class="text-muted-foreground text-sm">89
56+
posts</p></div></div><div class="relative mb-8"><div class="relative mb-4 flex items-center"><div class="bg-accent border-background absolute left-2 z-10 h-4 w-4 rounded-full border-2"></div><div class=ml-12><h3 class="text-foreground text-lg font-semibold">December 2025</h3><p class="text-muted-foreground text-xs">9
57+
posts</p></div></div><div class="ml-12 space-y-3"><article class="group bg-card border-border hover:bg-accent/50 rounded-lg border p-4 transition-all duration-300"><div class="flex items-center justify-between gap-4"><div class="min-w-0 flex-1"><h4 class="text-foreground group-hover:text-primary mb-3 font-medium transition-colors duration-200"><a href=/posts/taskwarrior-server-config-guide/ class=block>Taskwarrior Server Config Guide</a></h4><div class="text-muted-foreground flex items-center gap-4 text-xs"><div class="flex items-center gap-1"><svg class="h-3 w-3" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg>
58+
<time datetime=2025-12-27>12-27</time></div><div class="flex items-center gap-1"><svg class="h-3 w-3" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4l3 3m6-3A9 9 0 113 12a9 9 0 0118 0z"/></svg>
59+
<span>3
60+
min</span></div></div></div></div></article><article class="group bg-card border-border hover:bg-accent/50 rounded-lg border p-4 transition-all duration-300"><div class="flex items-center justify-between gap-4"><div class="min-w-0 flex-1"><h4 class="text-foreground group-hover:text-primary mb-3 font-medium transition-colors duration-200"><a href=/posts/python-pep-683-immoral-objects/ class=block>Python PEP 683: Immoral Objects</a></h4><div class="text-muted-foreground flex items-center gap-4 text-xs"><div class="flex items-center gap-1"><svg class="h-3 w-3" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg>
5861
<time datetime=2025-12-23>12-23</time></div><div class="flex items-center gap-1"><svg class="h-3 w-3" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M12 8v4l3 3m6-3A9 9 0 113 12a9 9 0 0118 0z"/></svg>
5962
<span>1
6063
min</span></div></div></div></div></article><article class="group bg-card border-border hover:bg-accent/50 rounded-lg border p-4 transition-all duration-300"><div class="flex items-center justify-between gap-4"><div class="min-w-0 flex-1"><h4 class="text-foreground group-hover:text-primary mb-3 font-medium transition-colors duration-200"><a href=/posts/shell/ class=block>Shell</a></h4><div class="text-muted-foreground flex items-center gap-4 text-xs"><div class="flex items-center gap-1"><svg class="h-3 w-3" fill="none" stroke="currentColor" viewBox="0 0 24 24"><path stroke-linecap="round" stroke-linejoin="round" stroke-width="2" d="M8 7V3m8 4V3m-9 8h10M5 21h14a2 2 0 002-2V7a2 2 0 00-2-2H5A2 2 0 003 7v12a2 2 0 002 2z"/></svg>

public/en/sitemap.xml

Lines changed: 1 addition & 1 deletion
Large diffs are not rendered by default.

0 commit comments

Comments
 (0)