agentzh
19-07-20 12:33 微博认证:OpenResty Inc 创始人

UNIX 文化的核心之一是工具编程,即每项功能都实现为一个小工具,然后在 shell 层面进行串并联组合。可惜 UNIX 的 shell 从来没有足够靠谱和足够强大过。于是大家又去写 Perl 和 Python 之类的东西,在里面内嵌 shell 命令,但很容易变得恶心,同时还要小心注入,另外也远不够灵活。

所以最近花了一个多月的时间实现了一个我梦想了多年的自动化命令行终端的小语言,叫做 opslang。编译器本身和生成的代码都完全基于 OpenResty 技术栈实现。OpenResty 的 ngx.pipe API 是实现 opslang 的核心技术之一,从而实现运行时的 100% 非阻塞通信。而流式正则匹配和替换技术则是另外一个基石。

这种小语言以基于规则的方式,可以摸拟人类直接对终端摸拟器进行各种复杂的操作,也支持像 screen/tmux 工具那样同时创建多个终端窗口,自动按需来回切换着操作,也可以使用多个轻线程同时在这些虚拟窗口中操作。可以像 Tcl/Expect 一样对终端输出进行模式匹配和交互操作,而且对终端控制序列的处理远比 Expect 来得更加透明和智能,可以同时并行匹配多个正则模式和规则。

Opslang 原生识别 shell 语言的记法,所以会自动根据在 shell 命令串中引用 opslang 变量的上下文,使用正确的转义规则(比如 Bash 里在双引号里面和外面的转义规则就很不一样)。这就根除了 shell 注入攻击的可能性,同时 opslang 代码可以保持优美和简洁。

Opslang 也支持 Gnu make 那样的目标和目标依赖描述,只不过这里的目标都不直接对应文件系统上的文件,而是抽象的。这样可以实现自动依赖计算和增量构造。

同时也内建了各种重试机制(比如变长等待延时的多次重试)和强大的异常处理模型。用户可以自定义异常。同时也有完整的算术运算、字符串操作、赋值运算、数组/哈希/标量等变量。用户自定义函数。拥有完整的模块系统,可以自定义模块并用 use 语句来加载。

目标机器上也无需预装任何软件,只要有标准的 bash 就可以了。毕竟 opslang 是直接摸拟的人类操作。

下面的图一是一个很简单的 opslang 样例程序,图二是这个程序执行后产生的终端操作日志。很像人类直接操作哈?