自己写了个跨设备图片文字中转池:shotsync
一个自己写的、跑在 Cloudflare 免费层上的跨设备图片文字中转池,手机免装 App,签名链接分享单张图。
之前早睡打卡那篇文章里顺带提过一嘴,说自己做了个跨设备同步的小工具。这次正式写一篇,把它是怎么来的、怎么用、怎么搭的,都理一遍。
先说痛点,其实很朴素:电脑上截个图,想发到手机上看看效果,或者转发到远程(云)服务器中,每次都得先存下来,再隔空投送,或者打开微信给自己发一遍。手机拍了张照片、随手记了句话,想在电脑上继续用,同样麻烦。苹果全家桶用户可能感觉不到,但只要有一台安卓手机、一台 Windows 电脑混在里面,这套流程立刻就变得很别扭。
我不想再为这种小事切来切去,就自己写了一个:shotsync。
它是什么
一句话说,就是自己的跨设备图片/文字中转池。电脑上截完图,自动传到一个网页相册里,手机打开同一个网址就能看到,不用再传一遍。手机上拍的照片、随手记的文字,也能丢进去,等于一个跨设备的剪贴板,哪台设备打开都能拿到。
手机上不用装 App,网页加到主屏幕,用起来跟原生 App 差不多,图标、全屏都有。相册大概每 20 秒自动刷新一次,另一台设备传上去的东西,几秒到几十秒内就能看到。
某张图想发给别人看,又不想把整个相册暴露出去,就点一下生成一个签名链接,7 天后自动失效。池子本身也不是永久仓库,东西放 30 天会自动清掉,定位就是个中转站,不是网盘。
怎么用
第一次在某台设备上打开网址,输入一个访问口令,之后这台设备就记住了,不用每次都输。想加东西,图片就点加图片,从相册选或者直接拍;文字就点加文字,粘贴或者打字进去发送。
点开某一项,能保存到本地、能复制文字、能生成分享链接、能删除。想批量清理的话,进选择模式,勾几个,一起删掉。
Mac 上如果懒得手动截图上传,仓库里还带了个菜单栏小工具,装上之后截图会自动进池子;iOS 上也配了一个快捷指令,任何 App 的分享面板里选一下就能丢进去。这两个是我自己实际在用的部分,比手动上传省事很多。
技术上怎么弄的
这东西没有服务器,也没有数据库,全靠 Cloudflare 的免费额度撑起来:一个 Worker 加一个 R2 存储桶。Worker 负责收图片、收文字、发签名链接、按口令做权限校验;真正的文件都扔进 R2,30 天自动删除靠 R2 自带的生命周期规则,不用自己写定时任务清理。
图片压缩、格式转换这些活儿都放在浏览器里做,手机拍出来的照片本地转成 JPEG、生成缩略图后再上传,Worker 收到什么就存什么,不做任何服务端图片处理,省了不少计算。前端是个 PWA,静态资源和接口都挂在同一个 Worker 上,加到主屏幕就是一个能全屏运行的网页应用。
分享链接靠 HMAC 签名,到期时间编进链接里,Worker 校验签名和时间就知道该不该放行,不用额外存一张「哪些链接还有效」的表。访问口令是单一共享密钥,常量时间比较防时序攻击,但说到底还是一个共享口令模式,不是多用户系统,谁都用这一把钥匙进出。
选这套方案,最在意的两点:一是免费,跑在 Cloudflare 的免费层里,不用为了传张图开个服务器;二是数据只在自己的账号里,不经任何第三方图床或者别人的服务器,截图里哪怕有什么不方便给别人看的东西,也不用担心。
开源地址和局限
代码在 github.com/Defiabell/shotsync,MIT 协议,自己搭一遍大概 5 分钟:建个 R2 桶、设个访问口令、npm run deploy。想先看看效果不想自己搭的,有个只读的在线 demo:shotsync-demo.defiabell.workers.dev。
局限也老实说一下。它是单一共享口令,拿到网址和口令的人可以看、可以传、可以删,适合自己一人多设备或者很小的信任圈子,不是给多用户团队用的工具。分享链接在到期之前是公开的,谁拿到链接都能看那一项。它是个 30 天自动清理的中转池,不是长期存档,重要的东西还是得自己另外备份。界面目前只有中文,想做国际化欢迎提 PR。
顺手解决了自己的一个小麻烦,也算是这半年折腾里比较顺手的一次。
留言
验证暂时加载不到,留言先关闭一会儿。