第0x00天
上帝看到了人类制造的各种规格的电脑设备,也组建了一些规模极小的、各种各样的网络,却没有办法把它们连接起来使用,很是伤心。
晚上,上帝就给温顿·瑟夫托梦,告诉他怎么样在一个不可靠的网络环境下可靠地传输数据,又托梦给鲍勃·卡恩,告诉他如何给每个主机分配一个“门牌号”, 如何兼容底层协议多样的网络......
第二天,温顿·瑟夫和鲍勃·卡恩见面以后,交流了一下晚上所做的奇怪的梦,觉得这些天一直思考的问题迎刃而解,不仅大声叫道:感谢上帝!
于是,TCP/IP诞生了。
有了TCP/IP的支持,大家可以跨越各个子网互相发送邮件(SMTP),可以从远程的机器上下载文件(FTP),还可以登陆到远程的机器上去操作(Telnet), 人类非常高兴。
第0x01天
上帝看到人类很容易满足,有点失望,直到他注意到一个叫做蒂姆·伯纳斯·李的小伙子。这个小伙子孜孜不倦地在追求一件事情: 把每个电脑中的文档给连接起来。
晚上,上帝决定故伎重演,在梦里告诉了蒂姆·伯纳斯·李“超文本”的秘密, 并且特别嘱咐他要买一台NeXT计算机作为服务器,因为上帝挺可怜那个被赶出苹果公司的家伙: Steve Jobs。
蒂姆·伯纳斯·李醒来后十分激动,都忘了说“感谢上帝!”,马上就投入了HTTP协议的制定当中。他果然买了一台NeXT计算机,还在上面贴了一张纸: 别关机,这是一台服务器!
服务器可是一个新鲜玩意儿,当时的计算机,性能非常低下,很难维持成千上万个来自浏览器的连接。
更重要的是,人类用浏览器访问服务器,仅仅为了把服务器的静态文件给下载到本地阅读,于是蒂姆·伯纳斯·李把HTTP设计成了无状态的协议! 这严重违背了上帝的教导。
每次浏览器访问服务器上的网页,都会建立一个TCP连接,等到数据传输完成,立刻就关闭连接。每次请求之间毫无关联。
上帝有点儿生气,想再给蒂姆·伯纳斯·李托梦,但转念一想: 费那劲儿干嘛,让人类自己醒悟吧!
第0x02天
HTTP迅速普及,在Mosaic,网景等浏览器的推波助澜下,人们纷纷上网。
如上帝所料, Web越来越繁荣,各种各样的网站雨后春笋般出现,交互性越来越强,动态性越来越高,那些单纯的,以浏览静态网页为目的的网站已经极少了。
人类中的程序员发现,蒂姆·伯纳斯·李发明的HTTP协议实在是笨拙:每次请求,都得打开一个连接,用完就关,下一个请求,又得开新的连接,在需要高度交互的系统(如聊天、游戏)中浪费至极。
这一次,上帝找不到托梦的人,只好给整个W3C的网络专家组托梦: 要节约,别浪费,要在一个TCP连接中发送多个HTTP请求!
这就是keep-alive。
程序员们高兴了几天后,很快又发现,即使是keep-alive, 每次HTTP请求都得发送HTTP Header,还是浪费。
更要命的是蒂姆·伯纳斯·李设计的HTTP协议都是由浏览器发起请求,服务器来响应。 现在服务器的数据有了变化,想主动告诉浏览器,该怎么办?
有的程序员想出了不断轮询的办法,让浏览器不断去问服务器,数据有变化没有? 数据有变化没有?
上帝看到这种情景,不由得笑了:可怜的人类,不听老人言,吃亏在眼前吧!
第0x03天
上帝给Sun公司的Games Gosling托梦, 让他创建了Java。
Games Gosling 为了推广Java, 想出了一个不错的点子, 在浏览器中安装了一个插件, 通过插件可以运行Java程序。既然是Java程序, 就可以直接和服务器建立Socket连接,在这个连接中,自然是想做什么事情就做什么事情,服务器也可以主动给浏览器发送数据,效率极高, 完全抛弃了HTTP协议。
这就是Applet。
但是Applet实在是不争气, 再加上各个浏览器也不断使坏, 就成会出现这种情况:
或者干脆是这种情况:
第0x04天
上帝惊奇地发现了Macromedia这个公司,它独辟蹊径,创造了一个叫做Flash的东西, 非常适合做小动画。
(小小作品:火柴人打斗)
虽然也和Applet一样需要在浏览器安装一个插件,但是各大“流氓”浏览器居然都支持。
有了插件的支持,浏览器的所有限制都不复存在, Flash也可以直接和后端的服务器用Socket进行双向通信。
可惜的是这Flash寿命不长久,尤其是和上帝钟爱的Jobs干了一架以后,慢慢地走上了不归路。
后来,连Jobs也被上帝带走了。
第0x05天
让上帝没有料到的是,随着Applet和Flash的消亡,JavaScript慢慢地发展成了前端之王,统治了浏览器。
但是由于HTTP协议的限制,服务器还是无法直接给浏览器推送数据。
人类的不满情绪慢慢累积:“这HTTP用起来这么麻烦, 能不能让我们JavaScript直接创建Socket去访问服务器啊,这样的话HTTP的一切问题都解决了!”
上帝心中暗喜,人类终于上道了, 但是上帝也清楚,在浏览器中直接使用JavaScript去创建Socket和服务器双向通信是一件吃力不讨好的事情, 比如:
1. Socket是个非常"低级"的通信方式,是基于Stream的,不是基于消息的。每个应用的通信双方必须自定义数据格式,处理粘包、分包的问题。
2. 如果想实现安全的通信,程序员必须自己来实现类似与Https的那一套机制,对称加密,非对称加密,消息摘要,数字证书 ......
于是上帝再次托梦,这一次他找到了Michael Carter,告诉他:“汝要带领大家,基于TCP协议,在应用层实现一套新的协议,要像Socket那样, 让浏览器和服务器可以双向通信;还要像HTTP那样让程序员容易使用,别在让程序员去处理那些低级的、麻烦的粘包问题/安全问题。”
Michael Carter 醒来后非常激动,他决定把新的协议叫做: web socket !
第0x06天
上帝托梦太多,他决定休息一下,人类也休息了一天。
这就是星期天的来历。
往期精彩回顾
我是一个线程
我是一个Java Class
面向对象圣经
函数式编程圣经
TCP/IP之大明邮差
CPU阿甘
我是一个网卡
我是一个路由器
一个故事讲完HTTPs
编程语言的巅峰Java:一个帝国的诞生
JavaScript:一个屌丝的逆袭