TinyPilot:第 29 个月
原文由 Michael Lynch 于 发布,订阅该博客
一句话总结
当长期任务停滞时,就该警惕了。
亮点
- TinyPilot 月营收达到 11.2 万美元,首次突破六位数大关。
- 我严重高估了 TinyPilot 履约团队的富余产能。
- 长期任务可以成为资源即将耗尽的预警信号。
目标完成度
每个月初,我都会定下当月想要完成的目标。以下是本月目标的完成情况:
准备将 TinyPilot 的履约环节迁移至第三方物流(3PL)供应商
- 结果:已就单一低销量产品启动与供应商的对接流程
- 评分:B
我低估了本地团队在这个项目上能投入的富余时间。加上突如其来的销售高峰,我们没能将现有的内部履约流程适配到第三方物流供应商。不过,即便流程还不完善,我们也可以先推进,再随着第三方物流为我们腾出时间逐步改进。
继续培养新的技术支持工程师
- 结果:两位技术支持工程师已能独立处理约 80% 的工单。
- 评分:A
技术支持团队的表现超出了我的预期。除了处理复杂的技术支持请求,他们还会深入排查问题,从源头上减少缺陷发生,并改进了 TinyPilot 的诊断日志。
减少由我处于关键路径上的项目
- 结果:已克制住启动任何新项目的冲动。
- 评分:B
推出一款新的 TinyPilot 型号总会占用我大量时间。我已经经历过多次,对其中的工作量有不少预判,但我也清楚,无论计划多周全,总会有意料之外的工作。即使有些日子感觉还有些余力,我也在尽量让自己的时间保持空闲。
TinyPilot 数据一览
| 指标 | 2022年10月 | 2022年11月 | 变化 |
|---|---|---|---|
| 独立访客 | 7,994 | 9,512 | +1,518 (+19%) |
| 总浏览量 | 17,862 | 20,387 | +2,525 (+14%) |
| 销售收入 | $85,834.20 | $107,223.10 | +$21,388.90 (+25%) |
| 企业订阅 | $290.70 | $290.70 | 0 |
| 版税 | $5,544.12 | $4,402.50 | -$1,141.62 (-21%) |
| 总营收 | $91,669.02 | $111,916.30 | +$20,247.28 (+22%) |
| 利润 | $26,042.39 | $7,407.30 | -$18,635.09 (-72%) |
TinyPilot 销量再创历史新高,总营收达到 11.2 万美元。这是 TinyPilot 首次单月营收突破六位数。
这次增长很大程度上得益于 TinyPilot 在 Linus Tech Tips 上获得的正面提及,这是面向家庭实验室爱好者最受欢迎的 YouTube 频道之一。尽管那期评测主要介绍的是竞品,但凭借该频道庞大的订阅量,TinyPilot 在接下来两周内订单量大幅攀升。
很高兴看到即便在成本异常偏高的情况下,近三个月的滚动利润仍稳居正值。TinyPilot 目前正额外付费以 3D 打印方式生产超出常规产能的外壳,但随着明年一月切换到金属外壳,成本应该会大幅下降。
我们甚至没有时间来为自己节省时间
十一月的目标之一是开始将履约环节迁移至第三方物流(3PL)供应商。我让履约团队的一位成员梳理现有流程,并准备移交给 3PL 供应商。
接下来的一周,受 Linus Tech Tips 视频的影响,订单量激增,因此 3PL 迁移的调研毫无进展。两周后,我们仍在忙于消化销售高峰带来的订单,依然没有取得任何进展。
下次与履约团队的同事沟通时,我问他平时在处理这类非常规任务上有多少富余时间,结果得知几乎为零。组装设备、打包发货、响应客服请求这些短期任务,就已经占满了他们一周的全部工时。
这种情况我并不陌生,只不过以往那个短期内分身乏术的人通常是我。
对于任何工作流程,通常都有显而易见的省时方法。比如自动化、增聘人手、改用托管服务等等。问题在于,改变流程本身会带来摩擦成本。
过去几个月里,我画了不少关于外包和授权所需时间投入的漂亮图表。延续这个思路,下图展示了我把一项任务交给他人前后所投入的时间:

一开始,这项任务很耗时,因为所有工作都由我亲自完成。招人之后,我反而要做更多工作——既要继续完成原有任务,又要投入招聘和培训新人的工作。只有当新人完全上手后,才能实现净节省,但这可能需要数周甚至数月,具体取决于任务的复杂程度。
现实中,一天只有那么多小时。如果把每日工时的上限考虑进去,会发生什么呢?

糟糕,现在我根本无法进入招人之后的省时阶段,因为我没有足够的短期富余时间去招聘和培训新人。我连为自己节省时间的时间都没有。
把长期任务当作耗竭的早期预警
迁移到 3PL 供应商的延迟让我意识到,我需要一套更好的预警机制来判断富余产能何时将要耗尽。
我目前最好的想法是,更自觉地平衡好每个人的短期任务和长期任务。例如,技术支持工程师的紧急职责是在 TinyPilot 帮助论坛和 CRM 平台上响应客户请求。工单量有起有伏,因此当他们有空闲时,就会去梳理支持请求中的共性问题,发布帮助文档或深入排查缺陷。
TinyPilot 的每个人都兼顾着短期和长期任务:
| 团队 | 短期任务 | 长期任务 |
|---|---|---|
| 创始人 | 团队管理 供应商管理 工作审核 填补职责空缺 | 市场推广 公开写作 战略复盘 招聘与培训 |
| 履约团队 | 组装设备 订单履约 客户服务 | 编写客服操作手册 协助市场推广 |
| 技术支持工程师 | 回答技术支持问题 | 编写文档 撰写博客文章 排查疑难缺陷 |
| 软件开发 | 发布新功能 修复紧急缺陷 | 重构代码 改善开发体验 编写自动化测试 修复非紧急缺陷 |
长期任务可以起到煤矿中金丝雀的作用。当一个团队在长期任务上的进展持续放缓时,很可能意味着他们已接近最大负荷。这时,我就应该通过减少职责或增加人手来减轻负担。
用长期任务作为预警信号有两个难点。首先,最经常忽视长期任务的团队是创始人团队,也就是我自己。当我不堪重负时,就不会注意到其他团队在长期任务上的放缓。即使注意到了,我也没有时间去处理。我想解决办法是更谨慎地控制自己承接的项目数量,以便为流程切换留出富余时间。
另一个问题是,履约团队的长期任务最不明确。我们的生产和履约流程并非那种可以每周都去优化的工作流。不过,随着我们把履约和生产转移给第三方供应商,履约团队的职责将转向客户支持。客户支持在短期工作(回答支持请求)和长期工作(完善内部操作手册)之间有着更自然的平衡。
走出 Ansible 泥潭
Ansible 是一款用于自动化配置服务器的工具。我已经用了七年,家用实验室里的所有虚拟机都是用它来管理的。
早在 2020 年开始做 TinyPilot 时,我需要一种方法把代码部署到 Raspberry Pi 上,并配置 TinyPilot 所需的操作系统功能。远程系统配置正是 Ansible 的看家本领,因此它非常合适。
发布 TinyPilot 时,对我来说让用户安装最简单的方法,就是复用我在开发时的工作流。我创建了一个简单的安装脚本,先引导搭建 Ansible 环境,再通过 Ansible 安装 TinyPilot。
当时我就知道,更常规的安装方式应该是使用 Debian 软件包。可问题是,我对如何制作 Debian 软件包一无所知,而且感觉工作量很大。我需要自己搭建 apt 仓库吗?需要管理仓库密钥吗?TinyPilot 依赖 nginx,那我该如何通过自己的软件包去配置 nginx 呢?
两年半过去了,开发团队正在为我当初选择 Ansible 付出代价。随着 TinyPilot 功能越来越多,我们的 Ansible 配置变得极其复杂。如果安装程序是纯 shell 脚本或 Debian 软件包,安装可能只需 10 到 20 秒。但 Ansible 带来的额外开销却让安装和更新时间拉长到六分钟甚至更久。
除了对最终用户的影响,Ansible 还会大量吞噬开发资源。Ansible 代码调试起来又慢又繁琐,尤其是在处理持续集成环境中没有的操作系统和架构时。哪怕是很小的改动,也常常会膨胀成一周的开发工作量。
近几个月,开发团队一直在探索如何将我们的 Ansible 代码迁移到 TinyPilot 的 Debian 软件包中。很高兴地告诉大家,我们已经取得了初步突破。我们打造了一个混合方案:让 TinyPilot 的 Ansible 角色去安装最新的 TinyPilot Debian 软件包。这样我们就可以逐步蚕食 Ansible 代码,将其一点点迁移到 Debian 软件包中。
以下是我希望在开始做 TinyPilot 时就了解的关于 Debian 的几点:
- 无需自建 apt 仓库,就可以创建和分发独立的 Debian 软件包。
- 如果跟着正确的教程,创建一个简单的 Debian 软件包只需 15 分钟。
- 可以使用 Docker QEMU 在 x64 系统上构建 ARM 架构的 Debian 软件包。
- 如果你的代码是用 Python 这类可移植语言编写的,就可以跳过 QEMU,直接构建与架构无关的 Debian 软件包。
- 如果你的软件包需要配置另一个软件包,通常的做法是在配置目录中添加一个文件,而不是去修改对方软件包拥有的文件。
- 例如,TinyPilot 的 Debian 软件包可以通过在
/etc/nginx/sites-enabled/目录下添加一个文件来配置 nginx。
- 例如,TinyPilot 的 Debian 软件包可以通过在
学习 Debian 最难的部分是在海量信息中找到有用的内容。很多资料基本上都在说:“去读那本 9000 页的 Debian 维护者指南吧,不过要忽略其中过时的部分。”
对我帮助最大的指南是:
- Alex Couture-Beil 的《Creating and hosting your own deb packages and apt repo》
- Vincent Bernat 的《Pragmatic Debian packaging》
Vincent 甚至还热心地与我进行了一次视频通话,解答了我关于 Debian 软件包的一些遗留疑问。
业余项目
ScreenJournal
我看了很多电视剧和电影,也喜欢向朋友推荐,但常常会忘记自己想推荐哪一部。
我找过不少像用 Goodreads 记录阅读那样来记录影视的应用,但没有一款符合我的设想。我觉得朋友们已经对默认公开的社交应用感到疲惫,所以我想要一个能让小圈子朋友共享推荐的应用。少一些像 Twitter,更像 Discord。
我已经开始做一款与朋友分享影评的应用,叫作 ScreenJournal:

ScreenJournal 就像是给沙发土豆准备的 Goodreads。
它还没有完全达到可发布的程度,目前影评仅对自己可见,而且只支持单用户。现在它更像是一个人的私人观影日记,不过我计划中的下一个功能就是支持多用户。
用户管理向来很难做对,所以我一直避免自己实现。过去几年,我一直使用朋友 David Toth 的 UserKit 服务来管理用户。UserKit 很好用,但尚未对外开放,这让想在自己服务器上运行 ScreenJournal 的其他开发者不太方便。
我为 Go 寻找过开源的用户管理框架,但大多数都依赖外部服务的 OAuth,这不是我想要的。剩下的又过于笨重复杂,让我望而却步。
相反,我决定冒险一试,自己实现用户管理。会话管理我会用 jeff,认证则打算用 bcrypt,只能寄希望于一切顺利。
总结
完成了什么?
- 启动了与 3PL 供应商的对接流程。
- 在多个重要方面改进了 TinyPilot 的 Debian 软件包。
- 为国际承包商找到了更好的支付平台。
- Deel 的体验很差,我也不太喜欢 Remote.com,所以我们决定改用 Pilot。
经验教训
- 长期任务是资源耗竭的良好先行指标。
- 如果一个团队在长期任务上的进展持续放缓,就要在失去流程切换余地之前及时处理。
- 对创始人来说,为长期任务保留时间尤为重要,否则就无法有效应对其他团队的资源耗竭。
- Debian 打包并没有一开始看起来那么可怕。
下月目标
- 完成来自 3PL 供应商的首笔订单履约。
- 完成下一个 TinyPilot Pro 版本的代码开发。
- 为一月份发布 TinyPilot Voyager 2a 做准备。
随机一篇博客
评论
登录后参与讨论