自动化数字生活:收藏网页 - Android

相比于 iOS 较为严格的沙盒环境,Android 提供的自动化工具就可以自由得多了。

趁手的工具

由于自动化工具需要的权限较多,并且我们还会在系统中进行设置,来让它们保持运行,避免「自动化」失效。所以出于安全考虑,我非常建议从 Google Play 上下载官方版本的应用。

较为成熟和推荐的应用有两款,一个叫 Automate,另一个是 Tasker。两者在功能性上并无太大差异,但是编写脚本时的思维方式还是挺不一样的,需要适应。

本文主要会以 Automate 作为示例,稍微提一嘴 Tasker。

先睹为快

在 Automate 中最终编辑完成的工作流大概长这样:

这里一共有三个入口,也就是三个「Flow beginning」,不过经过处理之后,最终汇集到同一个分支流中,这个分支流的主要功能是向服务器发出请求并处理应答。

所以总的思路跟前面说过的自动化工具一致,无论是 iPhone 上还是 Windows

新建一个工作流

安装好 Automate 后,点击主界面右上角的加号,新建一个工作流。

在工作流编辑界面,点击左上角的菜单可以打开所有结点的列表来供选择,

当然,一般使用「搜索」的方式来找结点……结点归类很迷,不大好找。

不能更快:剪贴板直接保存

这个入口我在 Android 上用得非常频繁。在 iPhone 上由于不能后台监控剪贴板,所以无法实现。

最终实现的效果是,当我在微信公众号的页面选择「复制链接」之后,书签就直接保存了。

主要的入口部分代码是:

结点 17 指示了当前工作流的一个入口。为了便于后面代码的服用,入口是可以设置多个的,启动时可以选择其中一个或者多个入口。

每一个入口都可以设置名称,方便识别。也可以指定桌面快捷方式直接启动。

结点 18 用于等待剪贴板的修改事件。在 Automate 中,结点一般分为两类,一类是立即执行的,一类是由监听事件触发的。

事实上,同一个结点往往兼具了这两种形式。比如这个剪贴板的结点,既可以立即获取当前剪贴板内容并执行下去,也可以设定成在剪贴板发生变化的时候才执行。

涉及到输出时,可以直接指定一个变量,输出会自动赋值给这个变量。

这里我们启动名为「copy」的入口之后,就开启对剪贴板修改时间的监听。如果剪贴板发生了改变,那么把修改后的剪贴板内容放入到名为「shared_text」的变量中,并启动一个新的分支流,来判断是否需要保存这个书签。

结点 20 启动了一个新的分支流,NEW 出来的分支流会独立执行,OK 引出的线条会在启动分支流之后立即执行下去,这样相当于开启了同时执行的父子两个流。

结点 21 采用正则表达式判断剪贴板中是否包含了我们所需的网址。我这里以知乎、微信、澎湃新闻和 V2EX 为例,具体的格式可以先查看每个应用分享出来的网址。

对每一个结点而言,点击蓝色部分的结点名称(如「Expression true?」就是结点名称),可以打开左侧描述抽屉。其中描述了每一个结点的输入、输出和处理过程,还有一些可供参考的链接。

在结点 21 中,我使用了 match 函数来判断字符串是否匹配。这个函数的原型为:

array matches(value, regex)

在正则式的开头可以设置标识位,来指定正则式的执行方式。这里 (?ms) 可以理解成对多行文本的适应,因为很多应用复制出来的链接并不只是一个网址,而会带着文章的摘要。具体标识位的用法可以看官网文档

此外在文档中也提到:

the whole regex must match, for a partial match use ., e.g. .*foo..

所以我在表达式的首尾都加了 .* 来正确匹配。

至此,通过复制直接保存书签的前置工作就完成了,现在书签地址保存在 shared_text 变量中,供之后的网络请求来调用。

灵活的下拉菜单按钮

由于不可能对剪贴板中的所有地址都直接保存,下拉菜单中的快捷方式按钮就可以很方便地「手动」保存了。

基本的原理是,先把网址复制到剪贴板中,然后触发这个工作流,令其读取剪贴板并保存书签。

入口部分的代码是:

结点 8 是入口结点,取名为「clipboard」。

结点 16 配置了一个下拉菜单按钮。自定义下拉菜单按钮的功能是在 Android 7 的时候引入的,不过时至今日也没有多少应用支持。

配置完之后,需要手动去下拉菜单的「编辑」选项中把这个按钮激活。

结点 9 选择了「立即」获取剪贴板内容,并同样把网址放到 shared_text 变量中。

结点 10 创建了一个新的分支流,并循环回结点 16,等待下拉菜单按钮点击事件再次触发。

和前面一个入口一样,这里也为下一步网络请求提供了保存于 shared_text 变量中的一个地址。

不过这个地址很可能并不是纯粹的,许多应用在复制到剪贴板时会掺杂着文章标题等内容。这个自动化脚本中不予处理,而放到服务器端的预处理程序中。

直接走系统分享菜单

系统分享菜单其实是一个不可或缺的入口,只不过现在 Android 上的应用们基本都自己实现了一个分享菜单,调用系统分享菜单往往需要多按好几下,而像微信则根本不允许调用系统分享菜单,只能在它自己适配的几个分享选项中选择。

系统分享的效果如下:

入口代码也非常简单:

结点 1 和 7 自不必说,结点 2 配置了一个系统分享菜单的选项,并指定了在分享内容为文本时显示。

系统分享的第一个选项「TITLE」可以指定在分享时的菜单中显示的提示语。

同样的,分享获得的文本内容会保存到 shared_text 变量中。

网络请求和应答处理

现在前面三个入口都使用了一个 shared_text 变量,并都通过「Fork」结点引出了一个新的分支流。

网络请求的代码如下:

入口是中间的 22 号结点,为了可能出现的网络异常,我这里做了个异常捕获,要是抛出异常,可以重试三次。失败了会在结点 23 中打印信息,然后在结点 3 中重新发起网络请求。

结点 23 用于调用系统的 Toast 接口来显示信息,Automate 中字符串的组合符号用的是 ++ 两个加号。

结点 3 用于网络请求,网址、请求方法和请求体都可以依据自己设计的 API 来填。这个结点支持 HTTP BASIC AUTH,添加账户后还可以在多个 Automate 脚本中共享。

最后输出的是应答码和应答体,分别保存到一个变量中。

收到的数据类似这样:

{"message":"Pinboard: success","title":"SanKo Blog"}

使用 jsonDecode 函数进行解析,并把 message 的值保存下来,分别用于日志记录和屏幕提示。

结点 5 用于设置变量,这个结点比较有趣,输出在前,输入在后,大概是为了满足「赋值」这个概念,与一般的编程语言相仿。

结点 6 会调用 Automate 的日志,记录后方便查阅。

结点 4 依然是一个 Toast 结点,用于在屏幕上显示简单的提示文本。

大功告成

好,现在可以保存编辑后的流,回退一步到流的设置页面。点击「Start」按钮。

如果没有获取到全部结点所需的权限,那么此时会弹出请求,选择「Grant」后,应用会唤起 Google Play 来安装相应的权限插件。Automate 的权限全部以插件的形式提供,一个新的权限就是安装一个应用,移除一个权限就是把它卸载掉。

安装完成后再回来点击「Start」按钮,就可以看到入口的选择菜单了,可以选择需要激活的入口,或者直接点击「All」激活全部入口。

现在,就可以使用前面所说的三种入口,分别来试一试啦。

另一个选择:Tasker

作为比 Automate 更出名的 Android 自动化工具,Tasker 同样值得看看。

我这边做一个简单的示例,实现:

  1. 复制任意内容
  2. 上传给预处理程序
  3. 显示结果

当然,Automate 能实现的那些工作,Tasker 也都能实现,这里只是稍作演示。

最终的效果跟 Automate 剪贴板直接收藏的入口一模一样,不再另外配动图。

此外,我强烈推荐你切换到英文,因为中文翻译实在是硬伤太多。

任务

与 Automate 和 Workflow 以「流」的形式从入口到功能一步步编写下来的逻辑不同,Tasker 中首先编写「功能」,而后确定「入口」。

切换到「任务」选项卡,新建一个任务,继续点击加号,新建一个操作。

任务相当于一个「函数」,而操作就相当于「语句」。选择操作的时候,依然可以直接搜索,而不用理会那些分类。

在 HTTP POST 操作中,填入正确的服务器地址和访问路径。数据就是 POST 的请求体,后面类型选择 application/x-www-form-urlencoded 时,这里直接采用 key=value 的格式即可。

数据中的 %CLIP 是全局变量,指代剪贴板内容。变量可以点击下面左图按钮展开,对应于各个参数的可选项可以点击下面右图的放大镜按钮。

应答数据如果是纯文本,那么会自动保存到 HTTPD 这个全局变量中。

不过我这边选择保存到一个文本文件中处理,因为 HTTPD 这个变量对服务器返回数据的要求比较高,并不一定能成功赋值。

接着就读取文件,把应答数据读出来。根据官方介绍,变量名至少一个大写字母时,这个变量就是个全局变量,在所有脚本中都有效。

再下面一步就必须硬编码了,我搜了一下,好像 Tasker 要处理 JSON 格式的数据只能写代码。这里也可以看到,Tasker 支持直接运行代码片段。

var msg = JSON.parse(resp).message

最后开一个闪光灯,显示一下这个 msg 变量,也就是服务器返回的书签保存结果。这里的「闪光灯」是翻译失误,原文是「Flash」,调用的是 Toast。

至此,任务编写完成,可以手动复制一个链接到剪贴板中,点击「任务编辑」界面左下角的播放按钮,查看运行是否正常。

配置文件

在 Tasker 中,入口称为「配置文件」。要监听剪贴板,选择「事件」下面的「变量集」。这里的「变量集」也是个翻译失误,原文是「Variable Set」,监听的是指定变量的赋值事件。

这里选择剪贴板内容 %CLIP 来监听即可。而后选择我们刚刚编写的任务作为触发任务,整个脚本就可以跑起来了。

现在,可以直接去复制一个链接,试试看能不能正确发送请求并处理消息。