python面试题三:Python 网络编程与并发

1 简述 OSI 七层协议。

OSI七层协议模型主要是:

应用层(Application):为用户的应用程序(例如电子邮件、文件传输和终端仿真)提供网络服务。

表示层(Presentation):使用一种通格式来实现多种数据格式之间的转换。

会话层(Session):通过运输层(端口号:传输端口与接收端口)建立数据传输的通路。主要在你的系统之间发起会话或者接受会话请求(设备之间需要互相认识可以是IP也可以是MAC或者是主机名)

传输层(Transport):定义了一些传输数据的协议和端口号(WWW端口80等).TCP,UDP

网络层(Network):在位于不同地理位置的网络中的两个主机系统之间提供连接和路径选择。Internet的发展使得从世界各站点访问信息的用户数大大增加,而网络层正是管理这种连接的层。

数据链路层(Data Link):定义了如何让格式化数据以进行传输,以及如何让控制对物理介质的访问。这一层通常还提供错误检测和纠正,以确保数据的可靠传输。

物理层(Physical):主要定义物理设备标准,如网线的接口类型、光纤的接口类型、各种传输介质的传输速率等。它的主要作用是传输比特流(就是由1、0转化为电流强弱来进行传输,到达目的地后在转化为1、0,也就是我们常说的数模转换与模数转换)

 

 

2 什么是C/S和B/S架构?

区别:

1、B/S架构是针对C/S架构缺点进行改进后提出的网络结构模式。 B/S结构属于C/S结构,是一种特殊的C/S,因为浏览器只是特殊的客户端。

2、C/S可以使用任何通信协议,而B/S架构规定必须实现HTTP协议。

b/s结构:

1、维护和升级简单,我们只要对服务器端进行维护和升级即可,不需要对成千上万的客服端进行维护和升级,减少了人力资源成本。

2、随时随地都可以访问,只要有一台连接互联网和安装了浏览器的计算机就可以访问。

3、减轻了客户端电脑载荷,客户端电脑只要运行少部分程序就能实现。因此对客服端电脑要求不高,对服务器端负荷较重,由于主要的功能都集中到了服务器端,因此对服务器要求高,但总体而言,还是大大降低了成本。

c/s结构:

1、充分发挥客户端PC的处理能力,很多数据可以通过客户端的处理后再发给服务器,降低了服务器的负荷,提高了速度。但维护和升级比较复杂,维护和升级是针对成千上万的客户机的。

2、必须安装专用的客户端软件。客户端是成千上万的,要安装专用软件,是多么大的工作量,如果一台客户机出现了问题,如:感染病毒、计算机故障等等原因,都需要进行安装或维护。系统软件需要升级的时候,每一台客户机都需要重新安装系统软件,维护和升级成本相当的高。

3、对客户机的操作系统有限制,对一些操作系统和新开发的操作系统不兼容。目前产品更新换代十分的快,要针对不同的操作系统系统版本开发不同的客户机软件,对成本而言是相当大。

总结:B/S对C/S而言,B/S具有的优势。

1、分布性:可以随时随地进行查询和浏览等业务;

2、功能业务扩展比较方便:增加服务器的功能,就能增加浏览器端的功能;

3、维护简单方便:改变服务器端数据即可以实现所有用户同步更新;

4、开发简单,共享性强,成本低,数据可以持久存储在服务器端而不必担心数据的丢失。

3 简述 三次握手、四次挥手的流程。

    序列号seq:占4个字节,用来标记数据段的顺序,TCP把连接中发送的所有数据字节都编上一个序号,第一个字节的编号由本地随机产生;给字节编上序号后,就给每一个报文段指派一个序号;序列号seq就是这个报文段中的第一个字节的数据编号。

    确认号ack:占4个字节,期待收到对方下一个报文段的第一个数据字节的序号;序列号表示报文段携带数据的第一个字节的编号;而确认号指的是期望接收到下一个字节的编号;因此当前报文段最后一个字节的编号+1即为确认号。

    确认ACK:占1位,仅当ACK=1时,确认号字段才有效。ACK=0时,确认号无效

    同步SYN:连接建立时用于同步序号。当SYN=1,ACK=0时表示:这是一个连接请求报文段。若同意连接,则在响应报文段中使得SYN=1,ACK=1。因此,SYN=1表示这是一个连接请求,或连接接受报文。SYN这个标志位只有在TCP建产连接时才会被置1,握手完成后SYN标志位被置0。

    终止FIN:用来释放一个连接。FIN=1表示:此报文段的发送方的数据已经发送完毕,并要求释放运输连接

    PS:ACK、SYN和FIN这些大写的单词表示标志位,其值要么是1,要么是0;ack、seq小写的单词表示序号。

 


三次握手过程理解

第一次握手:建立连接时,客户端发送syn包(syn=j)到服务器,并进入SYN_SENT状态,等待服务器确认;SYN:同步序列编号(Synchronize Sequence Numbers)。

第二次握手:服务器收到syn包,必须确认客户的SYN(ack=j+1),同时自己也发送一个SYN包(syn=k),即SYN+ACK包,此时服务器进入SYN_RECV状态;

第三次握手:客户端收到服务器的SYN+ACK包,向服务器发送确认包ACK(ack=k+1),此包发送完毕,客户端和服务器进入ESTABLISHED(TCP连接成功)状态,完成三次握手。

四次挥手过程理解 


1)客户端进程发出连接释放报文,并且停止发送数据。释放数据报文首部,FIN=1,其序列号为seq=u(等于前面已经传送过来的数据的最后一个字节的序号加1),此时,客户端进入FIN-WAIT-1(终止等待1)状态。 TCP规定,FIN报文段即使不携带数据,也要消耗一个序号。
2)服务器收到连接释放报文,发出确认报文,ACK=1,ack=u+1,并且带上自己的序列号seq=v,此时,服务端就进入了CLOSE-WAIT(关闭等待)状态。TCP服务器通知高层的应用进程,客户端向服务器的方向就释放了,这时候处于半关闭状态,即客户端已经没有数据要发送了,但是服务器若发送数据,客户端依然要接受。这个状态还要持续一段时间,也就是整个CLOSE-WAIT状态持续的时间。
3)客户端收到服务器的确认请求后,此时,客户端就进入FIN-WAIT-2(终止等待2)状态,等待服务器发送连接释放报文(在这之前还需要接受服务器发送的最后的数据)。
4)服务器将最后的数据发送完毕后,就向客户端发送连接释放报文,FIN=1,ack=u+1,由于在半关闭状态,服务器很可能又发送了一些数据,假定此时的序列号为seq=w,此时,服务器就进入了LAST-ACK(最后确认)状态,等待客户端的确认。
5)客户端收到服务器的连接释放报文后,必须发出确认,ACK=1,ack=w+1,而自己的序列号是seq=u+1,此时,客户端就进入了TIME-WAIT(时间等待)状态。注意此时TCP连接还没有释放,必须经过2∗∗MSL(最长报文段寿命)的时间后,当客户端撤销相应的TCB后,才进入CLOSED状态。
6)服务器只要收到了客户端发出的确认,立即进入CLOSED状态。同样,撤销TCB后,就结束了这次的TCP连接。可以看到,服务器结束TCP连接的时间要比客户端早一些。

 常见面试题
【问题1】为什么连接的时候是三次握手,关闭的时候却是四次握手?

答:因为当Server端收到Client端的SYN连接请求报文后,可以直接发送SYN+ACK报文。其中ACK报文是用来应答的,SYN报文是用来同步的。但是关闭连接时,当Server端收到FIN报文时,很可能并不会立即关闭SOCKET,所以只能先回复一个ACK报文,告诉Client端,"你发的FIN报文我收到了"。只有等到我Server端所有的报文都发送完了,我才能发送FIN报文,因此不能一起发送。故需要四步握手。

【问题2】为什么TIME_WAIT状态需要经过2MSL(最大报文段生存时间)才能返回到CLOSE状态?

答:虽然按道理,四个报文都发送完毕,我们可以直接进入CLOSE状态了,但是我们必须假象网络是不可靠的,有可以最后一个ACK丢失。所以TIME_WAIT状态就是用来重发可能丢失的ACK报文。在Client发送出最后的ACK回复,但该ACK可能丢失。Server如果没有收到ACK,将不断重复发送FIN片段。所以Client不能立即关闭,它必须确认Server接收到了该ACK。Client会在发送出ACK之后进入到TIME_WAIT状态。Client会设置一个计时器,等待2MSL的时间。如果在该时间内再次收到FIN,那么Client会重发ACK并再次等待2MSL。所谓的2MSL是两倍的MSL(Maximum Segment Lifetime)。MSL指一个片段在网络中最大的存活时间,2MSL就是一个发送和一个回复所需的最大时间。如果直到2MSL,Client都没有再次收到FIN,那么Client推断ACK已经被成功接收,则结束TCP连接。

【问题3】为什么不能用两次握手进行连接?

答:3次握手完成两个重要的功能,既要双方做好发送数据的准备工作(双方都知道彼此已准备好),也要允许双方就初始序列号进行协商,这个序列号在握手过程中被发送和确认。

       现在把三次握手改成仅需要两次握手,死锁是可能发生的。作为例子,考虑计算机S和C之间的通信,假定C给S发送一个连接请求分组,S收到了这个分组,并发 送了确认应答分组。按照两次握手的协定,S认为连接已经成功地建立了,可以开始发送数据分组。可是,C在S的应答分组在传输中被丢失的情况下,将不知道S 是否已准备好,不知道S建立什么样的序列号,C甚至怀疑S是否收到自己的连接请求分组。在这种情况下,C认为连接还未建立成功,将忽略S发来的任何数据分 组,只等待连接确认应答分组。而S在发出的分组超时后,重复发送同样的分组。这样就形成了死锁。

【问题4】如果已经建立了连接,但是客户端突然出现故障了怎么办?

TCP还设有一个保活计时器,显然,客户端如果出现故障,服务器不能一直等下去,白白浪费资源。服务器每收到一次客户端的请求后都会重新复位这个计时器,时间通常是设置为2小时,若两小时还没有收到客户端的任何数据,服务器就会发送一个探测报文段,以后每隔75秒钟发送一次。若一连发送10个探测报文仍然没反应,服务器就认为客户端出了故障,接着就关闭连接。
---------------------
作者:青柚_
来源:CSDN
原文:https://blog.csdn.net/qq_38950316/article/details/81087809
版权声明:本文为博主原创文章,转载请附上博文链接!

4 什么是arp协议?

地址解析协议(Address Resolution Protocol),其基本功能为透过目标设备的IP地址,查询目标的MAC地址,以保证通信的顺利进行。它是IPv4网络层必不可少的协议,不过在IPv6中已不再适用,并被邻居发现协议(NDP)所替代。

5 TCP和UDP的区别?

 UDPTCP
是否连接 无连接 面向连接
是否可靠 不可靠传输,不使用流量控制和拥塞控制 可靠传输,使用流量控制和拥塞控制
连接对象个数 支持一对一,一对多,多对一和多对多交互通信 只能是一对一通信
传输方式 面向报文 面向字节流
首部开销 首部开销小,仅8字节 首部最小20字节,最大60字节
适用场景 适用于实时应用(IP电话、视频会议、直播等) 适用于要求可靠传输的应用,例如文件传输

 

6 什么是局域网和广域网?

局域网的覆盖范围一般是方圆几千米之内,其具备的安装便捷、成本节约、扩展方便等特点使其在各类办公室内运用广泛。

广域网又称广域网外网、公网。是连接不同地区局域网或城域网计算机通信的远程网。通常跨接很大的物理范围,所覆盖的范围从几十公里到几千公里,它能连接多个地区、城市和国家,或横跨几个洲并能提供远距离通信,形成国际性的远程网络。广域网并不等同于互联网。

7 为何基于tcp协议的通信比基于udp协议的通信更可靠?

tcp协议一定是先建好双向链接,发一个数据包要得到确认才算发送完成,没有收到就一直给你重发;udp协议没有链接存在,udp直接丢数据,不管你有没有收到。

TCP的可靠保证,是它的三次握手双向机制,这一机制保证校验了数据,保证了他的可靠性。

而UDP就没有了,udp信息发出后,不验证是否到达对方,所以不可靠。

 

8 什么是socket?简述基于tcp协议的套接字通信流程。

socket 套接字 ip与端口组成一个套接字

基于tcp 协议的套接字通信流程:

1). 服务器先用 socket 函数来建立一个套接字,用这个套接字完成通信的监听。 
2). 用 bind 函数来绑定一个端口号和 IP 地址。因为本地计算机可能有多个网址和 IP,每一个 IP 和端口有多个端口。需要指定一个 IP 和端口进行监听。 
3). 服务器调用 listen 函数,使服务器的这个端口和 IP 处于监听状态,等待客户机的连接。 
4). 客户机用 socket 函数建立一个套接字,设定远程 IP 和端口。 
5). 客户机调用 connect 函数连接远程计算机指定的端口。 
6). 服务器用 accept 函数来接受远程计算机的连接,建立起与客户机之间的通信。 
7). 建立连接以后,客户机用 write 函数向 socket 中写入数据。也可以用 read 函数读取服务器发送来的数据。 
8). 服务器用 read 函数读取客户机发送来的数据,也可以用 write 函数来发送数据。 
9). 完成通信以后,用 close 函数关闭 socket 连接。

 

 

9 什么是粘包? socket 中造成粘包的原因是什么? 哪些情况会发生粘包现象?

只有TCP有粘包现象,UDP永远不会粘包!

粘包
:在接收数据时,一次性多接收了其它请求发送来的数据(即多包接收)。如,对方第一次发送hello,第二次发送world,
   在接收时,应该收两次,一次是hello,一次是world,但事实上是一次收到helloworld,一次收到空,这种现象叫粘包。 原因 粘包问题主要还是因为接收方不知道消息之间的界限,不知道一次性提取多少字节的数据所造成的。 什么情况会发生
1、发送端需要等缓冲区满才发送出去,造成粘包(发送数据时间间隔很短,数据很小,会合到一起,产生粘包) 2、接收方不及时接收缓冲区的包,造成多个包接收(客户端发送了一段数据,服务端只收了一小部分,服务端下次再收的时候还是从缓冲区拿上次遗留的数据,产生粘包)
解决方案:
一个思路是发送之前,先打个招呼,告诉对方自己要发送的字节长度,这样对方可以根据长度判断什么时候终止接受。

10 IO多路复用的作用?

I/O多路复用是用于提升效率,单个进程可以同时监听多个网络连接IO。

11 什么是防火墙以及作用?

12 select、poll、epoll 模型的区别?

select是通过系统调用来监视一组由多个文件描述符组成的数组,通过调用select()返回结果,数组中就绪的文件描述符会被内核标记出来,然后进程就可以获得这些文件描述符,然后进行相应的读写操作。

每次调用select,都需要把fd集合由用户态拷贝到内核态,在fd多的时候开销会很大,每次select都是线性遍历整个列表,当fd很大的时候,遍历的开销也很大

poll本质上与select基本相同,只不过监控的最大连接数上相较于select没有了限制,因为poll使用的数据结构是链表,而select使用的是数组,数组是要初始化长度大小的,且不能改变

Epoll:解决select和poll本身的缺陷

数组长度限制解决方案:fd上限是最大可以打开文件的数目,具体数目可以查看/proc/sys/fs/file-max。一般会和内存有关

需要每次轮询将数组全部拷贝到内核态解决方案:每次注册事件的时候,会把fd拷贝到内核态,而不是每次poll的时候拷贝,这样就保证每个fd只需要拷贝一次。

每次遍历都需要列表线性遍历解决方案:不再采用遍历的方案,给每个fd指定一个回调函数,fd就绪时,调用回调函数,这个回调函数会把fd加入到就绪的fd列表中,所以epoll只需要遍历就绪的list即可    

13 简述 进程、线程、协程的区别 以及应用场景?

a.进程是资源分配的单位

b.线程是操作系统调度的单位

c.进程切换需要的资源很大,效率很低

d.线程切换需要的资源一般,效率一般

e.协程切换任务资源很小,效率高

f.多进程、多线程根据cpu核数不一样可能是并行的,但是协程是在一个线程中所以是并发的

14 Python中如何使用线程池和进程池?

15 threading.local的作用?

为每个线程创建一个独立的空间,使得线程对自己的空间中的数据进行操作(数据隔离)

16 进程之间如何进行通信?

a.Queue使用方法:
Queue.qsize():返回当前队列包含的消息数量;
Queue.empty():如果队列为空,返回True,反之False ;
Queue.full():如果队列满了,返回True,反之False;
Queue.get():获取队列中的一条消息,然后将其从列队中移除,可传参超时时长。
Queue.get_nowait():相当Queue.get(False),取不到值时触发异常:Empty;
Queue.put():将一个值添加进数列,可传参超时时长。
Queue.put_nowait():相当于Queue.get(False),当队列满了时报错:Full。

#!/usr/bin/env python3
import time
from multiprocessing import Process,Queue

q = Queue()  #创建列队,不传数字表示列队不限数量
for i in range(11):
    q.put(i)
def A():
    while 1:
        try:
            num = q.get_nowait()
            print('我是进程A,取出数字:%d'%num)
            time.sleep(1)
        except :
            break
def B():
    while 1:
        try:
            num = q.get_nowait()
            print('我是进程B,取出数字:%d'%num)
            time.sleep(1)
        except :
            break

p1 = Process(target = A)
p2 = Process(target = B)
p1.start()
p2.start()

使用进程池Pool时,Queue会出错,需要使用Manager.Queue:

#!/usr/bin/env python3
import time
from multiprocessing import Pool,Manager,Queue
q = Manager().Queue()
for i in range(11):
    q.put(i)

def A(i):
    num = q.get_nowait()
    print('我是进程%d,取出数字:%d'%(i,num))
    time.sleep(1)
pool = Pool(3)
for i in range(10):
    pool.apply_async(A,(i,))

pool.close()
pool.join()

17 什么是并发和并行?

并发,是在同一个cpu上同时(不是真正的同时,而是看来是同时,因为cpu要在多个程序间切换)运行多个程序

并行,是每个cpu运行一个程序。

18  进程锁和线程锁的作用?

线程锁:

当有多个线程访问同一对象的加锁方法/代码块时,同一时间只有一个线程在执行,其余线程必须要等待当前线程执行完之后才能执行该代码段。但是,其余线程是可以访问该对象中的非加锁代码块的。

进程锁:

也是为了控制同一操作系统中多个进程访问一个共享资源,

只是因为程序的独立性,各个进程是无法控制其他进程对资源的访问的,

但是可以使用本地系统的信号量控制(操作系统基本知识)。

19 解释什么是异步非阻塞?

异步

当一个异步操作发出后,调用者在没有得到结果之前,可以继续执行后续操作。这就是异步。

非阻塞

在结果没有返回之前,该调用不会阻塞住当前线程。

20 路由器和交换机的区别?

两者都是连接互联网的设备,它们之间主要区别就是,交换机发生在网络的第二层数据链路层,而路由器发生在第三层网络层。这个区别是两者各自工作方式的根本区别。路由器可以根据IP地址寻找下一个设备,可以处理TCPIP协议,而上一篇我们讲过交换机是根据MAC地址寻址的。

交换机是分配网络数据,路由器可以给网络分配IP地址,分配给你地址而且可以随时通过地址过来找到你。

路由器可以在不同时间内把一个IP分配给多台主机使用。交换机是通过MAC地址和识别各个不同的主机。

21 什么是域名解析?

域名解析就是域名到IP地址的转换过程。

22 如何修改本地hosts文件?

23 生产者消费者模型应用场景及优势?
在 工作中,大家可能会碰到这样一种情况:某个模块负责产生数据,这些数据由另一个模块来负责处理(此处的模块是广义的,可以是类、函数、线程、进程等)。

产 生数据的模块,就形象地称为生产者;而处理数据的模块,就称为消费者。

在生产者与消费者之间在加个缓冲区,我们形象的称之为仓库,生产者负责往仓库了进商 品,而消费者负责从仓库里拿商品,这就构成了生产者消费者模型。

结构图如下:

生产者消费者模型的优点:

1、解耦

假设生产者和消费者分别是两个类。

如果让生产者直接调用消费者的某个方法,那么生产者对于消费者就会产生依赖(也就是耦合)。

将来如果消费者的代码发生变化, 可能会影响到生产者。而如果两者都依赖于某个缓冲区,两者之间不直接依赖,耦合也就相应降低了。

举个例子,我们去邮局投递信件,如果不使用邮筒(也就是缓冲区),你必须得把信直接交给邮递员。

有同学会说,直接给邮递员不是挺简单的嘛?其实不简单,你必须 得认识谁是邮递员,才能把信给他(光凭身上穿的制服,万一有人假冒,就惨了)。

这就产生和你和邮递员之间的依赖(相当于生产者和消费者的强耦合)。

万一哪天邮递员换人了,你还要重新认识一下(相当于消费者变化导致修改生产者代码)。

而邮筒相对来说比较固定,你依赖它的成本就比较低(相当于和缓冲区之间的弱耦合)。

 

2、支持并发

由于生产者与消费者是两个独立的并发体,他们之间是用缓冲区作为桥梁连接,生产者只需要往缓冲区里丢数据,

就可以继续生产下一个数据,而消费者只需要从缓冲区了拿数据即可,这样就不会因为彼此的处理速度而发生阻塞。

接上面的例子,如果我们不使用邮筒,我们就得在邮局等邮递员,直到他回来,

我们把信件交给他,这期间我们啥事儿都不能干(也就是生产者阻塞),或者邮递员得挨家挨户问,谁要寄信(相当于消费者轮询)。

 

3、支持忙闲不均

缓冲区还有另一个好处。如果制造数据的速度时快时慢,缓冲区的好处就体现出来了。

当数据制造快的时候,消费者来不及处理,未处理的数据可以暂时存在缓冲区中。 等生产者的制造速度慢下来,消费者再慢慢处理掉。

为了充分复用,我们再拿寄信的例子来说事。假设邮递员一次只能带走1000封信。万一某次碰上情人节(也可能是圣诞节)送贺卡,

需要寄出去的信超过1000封,这时 候邮筒这个缓冲区就派上用场了。邮递员把来不及带走的信暂存在邮筒中,等下次过来 时再拿走。

应用场景:

使用多线程,在做爬虫的时候,生产者用着产生url链接,消费者用于获取url数据,在队列的帮助下可以使用多线程加快爬虫速度。

import time
import threading
import Queue
import urllib2
 
class Consumer(threading.Thread):
  def __init__(self, queue):
    threading.Thread.__init__(self)
    self._queue = queue
 
  def run(self):
    while True:
      content = self._queue.get()
      print content
      if isinstance(content, str) and content == 'quit':
        break
      response = urllib2.urlopen(content)
    print 'Bye byes!'
 
 
def Producer():
  urls = [
    'http://211.103.242.133:8080/Disease/Details.aspx?id=2258',
    'http://211.103.242.133:8080/Disease/Details.aspx?id=2258',
    'http://211.103.242.133:8080/Disease/Details.aspx?id=2258',
    'http://211.103.242.133:8080/Disease/Details.aspx?id=2258'
  ]
  queue = Queue.Queue()
  worker_threads = build_worker_pool(queue, 4)
  start_time = time.time()
  for url in urls:
    queue.put(url)
 
  for worker in worker_threads:
    queue.put('quit')
  for worker in worker_threads:
    worker.join()
 
  print 'Done! Time taken: {}'.format(time.time() - start_time)
 
 
def build_worker_pool(queue, size):
  workers = []
  for _ in range(size):
    worker = Consumer(queue)
    worker.start()
    workers.append(worker)
  return workers
 
if __name__ == '__main__':
  Producer()

 

24 什么是cdn?

CDN的全称是Content Delivery Network,即内容分发网络。CDN是构建在网络之上的内容分发网络,依靠部署在各地的边缘服务器,通过中心平台的负载均衡、内容分发、调度等功能模块,使用户就近获取所需内容,降低网络拥塞,提高用户访问响应速度和命中率。CDN的关键技术主要有内容存储和分发技术。

25 LVS是什么及作用?

26 Nginx是什么及作用?

nginx是一个高性能的HTTP反向代理服务器,其特点是占用内存少,并发能力强.

1、作为Web服务器,Nginx处理静态文件、索引文件,自动索引的效率非常高

2、作为代理服务器,Nginx可以实现无缓存的反向代理加速,提高网站运行速度

3、作为负载均衡服务器,Nginx既可以在内部直接支持Rails和PHP,也可以支持HTTP代理服务器对外进行服务,同时还支持简单的容错和利用算法进行负载均衡

4、在性能方面,Nginx是专门为性能优化而开发的,实现上非常注重效率。它采用内核Poll模型,可以支持更多的并发连接,最大可以支持对5万个并发连接数的响应,而且只占用很低的内存资源

5、在稳定性方面,Nginx采取了分阶段资源分配技术,使得CPU与内存的占用率非常低。Nginx官方表示,Nginx保持1万个没有活动的连接,而这些连接只占用2.5MB内存,因此,类似DOS这样的攻击对Nginx来说基本上是没有任何作用的

6、在高可用性方面,Nginx支持热部署,启动速度特别迅速,因此可以在不间断服务的情况下,对软件版本或者配置进行升级,即使运行数月也无需重新启动,几乎可以做到7x24小时不间断地运行

27 keepalived是什么及作用?

keepalived观察其名可知,保持存活,在网络里面就是保持在线了,

也就是所谓的高可用或热备,它集群管理中保证集群高可用的一个服务软件,

其功能类似于heartbeat,用来防止单点故障(单点故障是指一旦某一点出现故障就会导致整个系统架构的不可用)的发生。

28 haproxy是什么以及作用?

HAProxy 是一款提供高可用性、负载均衡以及基于TCP(第四层)和HTTP(第七层)应用的代理软件,支持虚拟主机,它是免费、快速并且可靠的一种解决方案。

HAProxy特别适用于那些负载特大的web站点,这些站点通常又需要会话保持或七层处理。

HAProxy运行在时下的硬件上,完全可以支持数以万计的 并发连接。

并且它的运行模式使得它可以很简单安全的整合进您当前的架构中, 同时可以保护你的web服务器不被暴露到网络上。

(作用: 高可用性,负载平衡和用于TCP和基于http的应用程序的代理)

29 什么是负载均衡?

负载均衡改善了跨多个计算资源(例如计算机,计算机集群,网络链接,中央处理单元或磁盘驱动的的工作负载分布。负载平衡旨在优化资源使用,最大化吞吐量,最小化响应时间,并避免任何单个资源的过载。使用具有负载平衡而不是单个组件的多个组件可以通过冗余提高可靠性和可用性。负载平衡通常涉及专用软件或硬件。

30 什么是rpc及应用场景?

你编过程序吧?你程序里有函数或方法间的调用吧?

比如你写了两个函数fa和fb,在fa里肯定可以调用fb,这个可以理解吧?好了,铺垫完了。接下来入正题: 别人写了个程序,程序里有个函数rf,而且这个程序是独立运行的。你自己写程序时想调用这个rf,怎么办?rpc就是为了解决这个问题而出现的技术。远程过程调用就是一种在两个原本相互独立的进程间建立一种类似于单个程序内函数间调用的函数调用机制。这样,不仅一个程序内的函数可以相互调用,不同程序间的函数也可以相互调用了。 至于用途,你可以从程序内函数调用的用途出发进行思考。首先是可以直接利用别的程序的部分功能,这是最基础的。更重要的,利用rpc可以实现系统的分布式架构,一方面有些功能比较相关应该放到一起实现,一方面物理因素的原因要求系统分解为多机实现,因此有的功能实现为了一个机器上的进程,而另外的功能实现为在另外机器上的进程,这两个进程间的协同和信息交互就可以通过rpc来实现。 另外,有些现成系统所设计的扩展方式就是要通过rpc实现,这时你就需要通过它所选择的rpc协议编程方式对原系统进行功能扩展

楼上说的没错,我也举个例子。你操作你自己电脑硬盘上的文件,是个方法,和访问网络上的文件,在使用上没什么区别,但实际实现上存在差异。大体的差异你肯定能理解。至少有各种网络协议吧。rpc就是类似的东西。说来说去,就是不同计算主体之间数据协同问题。无非传统编写程序,函数和函数之间的调用,数据的协同很容易,基本在你的代码设计时,就考虑到了数据空间的设计和调用,甚至没有这个概念,只有局部变量和全局变量的概念。而跨进程的相互协同运行,则就多了数据协同的问题。有同步也有异步,不过总有同步点

RPC,就是将数据序列化之后传递给接收的服务器,然后获取一个序列化后的返回值。

在网络通信中,不管是TCP 还是UDP,我们都要在传输层上设计自己的应用层协议,使得前后端的数据可以相互通信传输一个可以识别的内容。

后来,人们期望能够更方便一点地让前后端进行交互,于是提出了RPC,就像调用函数一样来让前后端来进行通信,屏蔽掉复杂的应用层协议。

31 Post和Get区别

32 Cookie和Session

CookieSession
储存位置 客户端 服务器端
目的 跟踪会话,也可以保存用户偏好设置或者保存用户名密码等 跟踪会话
安全性 不安全 安全

33  apache和nginx的区别

nginx 相对 apache 的优点:

  • 轻量级,同样起web 服务,比apache 占用更少的内存及资源
  • 抗并发,nginx 处理请求是异步非阻塞的,支持更多的并发连接,而apache 则是阻塞型的,在高并发下nginx 能保持低资源低消耗高性能
  • 配置简洁
  • 高度模块化的设计,编写模块相对简单
  • 社区活跃

apache 相对nginx 的优点:

  • rewrite ,比nginx 的rewrite 强大
  • 模块超多,基本想到的都可以找到
  • 少bug ,nginx 的bug 相对较多
  • 超稳定

34 网站用户密码保存

  1. 明文保存
  2. 明文hash后保存,如md5
  3. MD5+Salt方式,这个salt可以随机
  4. 知乎使用了Bcrypy(好像)加密

35 简述浏览器通过WSGI请求动态资源的过程?

        浏览器发送的请求被Nginx监听到,Nginx根据请求的URL的PATH或者后缀把请求静态资源的分发到静态资源的目录,别的请求根据配置好的转发到相应端口。 实现了WSGI的程序会监听某个端口,监听到Nginx转发过来的请求接收后(一般用socket的recv来接收HTTP的报文)以后把请求的报文封装成environ的字典对象,然后再提供一个start_response的方法。把这两个对象当成参数传入某个方法比如wsgi_app(environ, start_response)或者实现了__call__(self, environ, start_response)方法的某个实例。这个实例再调用start_response返回给实现了WSGI的中间件,再由中间件返回给Nginx。

36 谈谈你对http协议的认识

一.HTTP协议版本
        HTTP1.0与HTTP1.1的区别主要体现在以下几个方面:
             1. HTTP1.0是短连接、HTTP1.1是长连接。
             2. 增加请求头和响应头。(什么是请求头和响应头?等下我会上图说明)
             3. 客户端不同请求之间是异步的。(个人理解,这里的异步并不是指客户端可以同时处理多个请求,而是当一个请求执行过程中遇等待情况时,可以切到另外一个请求上执 行)
        HTTP2.0相较于HTTP1.x主要在以下几个方面有所提升:
             1. HTTP2.0支持多路复用。
             2. HTTP2.0会根据请求优先级进行传输。(例如在浏览商品的时候突然滑到最下方,那么最下面的商品信息无疑是用户最想看到的,所以这时对最下面商品信息的请求属于优先级高的请求)
             3. HTTP2.0支持header压缩。
             4. HTTP2.0支持server推送。(http1.x只能由客户端发起请求,然后服务器被动的发送response。开启server push之后,server通过X-Associated-Content header告知客户端会有新的内容推送过来。在用户第一次打开网站首页的时候,server将资源主动推送过来可以极大的提升用户体验。)
             5. HTTP2.0支持server暗示。(与server推送不同,server暗示仅仅告知客户端服务器上有这些资源,或是有新内容产生,具体的下载还是要靠客户端发起请求完成,但由于省去了查询server状态这一过程,所以省去了一道询问)
二. HTTP通讯流程
        在HTTP1.0中,通讯流程可以概括为以下几步:
             1. 客户端与服务器建立TCP连接,一般使用80端口。
             2. 客户端向服务器发送请求。
             3. 服务器向客户端发送响应。
             4. TCP连接断开。
             5. 重复上述步骤。
       而在HTTP1.1中,通讯流程可以概括为以下几步:
             1. 客户端与服务器建立TCP连接,一般使用80端口。
             2. 客户端向服务器发送请求。
             3. 服务器向客户端发送响应。
             4. 重复上述步骤。
             5. 通讯完毕,TCP连接断开。

三. HTTP协议——请求与应答
两张图说明问题。
请求:

 

 

  响应:

再直白点:
请求:

<request line>
<headers>
<blank line>
<body>

响应(和请求一样,就是第一行变了):

<request line>
<headers>
<blank line>
<body>

37 谈谈你对websocket协议的认识

WebSocket介绍与原理
      WebSocket 是一种双向通信协议,在建立连接后,WebSocket 服务器和 Browser/Client Agent 都能主动的向对方发送或接收数据,就像 Socket 一样;
      WebSocket 需要类似 TCP 的客户端和服务器端通过握手连接,连接成功后才能相互通信。
目的:即时通讯,替代轮询
连接过程 —— 握手过程
        1. 浏览器、服务器建立TCP连接,三次握手。这是通信的基础,传输控制层,若失败后续都不执行。
        2. TCP连接成功后,浏览器通过HTTP协议向服务器传送WebSocket支持的版本号等信息。(开始前的HTTP握手)
        3. 服务器收到客户端的握手请求后,同样采用HTTP协议回馈数据。
        4. 当收到了连接成功的消息后,通过TCP通道进行传输通信。

WebSocket 机制
非 WebSocket 模式传统 HTTP 客户端与服务器的交互如下图所示:
图 1. 传统 HTTP 请求响应客户端服务器交互图

 

 

使用 WebSocket 模式客户端与服务器的交互如下图:
图 2.WebSocket 请求响应客户端服务器交互图

 

 

相对于传统 HTTP 每次请求-应答都需要客户端与服务端建立连接的模式,WebSocket 是类似 Socket 的 TCP 长连接的通讯模式,一旦 WebSocket 连接建立后,后续数据都以帧序列的形式传输。在客户端断开 WebSocket 连接或 Server 端断掉连接前,不需要客户端和服务端重新发起连接请求。
在海量并发及客户端与服务器交互负载流量大的情况下,极大的节省了网络带宽资源的消耗,有明显的性能优势,且客户端发送和接受消息是在同一个持久连接上发起,实时性优势明显。
WebSocket能更好的节省服务器资源和带宽并达到实时通讯,它建立在 TCP 之上,同 HTTP 一样通过 TCP 来传输数据。


WebSocket和 HTTP 最大不同是:
         HTTP协议是非持久化的,单向的网络协议,在建立连接后只允许浏览器向服务器发出请求后,服务器才能返回相应的数据。这样的方法最明显的缺点就是需要不断的发送请求,而且通常HTTP request的Header是非常长的,为了传输一个很小的数据 需要付出巨大的代价,是很不合算的,占用了很多的宽带。会导致过多不必要的请求,浪费流量和服务器资源,每一次请求、应答,都浪费了一定流量在相同的头部信息上
然而WebSocket的出现可以弥补这一缺点。在WebSocket中,只需要服务器和浏览器通过HTTP协议进行一个握手的动作,然后单独建立一条TCP的通信通道进行数据的传送。
不同点
1. WebSocket是双向通信协议,模拟Socket协议,可以双向发送或接受信息。HTTP是单向的。
2. WebSocket是需要握手进行建立连接的。
相同点
1. 都是一样基于TCP的,都是可靠性传输协议。
2. 都是应用层协议。
原理
WebSocket同HTTP一样也是应用层的协议,但是它是一种双向通信协议,是建立在TCP之上的。
 联系
WebSocket在建立握手时,数据是通过HTTP传输的。但是建立之后,在真正传输时候是不需要HTTP协议的。

38 什么是magic string ?

39 列举Http请求中常见的请求方式?

            GET:请求获取由 Request-URI 所标识的资源。

            POST:在 Request-URI 所标识的资源后附加新的数据。

            HEAD:请求获取由 Request-URI 所标识的资源的响应消息报头。

            OPTIONS:请求查询服务器的性能,或查询与资源相关的选项和需求。

            PUT:请求服务器存储一个资源,并用 Request-URI作为其标识。

            DELETE:请求服务器删除由 Request-URI所标识的资源。

            TRACE:请求服务器回送收到的请求信息,主要用语测试或诊断。

40 列举Http请求中的状态码?

      常见的响应状态码有以下几种,在各种下面分别列几个常见的状态码:         

           1开头(消息)

           2开头(成功)

               200(OK):请求成功

               202(Accepted):已接受请求,尚未处理

               204(No Content):请求成功,且不需返回内容

           3开头(重定向)

               301(Moved Permanently):被请求的资源已永久移动到新位置

               301(Moved Temporarily):被请求的资源已临时移动到新位置

           4开头(请求错误)

               400(Bad Request):请求的语义或是参数有错

               403(Forbidden):服务器拒绝了请求

              404(Not Found):未找到请求的资源

           5开头(服务器错误)

              500(Internal Server Error):服务器遇到错误,无法完成请求

              502(Bad Getway):网关错误,一般是服务器压力过大导致连接超时         

              503(Service Unavailable):服务器宕机

41 列举Http请求中常见的请求头?

l Accept:浏览器可接受的MIME类型;

l Accept-Charset:浏览器可接受的字符集;

l Accept-Encoding:浏览器能够进行解码的数据编码方式,比如gzip。Servlet能够向支持gzip的浏览器返回经gzip编码的HTML页面。许多情形下这可以减少5到10倍的下载时间;

l Accept-Language:浏览器所希望的语言种类,当服务器能够提供一种以上的语言版本时要用到;

l Authorization:授权信息,通常出现在对服务器发送的WWW-Authenticate头的应答中;

l Connection:表示是否需要持久连接。如果Servlet看到这里的值为“Keep-Alive”,或者看到请求使用的是HTTP 1.1(HTTP 1.1默认进行持久连接),它就可以利用持久连接的优点,当页面包含多个元素时(例如Applet,图片),显著地减少下载所需要的时间。要实现这一点,Servlet需要在应答中发送一个Content-Length头,最简单的实现方法是:先把内容写入ByteArrayOutputStream,然后在正式写出内容之前计算它的大小;

l Content-Length:表示请求消息正文的长度;

l Cookie:这是最重要的请求头信息之一;

l From:请求发送者的email地址,由一些特殊的Web客户程序使用,浏览器不会用到它;

l Host:初始URL中的主机和端口;

l If-Modified-Since:只有当所请求的内容在指定的日期之后又经过修改才返回它,否则返回304“Not Modified”应答;

l Pragma:指定“no-cache”值表示服务器必须返回一个刷新后的文档,即使它是代理服务器而且已经有了页面的本地拷贝;

l Referer:包含一个URL,用户从该URL代表的页面出发访问当前请求的页面。

l User-Agent:浏览器类型,如果Servlet返回的内容与浏览器类型有关则该值非常有用;

42 接口的幂等性是什么意思?

第一次访问一个接口后,再对该接口进行N次相同的访问时,对资源不造影响,就认为接口具有幂等性。
  GET,  #第一次获取结果、第二次也是获取结果对资源都不会造成影响,幂等。
  POST, #第一次新增数据,第二次也会再次新增,非幂等。
  PUT,  #第一次更新数据,第二次不会再次更新,幂等。
  PATCH,#第一次更新数据,第二次不会再次更新,非幂等。
  DELTE,#第一次删除数据,第二次不在再删除,幂等。

43 什么是RPC?

RPC(Remote Procedure Call)是远程过程调用,它是一种通过网络从远程计算机程序上请求服务,而不需要了解底层网络技术的协议。

RPC协议假定某些传输协议的存在,如TCP或UDP,为通信程序之间携带信息数据。在OSI网络通信模型中,RPC跨越了传输层和应用层。RPC使得开发包括网络分布式多程序在内的应用程序更加容易。

RPC采用客户机/服务器模式。请求程序就是一个客户机,而服务提供程序就是一个服务器。首先,客户机调用进程发送一个有进程参数的调用信息到服务进程,然后等待应答信息。

44 Http和Https的区别?

#Http: 80端口
#https: 443端口
#http信息是明文传输,https则是具有安全性的ssl加密传输协议。
#- 自定义证书 
    - 服务端:创建一对证书
    - 客户端:必须携带证书
#- 购买证书
    - 服务端: 创建一对证书,。。。。
    - 客户端: 去机构获取证书,数据加密后发给咱们的服务单
    - 证书机构:公钥给改机构

45 描述用浏览器访问www.baidu.com的过程

  • 先要解析出baidu.com对应的ip地址;
           1) 先要知道默认网关的mac地址;
                  1> 使用arp获取默认网关的mac地址;
           2) 组织数据发送给默认网关(ip还是dns服务器的ip,但是mac地址是默认网关的mac地址);
           3) 默认网关拥有转发数据的能力,把数据转发给路由器;
           4) 路由器根据自己的路由协议,来选择一个合适的较快的路径转发数据给目的网关;
           5) 目的网关(dns服务器所在的网关),把数据转发给dns服务器;
           6) dns服务器查询解析出baidu.com对应的ip地址,并把它原路返回给请求这个域名的client;
  • 得到了baidu.com对应的ip地址之后,会发送tcp的3次握手,进行连接;
  • 使用http协议发送请求数据给web服务器;
  • web服务器收到数据请求之后,通过查询自己的服务器得到相应的结果,原路返回给浏览器;
  • 浏览器接收到数据后,通过浏览器自己的渲染功能来显示这个网页;
  • 浏览器关闭tcp连接,即4次挥手;

46 怎么实现强行关闭客户端和服务器之间的连接?

       在socket通信过程中不断循环检测一个全局变量(开关标记变量),一旦标记变量变为关闭,则调用socket的close方法,循环结束,从而达到关闭连接的目的。

47 简述 asynio模块的作用和应用场景。

asyncio是Python 3.4版本引入的标准库,直接内置了对异步IO的支持。
asyncio的编程模型就是一个消息循环。我们从asyncio模块中直接获取一个EventLoop的引用,
然后把需要执行的协程扔到EventLoop中执行,就实现了异步IO。

48 简述 gevent模块的作用和应用场景。

当一个greenlet遇到IO操作时,比如访问网络,就自动切换到其他的greenlet,等到IO操作完成,
再在适当的时候切换回来继续执行。由于IO操作非常耗时,经常使程序处于等待状态,
有了gevent为我们自动切换协程,就保证总有greenlet在运行,而不是等待IO。
由于切换是在IO操作时自动完成,所以gevent需要修改Python自带的一些标准库,
这一过程在启动时通过monkey patch完成:

49 twisted框架的使用和应用?

 https://www.cnblogs.com/zhiyong-ITNote/archive/2017/08/14/7360442.html

 

posted @ 2020-01-25 10:39  秋华  阅读(1126)  评论(0编辑  收藏  举报