WPS签到脚本:我是怎么写出一个百星开源项目的
广州七月的夏天,闷热是从地板缝里钻出来的。宿舍里的空调发出沉闷的轰鸣,室友戴着耳机在打游戏,键盘敲击声和偶尔的叹息声混杂在一起。那是一个再普通不过的、甚至有些无聊的暑假下午。
我靠在椅背上,漫无目的地刷着 B 站。屏幕上的视频讲了些什么我已经记不清了,反而是飘过的一条弹幕停在了我的视线里:「WPS 的积分每天签到才能领,但是我老是忘,感觉亏了一个亿。」
我盯着那行白色的字看了几秒,点了点头。我也经常忘。WPS 有一套自己的积分体系,每天点一下签到,日积月累就能兑换会员时长。这其实是产品经理最喜欢用的用户留存手段,用一点微不足道的蝇头小利,换取你每天打开 App 的日活数据。原理大家都懂,但真到了每天去点那个按钮的时候,总是会被各种琐事打断。第一天记得,第二天记得,第三天可能就忘得一干二净。
我关掉浏览器里的视频标签页,顺手点开了桌面上黑色的 VS Code 图标。屏幕亮起的一瞬间,我突然觉得,与其每天被这些 App 绑架注意力,不如写段代码把它们全接管了。
既然要写,就不只写 WPS。我脑子里开始盘算那些需要每天打卡的平台:爱奇艺的 VIP 成长值、全民 K 歌的鲜花、有道云笔记的扩容空间、百度贴吧的经验值,还有 Bilibili、V2EX、AcFun……这些平台的签到逻辑本质上是一样的。我想做一个大而全的脚本,把所有常见的签到源都包进来。一个脚本,一键搞定所有的赛博打卡。
核心思路其实非常线性:抓包,找接口,模拟请求。
我先拿 WPS 开刀。打开 Fiddler,配置好代理,在手机上点下签到按钮。Fiddler 的界面里瞬间涌入了几十条网络请求,我一条条过滤,最后锁定了一个返回 JSON 格式的 POST 请求。点开请求头,分析里面带了哪些鉴权字段。WPS 的接口还算老实,只要把 Cookie 提取出来,用 Python 的 requests 库照猫画虎地构造一个相同的请求发过去,返回的状态码就是 200。
但事情并没有想象中那么顺利。当我把触角伸向其他平台时,才发现各个大厂的安全策略千奇百怪,简直像是在做一场没有标准答案的逆向工程考试。
有的平台比较原始,仅仅依赖长期的 Cookie;有的平台防范意识很强,用了 Token 加上动态生成的签名,我得去翻前端的压缩代码,硬生生把加密逻辑扒出来;还有的像 AcFun,接口里不仅有签名,还加上了时间戳防重放攻击,如果你发过去的时间戳和服务器时间误差超过几秒钟,直接返回 403 Forbidden。
那几天,我几乎从早到晚都挂在抓包软件上。看着终端里不断打印出来的报错信息,改代码,再运行,再报错。直到屏幕上终于跳出一排排绿色的 {"msg": "success"},那种长舒一口气的痛快感,是很难和不写代码的人解释清楚的。
脚本写完跑通了,但我很快意识到一个新问题。如果这个脚本只能在我的电脑上运行,那意味着我每天还是得记得打开电脑,点一下运行按钮。这不过是把「手动签到」变成了「手动跑脚本」,本质上的摩擦力依然存在。
我需要它在云端自动运行。买服务器显然不划算,为了几毛钱的签到积分去租一台几十块钱一个月的云主机,多少有点本末倒置。于是我把目光投向了 GitHub Actions。
这是一个极其优雅的解决方案。我写了一个简单的 YAML 配置文件,设定了定时任务。
on:
schedule:
- cron: '0 0 * * *'
因为 GitHub 的服务器在 UTC 时区,和北京时间差了 8 个小时,所以把 cron 表达式设为 0 0,刚好对应国内每天早上的 8 点。我还加了一段发送邮件的代码,把每天的签到结果汇总成一个表格发到我的 QQ 邮箱。
配置推送到仓库的那天晚上,我特意晚睡了一会儿。第二天早上 8 点过 5 分,手机屏幕亮了,是一封新邮件:「今日签到任务执行完毕,成功 8 项,失败 0 项。」看着那封邮件,我觉得这个项目算是真正闭环了。任何想用的人,只需要 Fork 我的仓库,在 Secrets 里填好自己的账号 Cookie,然后就可以把这件事彻底抛在脑后。
最开始,这个仓库安静得像是一座孤岛。没有推广,没有打广告,我只是把它挂在自己的 GitHub 主页上。后来觉得有点可惜,就在 V2EX 和几个平时潜水的软件工程交流群里发了帖子。
发完帖子的那个下午,我时不时就会去刷新一下网页。群里的反应很平淡,偶尔有人回一句「插眼」或者「会被封号吗」,然后很快就被其他聊天的消息淹没了。V2EX 上倒是有了几个点击,但大家似乎对这种小工具司空见惯。我关掉网页,心里稍微有点失落,但也觉得正常。毕竟在这个信息过载的时代,谁会在意一个三本学生写的小脚本呢。
第一个 Star 是在三天后出现的。那是一个完全陌生的 ID。我盯着屏幕右上角的那个小星星,点进那个人的主页看了一圈,猜测他可能也是个在校学生。那种感觉很奇妙,就像是你在海边随手扔了一个漂流瓶,你以为它会沉入海底,结果某天在另一个海岸线上,有人捡起它,并且对你挥了挥手。
然后慢慢地,数字开始跳动。10 个,20 个,50 个。
大概在仓库超过 100 个 Star 的时候,我才真切地意识到,原来有这么多人每天都在依赖我写的这几百行代码。
随之而来的,是维护的压力。有一天早上,我收到了一封 GitHub 的 Issue 邮件,标题很简短:「爱奇艺签到失效,报错 400」。我心里咯噔一下,赶紧打开电脑复现。原来是爱奇艺的接口更新了验证逻辑,增加了一个新的 Header 字段。我花了一上午的时间重新抓包、调试,把补丁打上去,然后回复那个 Issue:「已修复,请拉取最新代码。」对方很快回了一个大拇指的 Emoji。
最让我意外的,是开始有人给我提 Pull Request。有一天,一个我不认识的开发者提交了一段代码,帮我把网易云音乐的签到模块也加了进去。我看着他写的代码,结构很清晰,甚至在某些异常处理上比我原本的写法还要严谨。我点了 Merge,那一刻,这个脚本不再仅仅是我一个人的玩具了。
还有人在 Issue 区留言,不是为了报 Bug,只是简单地说了一句:「用了半年了,每天都在用,帮你省了不少买会员的钱,谢谢作者。」
我看着那条留言,坐在宿舍的椅子上发了很久的呆。
在现实生活里,我只是广州商学院一个普通的软件工程大四学生。我也会为了 GPA 去抠那些无聊的考试细节,也会为了双国奖的答辩紧张到手心出汗,也会在深夜里对未来的工作和去向感到迷茫。但在那个名为 wps_script 的仓库里,我只是一个 Maintainer。
开源这件事,以前总觉得是个很宏大、很极客的词汇,好像只有那些写出 Linux 操作系统或者 Vue 框架的大神才配谈论。但现在我有了不一样的感受。开源其实挺平易近人的。你只是因为自己生活中的一点小烦恼,写了一个不怎么完美的东西,然后你没有把它藏在自己的硬盘里,而是坦然地扔到了网上。
然后它就有了自己的生命。它会遇到接口失效的阵痛,会得到陌生人的修补,会和这个世界上各种各样你永远不会在现实中遇见的人产生真实的联系。
项目地址:github.com/poboll/wps_script ⭐ 139
139 个 Star,在 GitHub 浩瀚的星海里不值一提。但对我来说,那是 139 个在无数个清晨 8 点,被我的代码悄悄触碰过的生活。