1999,socket 第一次连到生产系统
原创 · 约 18 分钟阅读 · 阅读 --

1999,socket 第一次连到生产系统

作者: 字与码


古董级程序员,大厂出来后一直在创业公司,现在仍活跃在一线做 AI 相关开发。更完整的更新写在微信公众号「字与码」:工作经历、对新技术的想法,以及这些年折腾工具、模型和工程系统的记录,会不定期发在那里。

1998 年,我写的是 MIS,是表单、字段、数据库和报表。

到了 1999 年,表单开始连上更硬的东西。

那一年,我给银行做开发,使用 SCO UNIX 做前置机,真正在生产环境里使用 socket 编程。现在看这句话很平常,甚至有点老派。可是对当时的我来说,这是软件责任感发生变化的一年。

以前写程序,更多是在自己的机器、部门内部系统或者相对可控的环境里打转。错了可以改,慢了可以调,重启一下也未必是什么大事。银行系统不一样。它连着交易,连着柜台,连着用户的钱,也连着一套不能随便停、不能随便错、不能只靠“应该没问题”上线的生产秩序。

socket 也不再只是书上的 API。

它变成了一条真实的线。

线的这一头,是你写的程序;线的另一头,是一个更大的系统。

前置机这个词,带着年代感

“前置机”这个词,现在听起来有些古老。

但在 1990 年代末和 2000 年代初,它是很多行业系统里非常关键的一层。银行、证券、电信、税务、社保,各种核心系统都不会让外围业务系统随便直连。中间通常会有一层前置系统,负责协议转换、连接管理、报文收发、日志记录、权限隔离、异常处理。

它像一个门房,也像一个翻译。

柜台系统或者业务系统发来请求,前置机按约定格式组包,通过 socket 发到后端主机或者核心系统。返回结果再被解析、转换、记录,然后交回前端。今天我们会用 API Gateway、消息队列、服务网格、负载均衡、观测平台讲类似事情;当时的很多系统,则是更直接的 UNIX 进程、TCP 连接、固定格式报文和日志文件。

前置机的价值在于,它站在不稳定的边界上。

外部系统可能慢,网络可能断,核心系统可能返回错误,报文可能不合法,柜台人员可能重复操作。前置机不能只做“转发”。它要知道什么时候等待,什么时候超时,什么时候重试,什么时候拒绝,什么时候把问题写进日志,什么时候必须人工介入。

这些东西在教科书里不难理解。

到了生产系统里,每一个选择都变得具体。

超时时间设短了,正常交易可能失败;设长了,前端用户会一直等。日志太少,出问题查不到;日志太多,磁盘和性能又会受影响。错误码设计不清楚,业务人员看不懂;错误处理太随意,问题会被吞掉。

这就是生产系统给程序员上的第一课:代码不是只要能跑,还要能解释、能追溯、能承受现实。

SCO UNIX 上的真实感

我当时用的是 SCO UNIX。

今天很多人提到 UNIX,想到的是 macOS 的终端、Linux 服务器、云主机、容器。SCO UNIX 则属于另一个时代。它常常出现在行业系统、小型服务器、专用设备和比较传统的业务环境里。界面不花哨,命令也不亲切,但稳定、直接,带着一种“这里是生产环境”的气味。

这种环境会让人变谨慎。

你不会轻易动一台机器上的东西。目录结构、启动脚本、日志位置、配置文件、运行用户、端口占用,每一项都要看清楚。调试也不像今天这么舒服。没有完善的可观测性平台,没有现代 IDE 远程调试,没有容器随便起一套环境。很多时候就是终端、日志、命令、经验,以及对系统行为的判断。

这对程序员是很好的训练。

因为它会逼你尊重环境。

在自己的开发机上,程序员容易觉得世界围着代码转。到了生产 UNIX 机器上,代码只是系统里的一个进程。它要和其他进程共享资源,要遵守运维规则,要留下日志,要处理信号,要能被启动、停止、重启,要在异常时尽量不给别人添更大的麻烦。

这和 1998 年写 MIS 很不同。

MIS 让我理解了业务数据和用户流程。银行前置机让我理解了生产链路和系统边界。

socket 不是连接成功就完了

刚学 socket 的时候,最容易兴奋的是连接成功。

创建 socket,connect,send,recv。服务端 accept,读数据,写数据。两边一通信,好像事情就完成了。

真正写到生产里,才知道连接成功只是开始。

连接会断。对方会慢。报文会半包。一次 recv 不代表拿到完整消息。网络上没有“我以为应该一次收完”这种事。你要定义报文边界,要处理长度,要处理编码,要处理超时,要处理对方突然关闭连接,要处理本方进程重启后状态如何恢复。

1999 年银行前置机与 socket 链路示意图

银行前置机、柜台终端和核心系统之间的 socket 请求响应链路。图为按年代氛围生成的示意图。

还有更麻烦的:业务语义。

技术上发出去了,不等于业务成功。收到响应,也不等于可以放心。连接超时以后,这笔交易到底有没有到达对端?对端有没有处理?如果用户重试,会不会重复扣款?如果日志里只有一半信息,事后怎么对账?

这些问题会把 socket 编程从“网络 API”变成“业务协议”。

很多年后,互联网系统里会反复讨论幂等、重试、超时、分布式事务、最终一致性、链路追踪。其实金融系统更早就逼着程序员面对这些问题,只不过那时术语没有今天这么流行,工具也远没有今天这么完整。

当年写前置机,最能改变人的一点,是你开始把失败当成常态。

不是“如果失败怎么办”,而是“一定会失败,失败时系统应该怎样表现”。

这就是工程和写小程序最大的区别。

日志是生产系统的记忆

在生产系统里,日志不是调试时临时加几行输出。

日志是系统的记忆。

一笔请求什么时候进来,来自哪里,报文摘要是什么,发往哪里,对方什么时候响应,结果码是什么,耗时多少,失败原因是什么,是否重试过,最终状态是什么。这些信息在正常时候看起来啰嗦,在出问题时就是救命线索。

但日志也不能乱写。

日志太粗,查不到问题;日志太细,性能受影响,也可能让关键信息淹没在大量噪声里。日志格式不统一,事后分析困难;时间戳不准,不同机器之间就对不上。关键字段没记录,查到最后只能靠猜。

1999 年那种环境里,日志通常更朴素。

文本文件,按天滚动,必要时用命令行查。grep、tail、awk、sed 这些工具,很多程序员都是在生产问题里真正学会的。不是为了炫技,而是因为你必须在一堆文件里尽快找到那笔交易发生了什么。

后来做互联网系统,日志平台变得越来越强,链路追踪、指标、告警、可观测性都出来了。但本质没有变:系统必须留下足够的证据,证明自己做过什么。

没有证据的系统,是不适合上生产的。

公司内部的 Perl 论坛

1999 年前后,我还在公司内部用 Perl 做过一个论坛。

这件事和银行前置机相比,轻得多。

一个是生产交易系统,一个是公司内部交流工具;一个要严肃面对连接、协议和责任,一个更像程序员自己给自己做的小工具。但放在一起看,它们恰好代表了那几年软件的两个方向。

一边是行业信息化。银行、电信、企业、政府、学校,各种业务要进入系统,变成数据和流程。

另一边是 Web 和社区。论坛、留言板、个人主页、邮件列表、聊天室,这些东西让人第一次感到:软件不只是处理业务,也能组织人和人的交流。

Perl 在当时很有代表性。

它不像 C 那样靠近系统底层,也不像 Delphi 那样适合做 Windows 窗口应用。Perl 更像胶水。处理文本、生成页面、操作文件、写 CGI、拼接各种小工具,它很灵活,也很有脚本语言的味道。

公司内部论坛也许算不上什么大项目,但它让我意识到另一件事:软件的价值不一定来自复杂度,有时候来自它刚好放在一个需要交流的地方。

大家愿意用,它就活了。

1999 年的空气

1999 年还有一种特殊的时代空气:千年虫。

Y2K 问题今天听起来像一个历史笑话,但当年不是。很多系统用两位数表示年份,到了 2000 年可能把 00 误解成 1900 年。金融、电力、交通、政府、企业系统都需要检查。它让全世界第一次如此集中地意识到:软件里的一个字段设计,几十年后可能变成社会问题。

对程序员来说,这是非常有教育意义的一课。

技术债不是抽象概念。某个为了省空间、为了省事、为了符合当年习惯做出的设计,可能在很久以后以极高成本回来找你。

1999 年的软件行业,既有这种紧张,也有新的兴奋。

Linux 2.2 发布,GNOME 1.0 发布,开源桌面和服务器世界都在继续成长。Napster 出现,点对点共享把互联网版权和分发问题推到公众面前。Salesforce 成立,SaaS 的种子开始发芽。Alibaba 成立,中国互联网商业也开始进入新的阶段。QQ 的前身 OICQ 推出,即时通讯会慢慢变成中国互联网日常生活的一部分。

这些大事和我当时写的前置机,看起来不在同一个世界。

但它们共同说明,软件正在进入更多现实场景。

进入银行,进入企业,进入个人通信,进入音乐分发,进入商业交易,进入服务器,进入桌面,进入每一个需要连接的地方。

从表单到链路

1998 年,我理解了表单背后是组织。

1999 年,我理解了连接背后是责任。

这两个理解,对后来影响很大。表单让你看到业务规则,连接让你看到系统边界。前者告诉你数据怎么进入系统,后者告诉你系统如何和另一个系统发生关系。

很多年后,互联网后端工程看起来技术栈完全不同:HTTP、RPC、消息队列、缓存、数据库、微服务、容器、Kubernetes、可观测性。可是核心问题并没有变。

请求从哪里来?

发到哪里去?

超时怎么办?

失败能不能重试?

重复请求会不会出错?

日志能不能查清楚?

上下游系统的责任怎么划分?

这些问题,1999 年的 socket 已经问过一遍。

那时没有今天这么多漂亮的概念,但生产系统从来不缺真实问题。

下一年,去北京

1999 年之后,就是 2000 年。

我来到北京。CSDN 没能给到满意的薪资,最后去了外企。互联网泡沫已经吹到很高,也很快会破。一个来自新浪的小编说,拿到的补偿能铺满一床。那是另一个时代的气味:门户网站、创业公司、外企办公室、纳斯达克、期权、裁员和“互联网到底是不是泡沫”的争论。

1999 年的我还在生产系统里写 socket。

2000 年,网还在继续往前冲,人也跟着城市和行业一起换了地方。

下一篇,就写泡沫破了,网还在。

1999 年 IT 大事记

  • 千年虫进入最后倒计时。 1999 年,全世界大量系统都在为 Y2K 做最后检查和修复。它让软件行业集体意识到:日期、字段长度、历史兼容性这些看似细小的设计,可能在多年以后成为系统性风险。
  • Linux 2.2 发布。 Linux kernel 2.2 在 1999 年发布,增强了网络、SMP 等能力。Linux 正在从爱好者系统和服务器选择,逐步进入更严肃的生产场景,也为后来的互联网基础设施和云计算铺路。
  • GNOME 1.0 发布。 GNOME 1.0 在 1999 年发布。开源世界不只是在服务器上竞争,也在尝试提供更完整的桌面体验。它和 KDE 等项目一起,构成了后来 Linux 桌面生态的重要部分。
  • Napster 出现。 Napster 在 1999 年上线,把 P2P 文件共享推到大众面前。它改变了音乐分发,也引发了版权、平台和数字内容商业模式的大讨论。互联网不再只是网页,也开始冲击传统内容行业。
  • Salesforce 成立。 Salesforce 在 1999 年成立,后来成为 SaaS 的代表公司之一。它把企业软件从本地安装、项目交付,逐步推向按订阅使用的云服务模式。
  • Alibaba 成立。 Alibaba 在 1999 年成立。它后来深刻影响中国电子商务、支付、云计算和中小企业数字化。站在当时看,它还只是互联网创业潮中的一家公司。
  • OICQ 推出,后来成为 QQ。 1999 年,腾讯推出 OICQ,后来改名 QQ。即时通讯由此成为中国互联网最重要的入口之一,也改变了很多人的在线社交习惯。
  • VMware Workstation 早期产品发布。 VMware 在 1999 年发布早期虚拟化产品。虚拟化技术会在后来的开发测试、服务器整合、云计算和本地实验环境中产生深远影响。

参考资料

微信公众号

欢迎关注「字与码」

如果这篇文章对你有用,也欢迎在微信里继续关注后续更新。

微信公众号字与码二维码