ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

相同的套接字对象如何服务于不同的客户端?

2019-11-19 18:56:22  阅读:126  来源: 互联网

标签:sockets python


如文档中所述:Python socket.accept()

Accept a connection. The socket must be bound to an address and
listening for connections. The return value is a pair (conn, address)
where conn is a new socket object usable to send and receive data on
the connection, and address is the address bound to the socket on the
other end of the connection.

The newly created socket is non-inheritable.

Changed in version 3.4: The socket is now non-inheritable.

服务器代码是

>>> from socket import *
>>> sock = socket(AF_INET, SOCK_STREAM)
>>> sock.bind(("localhost", 20000))
>>> sock.getsockname()
('127.0.0.1', 20000)
>>> sock.listen(1)
>>> while True: 
...     conn, address = sock.accept()
...     print("Address of client : {0}".format(address))
...     print("Address of socket : {0}".format(conn.getsockname()))
... 
Address of client : ('127.0.0.1', 47165)
Address of socket : ('127.0.0.1', 20000)
Address of client : ('127.0.0.1', 47166)
Address of socket : ('127.0.0.1', 20000)

客户端代码是

>>> from socket import *
>>> sclient1 = socket(AF_INET, SOCK_STREAM)
>>> sclient2 = socket(AF_INET, SOCK_STREAM)
>>> sclient1.connect(("localhost", 20000))
>>> sclient2.connect(("localhost", 20000))

返回的新套接字对象的地址始终与实际接受连接的原始套接字的地址相同.

我一直以为服务器会使用不同的随机端口创建一个新的套接字对象,但是从上面可以看出,即使对于多个客户端,新conn对象的地址和端口也相同.那么服务器如何处理多个客户端?

编辑

我知道上面的代码正在阻止.如果我使用多个线程来处理不同的客户端连接,则必须将新的套接字对象和客户端地址发送到我的线程函数.因此,多个线程然后使用相同的服务器地址和端口来处理多个客户端.

线程服务器

>>> from socket import *    
>>> import threading
>>> def handler(conn, address):
...     print("Address of client : {0}".format(address))
...     print("Address of socket : {0}".format(conn.getsockname()))
... 
>>> sock = socket(AF_INET, SOCK_STREAM)
>>> sock.bind(("localhost", 20000))
>>> sock.listen(1)
>>> while 1:
...     conn, address = sock.accept()
...     t = threading.Thread(target=handler, args=[conn, address])
...     t.start()
... 
Address of client : ('127.0.0.1', 47169)
Address of socket : ('127.0.0.1', 20000)
Address of client : ('127.0.0.1', 47170)
Address of socket : ('127.0.0.1', 20000)

解决方法:

I always thought that the server would create a new socket object with a different random port

这将需要告诉客户端要使用哪个新端口进行连接.很好,没有必要,请参阅下文.这也意味着,到一个主机地址的打开连接数不能超过65535,这对于某些系统可能会中断很多.

How is then the server able to handle multiple clients?

客户端连接后,元组(server_addr,server_port,client_addr,client_port)是唯一的.当有数据包进入时,网络堆栈会搜索与该元组匹配的开放连接,并将传入的数据包重定向到相关的套接字(/文件描述符).

服务器套接字(您在其上执行accept())未连接(正在侦听),但已绑定.这意味着它在另一端没有对等方(没有客户端地址),但是却有本地地址(服务器端).

accept()返回一个新的套接字.这是绑定和连接.绑定与上面相同:它具有本地地址和端口.该地址与服务器套接字的地址相同,但是新套接字的状态也已连接.这意味着我们可以与对方进行通信的另一方(具有地址).我们还具有该对等方的地址(对等方地址)和端口(对等方端口).此信息足以唯一标识连接.

客户端套接字仅接受与所有四个(server_addr,server_port,client_addr,client_port)匹配的数据.

标签:sockets,python
来源: https://codeday.me/bug/20191119/2038349.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有