又是一个双周的周五,到了我向社区汇报最近这个 Iteration 进展的时候。本次 Iteration 是我个人的第五个周期,从 2022-01-172022-01-30,共计两周。完整的工作内容可以参见 Xuanwo's Work: Iteration 5

接下来会按照项目组织逐个讲讲我觉得有意思的地方。

Rust

首先聊我们最爱的 Rust。

上个周期我就提到了 PR std: Implement try_reserve and try_reserve_exact on PathBuf 相关的工作,在永远的神 @dtolnay 的帮助下,这个周期终于合并进去了,预计会在 Rust 1.60 中发布。这个 PR merge 后,feature try_reserve_2 需要的实现工作已经都完成了,我们邀请了 Lib Team 的成员开展 FCP (final-comment-period),他们将会决定是否稳定这些接口。

sqllogictest-rs

sqllogictest-rssingularity-data 团队基于 sqllogictest 实现的 SQL 正确性验证框架。我这个周期看了一些 Databend 测试相关的内容,于是顺手贡献了一些东西。

sqllogictest-rs 之前只支持静态的内容,没法验证会产生动态内容的 SQL 是否正确,比如说:

SELECT now();

Databend 目前的做法是在正确的输出之外提供一个 filter 文件,通过 sed 过滤来判断,看起来大概是这样:

SQL 语句:

SELECT * from system.tables where name = 'tables';

结果使用占位符而不是真实的数据:

system	tables	SystemTables	yyyy-mm-dd HH:MM:SS.sss +0000

然后附加一个 result_filter 文件:

\d\d\d\d-\d\d-\d\d \d\d:\d\d:\d\d[.]\d\d\d [+-]\d\d\d\d
yyyy-mm-dd HH:MM:SS.sss +0000

在测试的时候需要调用 sed 来做正则匹配。这样不仅实现和维护起来麻烦,测试的效率也不高。

所以我在这个 PR 中增加了 Validator 的抽象,让用户可以自行控制验证的逻辑。用起来的感觉如下:

fn main() {
    let script = std::fs::read_to_string(Path::new("examples/validator.slt")).unwrap();
    let mut tester = sqllogictest::Runner::new(FakeDB);
    // Validator will always return true.
    tester.with_validator(|_, _| true);
    tester.run_script(&script).unwrap();
}

通过 with_validator 传入一个 Validator = fn(&Vec<String>, &Vec<String>) -> bool 即可,我感觉我设计的海星

未来会尝试把部分 Databend 的测试迁移到 sqllogictest-rs 上来,不再依赖外部的各种工具,一方面能提升测试执行的速度,另一方面也能够改进开发者编写测试用例的体验。

bentoml/Yatai

Yatai&yetone 主导设计和开发的 ML Ops 平台。乘着宣布开源的东风,我借机水了一个 PR,把所有的 Go import 都按照统一的格式进行了整理。期间还暴露了项目的 CICD 中 golangci-lint 没有正确运行的问题,这些八卦欢迎来 *: Format import 查看。

Databend

剩下的工作就是跟 Databend 相关了。

目前主要关心的还是 Databend 与持久化数据存储的交互的 Data Access Layer。我之前发起了一项名为 DAL2 的工作,旨在重构 DAL 层,让它能够更容易的接入新的存储后端。这个周期工作进展不少,DAL2 的接口基本成型,部分模块切换成了 DAL2,已有的测试用例全部通过。

得益于 DAL2 的优秀抽象,我们能够增加一个通用的 Interceptor / Layer 层来运行用户对 DAL2 的行为做一些装饰,增加回调的处理。这样可以满足业务对 DAL2 的要求,比如说 Metric 等等。等到所有的模块都切换成 DAL2 之后,就能让社区一起参与进来,去实现更多的存储后端。

除了 DAL 之外,我还做一些简单的工程效率工作,处理了一些跟 CI 相关的问题,包括为 Databend 引入了 peotry 来管理 Python 依赖等等。其中有个社区里经常遇到的问题是 CI 中使用了错误的 Rust 版本。

过去我们经常会使用这样的 action 来初始化 Rust 构建环境:

- uses: actions-rs/toolchain@v1
  with:
    toolchain: stable
- uses: actions-rs/cargo@v1
  with:
    command: build
    args: --release --all-features

这往往会导致 CI 中实际使用的版本跟我们预期的不一致,解决方法很简单:将 actions-rs/toolchain@v1 这一步去掉即可。因为通过 rustup 安装的 cargo 在首次运行的时候会自动选择正确的工具链,并不需要额外的配置。我在 Rustup 实现原理 中介绍了具体的行为,感兴趣的同学可以去看看~

Xuanwo

这个周期一直在高强度跟 Async Rust 打交道,突击学了不少相关的概念和知识,解决掉了很多一直以来的困惑,这些都记录在了 Xuanwo's Note 中:

从这个周期开始,我还在尝试每天在 Twitter 上分享今天学到了什么。最让我开心的是某天关于 Futures 的分享还启发了参考资料中的作者 @JmPotat0,帮助他将自己的文章补充的更完整,形成了一个正向循环。

这种互相连接的感觉很棒,希望以后也能跟推友们共同学习,一起进步!


总的来说这个周期过的比较充实,我们年后再见~