当今的世界是一个互联的世界,绝大多数的计算机和人都在通过网络和他人传递信息、沟通互联。我们在网络上学习、游戏、工作,我们提供各种各样的网络服务,又有很多人使用着各种各样的网络服务。网络改变了世界,而程序员“定义”了网络。我们在代码中实现了网络的通信,让一切变得可能。
那么,这是怎么做到的?要回答这个问题,我们必须简单介绍下TCP/IP协议,当今互联网的基石。
TCP/IP协议
是Transmission Control Protocol/Internet Protocol
的简写,即传输控制协议/因特网互联协议,又名网络通讯协议,是Internet最基本的协议、Internet国际互联网络的基础,由网络层的IP协议和传输层的TCP协议组成。TCP/IP 定义了电子设备如何连入因特网,以及数据如何在它们之间传输的标准。协议采用了4层的层级结构,每一层都呼叫它的下一层所提供的协议来完成自己的需求。
然而,TCP/IP协议并不是国际官方组织制定的标准,而是民间组织(一些大型国际厂商、高等院校)自行商定的标准,因为更简便,推广力度更大,而成为了事实上的标准。
那么,国际官方组织制定的标准是什么呢?是OSI七层网络模型!该模型从最顶层的应用层到最底层的物理层,一共有7层,可以通过首字进行简单记忆,也就是“应、表、会、传、网、数、物”。
应用层
表示层
会话层
传输层
网络层
数据链路层
物理层
OSI七层网络模型虽然没能成为真正的应用标准,但在网络教学上,对于理解网络协议还是很有帮助的。这七层的作用分别是:
物理层:电缆、光纤、无线等真实的物理介质,整个虚拟网络的真实载体。其内部通过高低电平表示1和0,表现形式为“电压不稳”忽高忽低的电流。通过这种形式,类似101011001001的二进制串就被发送出去,再被其他节点接收。
数据链路层:是直接将类似zip、tar这种压缩包通过物理介质传输过去吗?那么这和搞笑图片中对方扔给你一个榴莲没什么区别。我们只能发送类似101011001001这样的数串。这就需要对原始数据进行编码和解码,必须有一个统一的“编码字典”,也就是编码方式来定义其中的含义。那么由谁来做这个工作呢?网卡!现代网络规定,每台计算机都必须有一块网卡(或虚拟网卡),通过它才能连接网络。同时,每块网卡都必须有一个出厂设置世界唯一的MAC地址,也就是这块网卡的“身份证号”。
网络层:101011001001我们有了,编码方式我们有了,接下来该把数据往哪发呢?世界这么大,如何找到正确的地点?通过MAC地址,确定了每台主机的唯一位置,但我们并不知道如何到达那个位置,也就是不知道去那里的“路”。网络层就是为了解决路的问题。IP协议是网络层事实上的标准协议,它以类似111.111.111.111
的方式,将全世界所有的因特网内的主机连在一起,并分别设定IP地址,通过路由的方式,数据包就能知道发往目的地址的正确路径。但这里还有个问题,那就是目标主机内可能同时运行了很多在进行网络通信的程序,那么如何找到正确的对应程序呢?通过端口port!一个IP地址+端口能够唯一确定一个服务程序。
传输层:通过上面三层的努力工作,数据已经送到目标手中,貌似一切ok了?但是目标服务却说“你这数据不合规范不是我想要的”,或者说“哎呀,我还没准备好,你怎么就来了呢?”计算机不是人,没有那么高的智商(至少目前没有),它有它自己规定好的业务逻辑,你必须在正确的时候正确的地点将正确的数据送给它,它才会正确的使用数据!传输层就是负责在两者之间进行传输逻辑控制的协议。典型的代表就是TCP协议的三次握手连接和四次挥手断开逻辑。
应用层、表示层、会话层:通过前面几层的工作,基本都ok了,只剩下数据的利用了。这三层都与应用、具体程序、交互界面等相关,对于用户,其实就是类似QQ、浏览器、迅雷之类的东西,运行的是类似FTP/HTTP/SMTP等应用协议。
网络的发展史是一部”混乱“向”秩序“发展的历史,是一部妥协与斗争的历史,是一部“民间”战胜“政府“的历史,在技术上也有一定的突破(本节内容不会深入讨论网络技术细节,也不会细究某些内容是否依然准确的问题,有兴趣的可以看看专门的网络文献)。国际标准组织推出的OSI七层网络模型,看起来"高富帅",实则分得太细,比较复杂,有点冗余。而TCP/IP网络模型作为“民间人士”,只设置了四层网络,较为简单和实用,因此被各大国际厂商推广,成为行业事实标准,OSI七层网络模型则被用作学校进行网络基础教育的示范和典型。TCP/IP网络模型四层模型从根本上和OSI七层网络模型是一样的,只是合并了几层,具体如下:
在TCP/IP协议中,其各层之间的通信机制,大致如下图所示:
那么回到Python上来,对于我们程序员来说,在Python进程内实现网络通信,不要从“原始社会”一点点的做起!
应用层是我们的核心业务,没得说全是你的事。那么,网络通信呢?我们有TCP/IP协议,可以拿来用。但是,将Python代码和TCP/IP网络协议连接起来,需要你具备大量、扎实和高水平的网络相关知识,需要你编写大量的网络协议实现相关代码,这些工作对于大多数人来说,不但是困难的,也是耗时费力,还不一定做得好的。这也不符合现代编程理念,因为网络通信是一个非常通用,应用非常广泛的场景,底层内容大家都是一样的,完全可以封装成一个通用的模块,提供调用接口,方便大家使用。socket做的就是这件事!
socket又称“套接字”,应用程序通常通过“套接字”向网络发出请求或者应答网络请求,使主机间或者一台计算机上的进程间可以通讯。白话说,socket就是两个节点为了互相通信,而在各自家里装的一部‘电话’。加入socket后,网络关系如下图所示:
我们的应用程序,不再需要苦逼的去和TCP/IP协议通信了,而是通过socket这个“代理”帮我们完成通信工作,我们只需要简单地向socket发布“命令”,不用考虑底层的网络通信问题。
需要强调的是,socket是一个通用的技术,并不是python专属的,在各个领域都被广泛使用,尤其是Linux中。
为了支持socket网络编程,Python 提供了两个级别访问网络的服务:
低级别的网络服务支持基本的socket
模块,它提供了标准的BSD Sockets API
,可以访问底层操作系统socket接口的全部方法。
高级别的网络服务模块socketserver
,它提供了服务器中心类,可以简化网络服务器的开发。
请继续关注我
记得点赞加关注哦,记得加鸡腿啊