python使用套接字

编程入门 行业动态 更新时间:2024-10-26 04:29:05

<a href=https://www.elefans.com/category/jswz/34/1770869.html style=python使用套接字"/>

python使用套接字

python使用套接字

插座介绍 ( Introduction to Socket )

As a complement to the network client tutorial, this tutorial shows how to implement a simple web server in Python. To be sure, this is no substitute for Apache or Zope. There are also more robust ways to implement web services in Python, using modules like BaseHTTPServer. This server uses the socket module exclusively.

作为网络客户端教程的补充,本教程展示了如何在Python中实现简单的Web服务器。 可以肯定的是,这不能替代Apache或Zope。 使用BaseHTTPServer之类的模块,还有更健壮的方法可以在Python中实现Web服务。 该服务器专门使用套接字模块。

You will recall that the socket module is the backbone of most Python web service modules. As with the simple network client, building a server with it illustrates the basics of web services in Python transparently. BaseHTTPServer itself imports the socket module to affect a server.

您会记得,套接字模块是大多数Python Web服务模块的基础。 与简单的网络客户端一样,构建服务器来透明地说明Python中Web服务的基础。 BaseHTTPServer本身会导入套接字模块以影响服务器。

正在运行的服务器 ( Running Servers )

By way of review, All network transactions happen between clients and servers. In most protocols, the clients ask a certain address and receive data.

作为回顾,所有网络事务都在客户端和服务器之间发生。 在大多数协议中,客户端询问特定地址并接收数据。

Within each address, a multitude of servers can run. The limit is in the hardware. With sufficient hardware (RAM, processor speed, etc.), the same computer can serve as a web server, an ftp server, and mail server (pop, smtp, imap, or all of the above) all at the same time. Each service is associated with a port. The port is bound to a socket. The server listens to its associated port and gives information when requests are received on that port.

在每个地址内,可以运行许多服务器。 限制在硬件中。 借助足够的硬件(RAM,处理器速度等),同一台计算机可以同时充当Web服务器,FTP服务器和邮件服务器 (pop,smtp,imap或以上所有功能)。 每个服务都与一个端口关联。 端口绑定到套接字。 服务器侦听其关联的端口,并在该端口上收到请求时提供信息。

通过套接字通信 ( Communicating Via Sockets )

So to affect a network connection you need to know the host, the port, and the actions allowed on that port. Most web servers run on port 80. However, in order to avoid conflict with an installed Apache server, our web server will run on port 8080. In order to avoid conflict with other services, it is best to keep HTTP services on port 80 or 8080. These are the two most common. Obviously, if these are used, you must find an open port and alert users to the change.

因此,要影响网络连接,您需要知道主机,端口以及该端口上允许的操作。 大多数Web服务器在端口80上运行。但是,为了避免与已安装的Apache服务器冲突,我们的Web服务器将在端口8080上运行。为了避免与其他服务冲突,最好将HTTP服务保留在端口80或8080.这是最常见的两种。 显然,如果使用了这些,则必须找到一个开放的端口,并向用户发出更改通知。

As with the network client, you should note that these addresses are the common port numbers for the different services. As long as the client asks for the correct service on the right port at the right address, communication will still happen. Google's mail service, for example, did not initially run on the common port numbers but, because they know how to access their accounts, users can still get their mail.

与网络客户端一样,您应注意,这些地址是不同服务的通用端口号。 只要客户在正确的地址,正确的端口上请求正确的服务,通信仍然会发生。 例如, 谷歌的邮件服务最初并未在通用端口号上运行,但是由于他们知道如何访问其帐户,因此用户仍然可以获取其邮件。

Unlike the network client, all variables in the server are hardwired. Any service that is expected to run constantly should not have the variables of its internal logic set at the command line. The only variation on this would be if, for some reason, you wanted the service to run occasionally and on various port numbers. If this were the case, however, you would still be able to watch the system time and change bindings accordingly.

与网络客户端不同,服务器中的所有变量都是硬连线的。 任何期望持续运行的服务都不应在命令行中设置其内部逻辑的变量。 唯一的变化是,由于某种原因,如果您希望该服务偶尔在不同的端口号上运行。 但是,如果是这种情况,您仍然可以观看系统时间并相应地更改绑定。

So our sole import is the socket module.

因此,我们唯一的导入是套接字模块。


import socket

Next, we need to declare a few variables.

接下来,我们需要声明一些变量。

主机和端口 ( Hosts and Ports )

As already mentioned, the server needs to know the host to which it is to be associated and the port on which to listen. For our purposes, we shall have the service apply to any host name at all.

如前所述,服务器需要知道与之关联的主机和侦听的端口。 为了我们的目的,我们将使该服务完全适用于任何主机名。

 host = '' 
port = 8080

The port, as mentioned earlier, will be 8080. So note that, if you use this server in conjunction with the network client, you will need to change the port number used in that program.

如前所述,端口将为8080。因此请注意,如果将此服务器与网络客户端一起使用,则需要更改该程序中使用的端口号。

创建一个套接字 ( Creating a Socket )

Whether to request information or to serve it, in order to access the Internet, we need to create a socket. The syntax for this call is as follows:

无论是请求信息还是提供信息,为了访问Internet ,我们都需要创建一个套接字。 此调用的语法如下:


<variable> = socket.socket(<family>, <type>)

The recognised socket families are:

公认的套接字系列是:

  • AF_INET: IPv4 protocols (both TCP and UDP)

    AF_INET:IPv4协议(TCP和UDP)
  • AF_INET6: IPv6 protocols (both TCP and UDP)

    AF_INET6:IPv6协议(TCP和UDP)
  • AF_UNIX: UNIX domain protocols

    AF_UNIX:UNIX域协议

The first two are obviously internet protocols. Anything that travels over the internet can be accessed in these families. Many networks still do not run on IPv6. So, unless you know otherwise, it is safest to default to IPv4 and use AF_INET.

前两个显然是互联网协议。 这些家庭可以访问互联网上进行的任何旅行。 许多网络仍无法在IPv6上运行。 因此,除非您另外知道,否则默认设置为IPv4并使用AF_INET是最安全的。

The socket type refers to the type of communication used through the socket. The five socket types are as follows:

套接字类型是指通过套接字使用的通信类型。 五个套接字类型如下:

  • SOCK_STREAM: a connection-oriented, TCP byte stream

    SOCK_STREAM:面向连接的TCP字节流
  • SOCK_DGRAM: UDP transferral of datagrams (self-contained IP packets that do not rely on client-server confirmation)

    SOCK_DGRAM:数据报的UDP传输(不依赖客户端-服务器确认的独立IP数据包)
  • SOCK_RAW: a raw socket

    SOCK_RAW:原始套接字
  • SOCK_RDM: for reliable datagrams

    SOCK_RDM:用于可靠的数据报
  • SOCK_SEQPACKET: sequential transfer of records over a connection

    SOCK_SEQPACKET:通过连接顺序传输记录

By far, the most common types are SOCK_STEAM and SOCK_DGRAM because they function on the two protocols of the IP suite (TCP and UDP). The latter three are much rarer and so may not always be supported.

到目前为止,最常见的类型是SOCK_STEAM和SOCK_DGRAM,因为它们在IP套件的两个协议(TCP和UDP)上起作用。 后三种情况很少见,因此可能并不总是得到支持。

So let's create a socket and assign it to a variable.

因此,让我们创建一个套接字并将其分配给变量。


c = socket.socket(socket.AF_INET, socket.SOCK_STREAM)

设置套接字选项 ( Setting Socket Options )

After creating the socket, we then need to set the socket options. For any socket object, you can set the socket options by using the setsockopt() method. The syntax is as follows:

创建套接字后,我们需要设置套接字选项。 对于任何套接字对象,都可以使用setsockopt()方法设置套接字选项。 语法如下:

socket_object.setsockopt(level, option_name, value) For our purposes, we use the following line:
socket_object.setsockopt(level,option_name,value)出于我们的目的,我们使用以下行:


c.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)

The term 'level' refers to the categories of options. For socket-level options, use SOL_SOCKET. For protocol numbers, one would use IPPROTO_IP. SOL_SOCKET is a constant attribute of the socket. Exactly which options are available as part of each level are determined by your operating system and whether you are using IPv4 or IPv6.
术语“级别”是指选项的类别。 对于套接字级别的选项,请使用SOL_SOCKET。 对于协议号,可以使用IPPROTO_IP。 SOL_SOCKET是套接字的常量属性。 每个级别中确切可用的选项取决于您的操作系统以及使用的是IPv4还是IPv6。
The documentation for Linux and related Unix systems can be found in the system documentation. The documentation for Microsoft users can be found on the MSDN website. As of this writing, I have not found Mac documentation on socket programming. As Mac is roughly based upon BSD Unix, it is likely to implement a full complement of options.
Linux和相关Unix系统的文档可以在系统文档中找到。 可以在MSDN网站上找到Microsoft用户的文档。 在撰写本文时,我还没有找到有关套接字编程的Mac文档。 由于Mac大致基于BSD Unix,因此它可能会实现全部选项。
In order to ensure reusability of this socket, we use the SO_REUSEADDR option. One could restrict the server to only run on open ports, but that seems unnecessary. Do note, however, that if two or more services are deployed on the same port, the effects are unpredictable. One cannot be certain which service will receive which packet of information.
为了确保此套接字的可重用性,我们使用SO_REUSEADDR选项。 可以将服务器限制为只能在打开的端口上运行,但这似乎是不必要的。 但是请注意,如果在同一端口上部署了两个或多个服务,则影响是不可预测的。 不能确定哪个服务将接收哪个信息包。
Finally, the '1' for a value is the value by which the request on the socket is known in the program. In this way, a program can listen on a socket in very nuanced ways.
最后,值的“ 1”是在程序中知道套接字上的请求的值。 这样,程序可以以非常细微的方式监听套接字。

将端口绑定到套接字 ( Binding the Port to the Socket )

After creating the socket and setting its options, we need to bind the port to the socket.

创建套接字并设置其选项后,我们需要将端口绑定到套接字。


c.bind((host, port))

The binding done, we now tell the computer to wait and to listen on that port.

绑定完成后,我们现在告诉计算机等待并在该端口上侦听。


c.listen(1)

If we want to give feedback to the person who calls the server, we could now enter a print command to confirm that the server is up and running.

如果我们想给调用服务器的人员反馈,我们现在可以输入打印命令来确认服务器已启动并正在运行。

处理服务器请求 ( Handling a Server Request )

Having setup the server, we now need to tell Python what to do when a request is made on the given port. For this we reference the request by its value and use it as the argument of a persistent while loop.

设置服务器后,我们现在需要告诉Python在给定端口上发出请求时该怎么做。 为此,我们通过请求的值引用该请求,并将其用作持久性while循环的参数。

When a request is made, the server should accept the request and create a file object to interact with it.

发出请求后,服务器应接受该请求并创建一个文件对象与之交互。

 while 1: 
csock, caddr = c.accept()
cfile = csock.makefile('rw', 0)

In this case, the server uses the same port for reading and writing. Therefore, the makefile method is given an argument 'rw'. The null length of the buffer size simply leaves that part of the file to be determined dynamically.

在这种情况下,服务器使用相同的端口进行读写。 因此,makefile方法的参数为“ rw”。 缓冲区大小的空长度只是使文件的那一部分可以动态确定。

向客户端发送数据 ( Sending Data to the Client )

Unless we want to create a single-action server, the next step is to read input from the file object. When we do that, we should be careful to strip that input of excess whitespace.

除非我们要创建单动服务器,否则下一步是从文件对象读取输入。 当我们这样做时,我们应该小心删除多余的空白输入。

 line = cfile.readline().strip()

The request will come in the form of an action, followed by a page, the protocol, and the version of the protocol being used. If one wants to serve a web page, one splits this input to retrieve the page requested and then reads that page into a variable which is then written to the socket file object. A function for reading a file into a dictionary can be found in the blog.

该请求将以操作的形式出现,随后是页面,协议和所使用协议的版本。 如果要为网页提供服务,则可以拆分此输入以检索请求的页面,然后将该页面读取到一个变量中,然后将其写入套接字文件对象。 可以在博客中找到将文件读入字典的功能。

In order to make this tutorial a bit more illustrative of what one can do with the socket module, we will forego that part of the server and instead show how one can nuance the presentation of data. Enter the next several lines into the program.

为了使本教程更能说明套接字模块的功能,我们将放弃服务器的那一部分,而是展示如何细化数据的呈现。 在程序中输入接下来的几行。

 cfile.write('HTTP/1.0 200 OK\n\n') 
cfile.write('<html><head><title>Welcome %s!</title></head>' %(str(caddr)))
cfile.write('<body><h1>Follow the link...</h1>')
cfile.write('All the server needs to do is ')
cfile.write('to deliver the text to the socket. ')
cfile.write('It delivers the HTML code for a link, ')
cfile.write('and the web browser converts it. <br><br><br><br>')
cfile.write('<font size="7"><center> <a href=".html">Click me!</a> </center></font>')
cfile.write('<br><br>The wording of your request was: "%s"' %(line))
cfile.write('</body></html>')

最终分析并关闭 ( Final Analysis and Shutting Down )

If one is sending a web page, the first line is a nice way of introducing the data to a web browser. If it is left out, most web browsers will default to rendering HTML. However, if one includes it, the 'OK' must be followed by two new line characters. These are used to distinguish the protocol information from the page content.

如果要发送网页,则第一行是将数据引入Web浏览器的一种好方法。 如果将其忽略,大多数Web浏览器将默认呈现HTML 。 但是,如果其中包括一个字符,则必须在“ OK”之后加上两个换行符。 这些用于区分协议信息和页面内容。

The syntax of the first line, as you can probably surmise, is protocol, protocol version, message number, and status. If you have ever gone to a web page that has moved, you have probably received a 404 error. The 200 message here is simply the affirmative message.

您可能会猜到,第一行的语法是协议,协议版本,消息号和状态。 如果您曾经访问过已移动的网页,则可能已收到404错误。 这里的200消息只是肯定的消息。

The rest of the output is simply a web page broken up over several lines. You will note that the server can be programmed to use user data in the output. The final line reflects the web request as it was received by the server.

其余的输出只是一个分成几行的网页。 您会注意到,可以对服务器进行编程以在输出中使用用户数据。 最后一行反映了服务器收到的Web请求。

Finally, as the closing acts of the request, we need to close the file object and the server socket.

最后,作为请求的关闭操作,我们需要关闭文件对象和服务器套接字。

 cfile.close() 
csock.close()

Now save this program under a recognisable name. After you call it with 'python program_name.py', if you programmed a message to confirm the service as running, this should print to the screen. The terminal will then seem to pause. All is as it should be. Open your web browser and go to localhost:8080. You should then see the output of the write commands we gave. Please note that, for the sake of space, I did not implement error handling in this program. However, any program released into the 'wild' should.

现在,以可识别的名称保存该程序。 在使用“ python program_name.py”调用它之后,如果您编写了一条消息以确认该服务正在运行,则该消息将显示在屏幕上。 然后,终端将似乎暂停。 一切都是应有的。 打开您的Web浏览器,然后转到localhost:8080。 然后,您应该看到我们给出的写命令的输出。 请注意,为了节省空间,我没有在该程序中实现错误处理。 但是,任何发布到“野外”的程序都应该。

翻译自:

python使用套接字

更多推荐

python使用套接字

本文发布于:2024-03-15 03:21:06,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1738005.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:python

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!