今天将python中socket模块的基本API学习完后,照着书上的实例编写一个套接字服务器和客户端。采用python3.5版本,在注释中会标明python2和python3的不同之处。

1.代码

(1)服务器端及对应代码解释

 1 # ! /usr/bin/env python
 2 # -*- coding: utf-8 -*-
 3 # 编写回显服务器
 4 
 5 import socket
 6 import sys
 7 import argparse
 8 
 9 # 定义常量
10 host = 'localhost'
11 data_payload = 2048
12 backlog = 5
13 
14 
15 def echo_server(port):
16 
17     # 创建一个TCP socket
18     sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
19 
20     # 设置TCP套接字关联选项——重用地址
21     sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
22 
23     # 建立套接字端口
24     server_address = (host, port)
25     print("Starting up echo server on %s port %s" % server_address)
26 
27     # 将socket绑定到server_address地址
28     sock.bind(server_address)
29 
30     # 监听客户端
31     # backlog指定最多允许多少个客户连接到服务器。它的值至少为1。收到连接请求后,这些请求需要排队,如果队列满,就拒绝请求。
32     # 这里设定为5
33     sock.listen(backlog)
34     # 在调用 Listen 之前,必须首先调用 Bind 方法,否则 Listen 将引发 SocketException。
35     while True:
36         print("Waiting to receive message from client")
37 
38         # 调用accept方法时,socket会时入“waiting”状态。客户请求连接时,方法建立连接并返回服务器。
39         # accept方法返回一个含有两个元素的 元组(connection,address)。第一个元素connection
40         # 是新的socket对象,服务器必须通过它与客户通信;第二个元素 address是客户的Internet地址。
41         client, address = sock.accept()
42 
43         # 指定data最大长度为2048字节
44         data = client.recv(data_payload)
45         if data:
46             print("Data: %s" % data)
47             client.send(data)
48             print("sent %s bytes back to %s" % (data, address))
49         # 关闭连接
50         client.close()
51 
52 if __name__ == '__main__':
53     # 创建一个解析对象,其中描述为"Socket Error Examples"
54     parser = argparse.ArgumentParser(description='Socket Server Example')
55     # 采用add_argument方法
56     # name or flags —— 必须的参数,该参数接收选项参数或者是位置参数
57     # action:
58         # (1)store —— 默认action模式,储存值到指定变量
59         # (2)store_const —— 储存值在参数的const部分指定,多用于实现非布尔的命令行flag
60         # (3)store_true/store_false —— 布尔开关。可以2个参数对应一个变量
61         # (4)append —— 储存值到列表,储存值在参数的const部分指定
62         # (5)append_const —— 储存值到列表,储存值在参数的const部分指定
63         # (6)version —— 输出版本信息然后退出
64     # type —— 把从命名行输入的结果转成设置的类型,通常用来检查值的范围,以及合法性。默认string  
65     # required —— 指定某个选项在命名中出现, 默认False, 若为 True, 表示必须输入该参数
66     # dest —— 把位置或者选项关联到一个特定的名字
67     parser.add_argument('--port', action="store", dest="port", type=int, required=True)
68     # 调用parse_args()方法进行解析
69     given_args = parser.parse_args()
70     port = given_args.port
71     echo_server(port)
72 
73 def bind(self, address):  # real signature unknown; restored from __doc__
74     """
75     bind(address)
76 
77     Bind the socket to a local address.  For IP sockets, the address is a
78     pair (host, port); the host must refer to the local host. For raw packet
79     sockets the address is a tuple (ifname, proto [,pkttype [,hatype]])
80     """
81     pass
82 def listen(self, backlog=None):  # real signature unknown; restored from __doc__
83     """
84     listen([backlog])
85 
86     Enable a server to accept connections.  If backlog is specified, it must be
87     at least 0 (if it is lower, it is set to 0); it specifies the number of
88     unaccepted connections that the system will allow before refusing new
89     connections. If not specified, a default reasonable value is chosen.
90     """
91     pass
服务器端代码

相关文章:

  • 2022-12-23
  • 2021-07-12
  • 2022-02-26
  • 2022-12-23
  • 2021-12-04
  • 2022-12-23
  • 2021-12-10
  • 2022-12-23
猜你喜欢
  • 2022-12-23
  • 2021-03-28
  • 2021-11-15
  • 2022-01-28
  • 2022-12-23
  • 2021-11-25
  • 2022-12-23
相关资源
相似解决方案