速来报名!AICon北京站鸿蒙专场~ 了解详情
写点什么

拒绝背锅!39 岁失业后,我写出了一个超一万亿使用量的数据库

  • 2024-08-19
    北京
  • 本文字数:5000 字

    阅读完需:约 16 分钟

大小:2.39M时长:13:56
拒绝背锅!39岁失业后,我写出了一个超一万亿使用量的数据库

SQlite 如今走过了 24 个年头,如今有了超一万亿的活跃使用量,它被许多顶尖的网页浏览器、操作系统、移动电话和其他嵌入式系统使用,是部署最广泛的数据库引擎之一,许多编程语言都有与 SQLite 库绑定。但 SQlite 背后的贡献开发者却只有三人,其中项目最初的开发者 Richard 也已经 63 岁。Richard 如何失业后“闲着也是闲着”,然后搞出了这么一个使用范围超级广的通用关系数据库?

 

“不想背锅”


1992 年,31 岁的 D. Richard Hipp 在 Hwaci.公司负责技术开发,他的专项团队中有一个客户是巴斯钢铁厂,负责为 DDG-79 Oscar Austin 号开发软件——那是一艘庞大、复杂、随时都会出毛病的战舰。

 

当时的数据库 Informix 运行得并不好,有时候服务器会宕机,导致应用程序无法运行。船员双击这款软件后会弹出对话框报错:“无法连接到数据库服务器”,而负责此项目的 Richard 团队对此无可奈何,因为他们无权控制数据库服务器。

 

Richard 之所以被选中,是因为他向来以能解决难题而闻名。“头顶着技术团队的名号,出的问题还是要由我们背锅,毕竟对话框这块可是我们负责的。”Richard 说道。

 

Richard 团队的思路是哪怕在战斗中受损,整个船舶系统也应该能够正常工作,因此数据库必须可靠。事实上,他们做的事情很简单,就是把数据读入 RAM——不做事务处理、不做任何类似的操作,只是把数据拉入内存。

 

这给了 Richard 这样的领悟:我们为什么非得需要服务器?为什我不能直接从磁盘驱动器上把数据提取出来?这样如果计算机运行状态良好,它就能运行应用程序,整个流程中不再存在可能导致失败的依赖项。

 

但四处打探后,他发现当时根本就没有能做到这一点的 SQL 数据库引擎。之后,Richard 的一位同事提醒道:

 

“Richard,你为什么不自己写一个呢?”

“行啊,我试试吧。”

 

Richard 回应了,但并没有立马动手。2000 年左右,公司资金中断,当时恰逢纽特·金里奇和比尔·克林顿就国会预算案发生了争执,导致所有政府合同都被取消了,Richard 被迫失业了好几个月。

 

“闲着也是闲着,正好来写那个数据库引擎。”就这样,Richard 开始了 SQLite 的研发。

 

2000 年时,人们主要使用拨号上网,只有 1%的美国家庭拥有网络带宽,因此 Richard 不像现在的人们那样可以谷歌搜索学会构建数据库。

 

但他根据自己先前的编译器构建经验制定了一项清晰的计划:如果把每一条 SQL 语句视为一个程序,那自己的任务就是把这些程序编译成某种可执行的代码。

 

因此,Richard 编写了一套能够实际运行查询的字节码引擎,之后又编写了一款编译器,用于将 SQL 转换成相应的字节码。就这样,SQLite 诞生了。

 

可惜它并没有在 Richard 当时从事的战舰项目上发挥作用,因为那个项目被关闭了。后来项目重启,Richard 尝试把 SQLite 引入其中进行测试。不过遗憾的是客户坚持使用 Informix。“倒是可以理解,但 Informix 在开发方面的使用感受真的很差。”Richard 说道。

 

为了不浪费,Richard 把它放在了互联网上,于是有更多人开始使用。“当时还没有 Twitter 之类的东西,但已经有帖子说‘哇,我在自己的 Palm Pilot PDA 设备上运行 SQL 数据库啦!’不开玩笑,这样的事情当时确实吸引到很多人的关注,这也激励着我继续做研究和开发。”Richard 表示。

 

“其实我只是在到处借鉴”

 

“我最早开始编写 SQLite 的时候,曾经到处搜寻,想要看看有没有关于如何编写 SQL 数据库引擎的参考资料。可我什么都没找到,所以只能边做边学边发明。这是个完全由自己摸索出来的路径。”Richard 说道。

 

大部分理论都是由麻省理工学院、哈佛大学、剑桥大学或者伯克利大学的研究小组提出的,而如果大家没上过这些学校,就很可能完全没听说过这些理论,更没有靠谱的方式能够查询相关资料。

 

但奇怪的是,如果回头看看 Postgres 使用的火山模型和 SQLite 曾经使用的字节码模型,就会发现大家都不约而同选择了类似的方向。这些方案虽然从宏观来讲起点各不相同,但大家在如何提高速度表现方面却意见统一,所以 Richard 认为这也是对理论的一种印证,两条独立的开发路径得出了同样的答案。

 

例如,Richard 就从来没听说过覆盖索引。只是在一场位于德国的 PHP 大会上,他见到了 MySQL 初创团队成员之一的 David Axmark,Axmark 解释了 MySQL 是如何实现覆盖索引的。Richard 想,“哇哦,这个想法简直天才!”于是在回途的飞机上就开始为 SQLite 编写覆盖索引。

 

“其实我只是在到处借鉴。”Richard 说道,人们会分享自己的心得,有人会主动找他:

 

“你为什么不试试这种优化方法?”

“我没想到啊。”

“那你看能行吗?”

“那就试试呗。”

 

之后它就成了 SQLite 的一部分。这就是边做边学边发明的好处。

 

SQLite,“三战”成名

 

SQLite 开发出来的头一两年,Richard 忙于推进他的数据库项目。突然,有一天他接到了当时科技巨头摩托罗拉打来的电话。

 

“你好,我们正在设计一款新的手机操作系统,而且打算将 SQLite 纳入其中。你能为我们提供支持吗?”

“哦,可以的。我没问题。”

“那能不能给报个价?”

“好的,这样吧,明天咱们再打个电话,到时候我给你答复。”

 

当时 Richard 的内心一阵狂跳——居然还能靠做开源软件赚钱?真有这样的事?我该定多少钱?怎么办怎么办……Richard 四下搜索,想出了几种定价策略。摩托罗拉当时还有改进要求,需要适应手机硬件,于是 Richard 报了 8 万美元左右。“在当时的我看来,那数字简直就是在明抢,可以说贵得离谱。”

 

后来,Richard 又找来三位前同事一起做这个项目,而这就是 SQLite 项目起飞的原点。

 

而真正让 SQLite 走上成功道路的是诺基亚手机的操作系统塞班。塞班打电话希望 Richard 在感恩节那天能飞一趟伦敦总部。去了之后,Richard 才发现,塞班之前已经搞了一场大规模的招标,从中挑选出塞班系统的数据库引擎。

 

当时参加选拔的大约有 10 种不同的数据库引擎,其中有两款是开源项目,另外七款属于专有产品。塞班在数据集上运行了这些引擎,想看看哪种最适合自己的需求,最后 SQLite 顺利胜出。塞班还给了其他九家调整的机会,但最后又是 SQLite 赢了。

 

Richard 过去后,塞班的人对 SQLite 大加赞赏,同时又提出了一些改进要求。之后,双方签订了合同,由 Richard 负责做相应的开发。

 

当时 Richard 几人真的是尽心尽力,Richard 本人差不多是全职在做这方面工作了。

 

但是,后来塞班的人告诉他们:“不好意思,你得想办法提高巴士因子。”他们觉得 SQLite 的巴士因子不够……所以希望建立一个 SQLite 联盟,让更多人参与进来以保证项目长期存续。

 

注:所谓巴士因子,就是说一支团队里有多少成员意外被巴士撞了(或者受其他偶发因素影响而无法继续工作),才会导致项目陷入停滞。

 

接到需求后,Richard 开始推动这项重要工作,但他其实也不知道该怎么做。后来,当时 Mozilla 基金会的负责人 Michell Baker 听到了风声,主动给他打电话说:“Richard,你的做法有问题,让我来告诉你怎么建立一个联盟。”

 

Baker 制定了规则,强调“开发者必须掌控一切,开发者的决定就是最终决定。对于批准哪些内容加入项目,其他人没有投票权。企业参与者只有享受成果和贡献资金的荣誉头衔,但决定还是要由你自己掌握。”她对此非常坚定,而且对我可以说是知无不言、言无不尽。

 

Baker 是律师出身,我问她“那要怎么吸引人们加入?得设置怎样的激励措施?”她回答道,“别担心,人们肯定会加入的。只要按我的办法来,Mozilla 首先就会成为创始成员之一。”而在联盟计划公布后,果然吸引到了 Mozilla、塞班和 Adobe 的支持,各方共同成立了 SQLite 联盟。

 

值得一提的是,SQLite 的版权声明中还有一条:Open-Source, not Open-Contribution(开源,但是并不开放代码贡献)。因此,至今 SQLite 项目总共只有三位开发人员 D. Richard Hipp、Dan Kennedy 和 Joe Mistachkin。

 


构建智能手机这样的嵌入式开发是个缓慢的过程,需要长时间的迭代循环,更需要花时间等待各种功能在原型设计中一一体现,人们只能在看起来跟成品完全不同的“坯子”上进行开发。

 

谷歌联系了 Richard,当时的搜索巨头还跟手机或者嵌入式开发牵不上半点关系。

 

2005 年左右,Richard 几人正在跟 Android 开会,那时候这款如今声名大噪的操作系统还没真正出现,当时也没有 iPhone。那时候的手机下方是完整的 QEWRTY 全键盘,上方则是个较小的显示窗口。

 

Richard 团队使用 SQLite 进行调试:端连着手机,另一端在工作站上运行调试器。“这种感觉挺神奇的。其他人都不会干,而当我们把手机接入调试器时,电话响了。这位同事看了一眼说,‘哦,是我老婆,我得接个电话,不好意思。’我离开了房间,留他慢慢跟妻子聊天。”

 

当时 Richard 虽然表面上不露声色,但脑袋里却炸开了锅。“我们居然在接着公共网络的手机上调试应用程序,而且完全不耽误正常通话,这真是太令人震惊了。无论是摩托罗拉、塞班还是诺基亚,当时都没人能做到这一点。就在那个瞬间,我就知道 Android 绝对会大获成功。”

 

“我真的以为能写出没有 bug 的软件”

 

不过幸福之后,烦恼也会随之而来。

 

“我们曾经天真地宣传,SQLite 从不出错,至少不会搞出严重的 bug。但 Android 证明我们还是太过年轻、有时幼稚。我以前真的以为能编写出没有 bug 的软件,可一旦软件被发布到数百万台设备上时,引发的 bug 数量绝对会多到难以想象。”Richard 回忆道。

 

当时还在为航空电子设备制造商 Rockwell Collins 工作的 Richard,了解到了 DO-178B 的概念,他意识到其中最有价值、最关键的理念之一,就是要求实现 100%的 MCDC 测试覆盖率。

 

注:MCDC,指的是确定代码修改条件的决策覆盖率。也就是说测试必须保证所生成二进制代码中的每个分支操作至少跑通一次。

 

受到启发后的 Richard 决定通过编写测试让 SQLite 也达到 100%的 MCDC 覆盖率,而这花了他整整一年的时间,每周要工作 60 个小时。

 

“这项工作相当相当艰苦,我每天要干 12 个小时。这段经历真的让我感到厌倦,而且相信大家都听过一句老生常谈:我们用前 95%的预算干完了 95%的工作,再用另外 95%的预算做完最后 5%。实际情况确实如此,把测试覆盖率推到 90%甚至 95%都很容易,可最后这 5%则是难而又难,我花了大约一年时间才达成这个目标。”Richard 回忆时说道。

 

对于典型的发布周期,他们要运行十亿级别的测试,大约有 10 万个不同的测试用例。他们的第一项测试是用 TCL 编写的,真正 100%覆盖的 MCDC 测试名叫 TH3,属于专有成果。Richard 本来希望把这些测试出售给航空电子设备制造商赚点钱,但一份都没卖出去。

 

团队有一个叫 SQL 逻辑测试的工具,目的是设法让每种数据库引擎都出现段错误,其中也包括 SQLite。“我们搞崩过 Oracle,包括 Oracle 的商用版本。我们搞崩过 DB2,尝试把我们能接触到的所有数据库并努力把它搞崩。”Richard 提到,唯一的例外就是 Postgres,它的稳定性给 Richard 留下了非常深刻的印象。

 

总之,提高测试覆盖率成了一项深远影响的决策,Richard 团队在接下来的八、九年里再也没遇到过任何 bug。

 

“我的项目听我的”

 

SQLite 基本上全都是 Richard 亲自动手开发的依赖项。除了 C 编译器和 libc 之类的现成方案,他甚至构建了自己的源代码控制系统和 bug 跟踪器。总之,Richard 的项目都由他来掌握。

 

“人们去背包旅行或徒步,表面上看是种自由,但实际上途中到底如何取决于他们的背包准备得是否充足。因此,他们讨论的自由其实就是自己到底为此付出了多少心力。”Richard 说道,“所以当我们编写自己的项目时,肯定可以享受其中的自由、不再受到其他人的约束。毕竟我们不依赖于不同供应商直接提供的现成方法。”

 

就像当初选择使用本来开源的 Berkeley DB 作为 SQLite v2 版本的存储引擎的话,当它被卖给甲骨文、成了双源专有模型后,本来理想的情况就变得相当被动。

 

SQLite 中的解析器生成器 Lemon 是多年之前 Richard 亲手编写的。“每当我需要一些无法从 Yacc 或者 GNU Bison 处获得的新型语言功能时,由于拥有对解析器生成器的掌控权,我可以随时调整 SQLite 的版本控制系统并做出自己想要的调整。”

 

他最初使用 CSV,因为 2000 年那会儿每个项目都在使用 CVS, 而进入 2000 年代中期后则需要更好的系统。Richard 先后研究了 Git、Mercurial,又回顾了自己的需求,突然发现“得自己写一个才行”。于是 Richard 编写了自己的版本控制系统,而现在它本身也成了独立的项目,而且效果非常好。

 

“因为是自己亲力亲为,所以它能够充分满足我的需求,可以跟一切原有、现有及未来将要出现的工作场景相契合。”Richard 说道,“这种自己动手方式能把命运把握在自己指尖,以摆脱第三方的方式真正拥抱自由。”

 

原文链接:

https://corecursive.com/066-sqlite-with-richard-hipp/

2024-08-19 11:208388

评论

发布
暂无评论
发现更多内容

Java-23种设计模式概述,手动实现一个简单的AOP框架

爱好编程进阶

Java 面试 后端开发

两个通宵熬出来的互联网大厂最新面试题收集整理1000道(七-并发编程-下篇),欢迎点赞收藏!!!

爱好编程进阶

Java 面试 后端开发

星环科技春季新品发布周,4月19日-23日重磅内容等你来解锁!

星环科技

SpringMVC之Interceptor拦截器之登录拦截器,阿里巴巴java面试题

爱好编程进阶

Java 面试 后端开发

2021阿里总监最新整理:初级-中级-高级大厂面试真题(附答案解析

爱好编程进阶

Java 面试 后端开发

Sentinel FlowSlot 限流实现原理(文末附流程图与总结),50家大厂面试万字精华总结

爱好编程进阶

Java 面试 后端开发

【阿里Java岗的魔鬼三面】狠心刷完这6份pdf,java关于异常的面试题

爱好编程进阶

Java 面试 后端开发

世界级计算机大神花两年总结出2000页深入理解计算机系统文档

爱好编程进阶

Java 面试 后端开发

架构实战营 - 第 6 期 模块三课后作业

乐邦

「架构实战营」

JavaEE框架学习笔记——SpringMVC篇,java集合详解和集合面试题目

爱好编程进阶

Java 面试 后端开发

百度ToB垂类账号权限平台的设计与实践

百度Geek说

架构 后端

无聊科技正经事(第1期):裁员毕业潮,你焦虑吗?

潘大壮

裁员 周刊 科技

【并发编程系列12】从Java线程池的常用4种写法深入分析线程池(Thread Pool)的实现原理

爱好编程进阶

Java 面试 后端开发

三面头条+四面阿里+五面腾讯拿offer分享面经总结,java最新多线程面试题及答案

爱好编程进阶

Java 面试 后端开发

一键智能Mock,你值得拥有

Liam

前端 前端开发 Postman swagger web前端开发

Docker编排利器DockerCompose,java面试题大汇总

爱好编程进阶

Java 面试 后端开发

Github上都在疯找的阿里内部“全栈技能修炼”终于来了,中级java工程师面试题

爱好编程进阶

Java 面试 后端开发

HTTP 中 ServletContext 对象,java软件工程师面试话术

爱好编程进阶

Java 面试 后端开发

mybatis-plus如何自动填充字段创建时间和修改时间,10天拿到阿里Java岗offer

爱好编程进阶

Java 面试 后端开发

银杏谷创始人陈向明博士谈云原生的投资策略与思考 | 云原生加速器观点

阿里巴巴云原生

SpringBoot+JWT+Shiro,linux高级编程面试题

爱好编程进阶

Java 面试 后端开发

【Java 基础语法】纯 Java,springmvc面试题常问2022

爱好编程进阶

Java 面试 后端开发

90天吃透阿里P8推荐的625页Java编程兵书技术实战,直接入职阿里定级P6

爱好编程进阶

Java 面试 后端开发

建议收藏!总结了42种前端常用布局方案

云智慧AIOps社区

CSS html 前端 大前端 HTML5, CSS3

eclipse配置SVN和Maven插件,原生Java开发的路该怎么走

爱好编程进阶

Java 面试 后端开发

Java 定时任务技术趋势

阿里巴巴云原生

百度程序员开发避坑指南(Go语言篇)

百度Geek说

后端

关于 MySQL 数据库学习的书籍有哪些值得推荐?

程序员万金游

MySQL 数据库 java 日志 MySQL 数据库 java

FastDFS入门,Java编程笔试题及答案

爱好编程进阶

Java 面试 后端开发

一天下载量突破9000000!限时分享:阿里Java架构师成长笔记

爱好编程进阶

Java 面试 后端开发

阿里云强力贡献:如何让 StarRocks 做到极速数据湖分析

StarRocks

数据库 大数据 StarRocks

拒绝背锅!39岁失业后,我写出了一个超一万亿使用量的数据库_数据库_核子可乐_InfoQ精选文章