简介
socket又称“套接字”,应用程序通常通过“套接字”向未来发出请求或应答网络请求,使主机或一台计算机上的进程可以通讯。
使用socket函数来创建套接字,语法: socket.socket(family,type,protocol)
参数如下:
family:套接字家族可以使用AF_UNIX 或者AF_INIT, 前者只能够用于单一的Unix系统进程间通信,后者用于服务器之间网络通信
type:套接字类型可以根据是面向连接的还是非连接分为SOCK_STREAM或者SOCK_DGRAM 前者用于tcp,后者用于udp
protocol:一般不填
socket对象方法
服务器端:
s.bind() 绑定地址(host,port)到套接字,在AF_INIT下,以元组(host,port)的形式表示地址
s.listen() 开始tcp监听,backlog指定在拒绝连接之前,操作系统可以挂起的最大连接数量。该值至少为1,大部分应用程序设为5就 可以了。
s.accept() 被动接收tcp客户端连接,(阻塞式)等待连接的到来。
客户端:
s.connect() 主动初始化tcp服务器连接,连接出错就返回socket error
公共用途的套接字函数:
s.recv() 接收tcp数据,数据以字符串形式返回
s.send() 发送tcp数据,将string中的数据发送到连接的套接字。返回值是要发送的字节数量,该数量可能小于string的字节大小
s.sendall() 完整发送tcp数据,将string中的数据发送到连接的套接字,但在返回之前尝试发送所有数据,成功返回none,失败抛 出异常
s.close() 关闭套接字
socket编程思路
tcp服务端:
1、创建套接字,绑定套接字到本地ip和端口
socket.socket(socket.AF_INET,socket.SOCK_STREAM) s.bind()
2、开始监听连接
s.listen()
3、进入循环,不断接受客户端的连接请求
s.accept()
4、然后接收传来的数据,并发送给对方数据
s.recv() s.sendall()
5、传输完毕,关闭套接字
s.close()
tcp客户端:
1、创建套接字,连接远端地址
socket.socket(socket.AF_INET,socket.SOCK_STREAM) s.connect()
2、连接后发送数据和接收数据
s.sendall() s.recv()
3、传输完毕,关闭套接字
s.close()
代码如下:
server.py
# coding=utf-8
import socket
s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.bind(('localhost',8899))
s.listen(1)
while 1:
conn,addr = s.accept()
print('ip:',addr)
data = conn.recv(1024).decode()
conn.send(data.encode())
conn.close()
client.py
# coding=utf-8
import socket
s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.connect(('localhost',8899))
s.send(('123').encode())
data = s.recv(1024)
print(data.decode())
s.close()
a bytes-like object is required, not 'str'错误问题:由于Python2与Python3在套接字返回值类型上有区别,发送数据须为bytes型,通过encode()函数将str型数据转变为bytes,接收到数据需要打印时用decode()函数解码为str型数据。
使用Python3的subprocess代替Python2的command模块 执行cmd命令
server.py
# coding=utf-8
import socket
import subprocess
s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.bind(('localhost',8899))
s.listen(5)
while 1:
conn,addr = s.accept()
print('ip:',addr)
cmd = conn.recv(1024).decode()
cmd_status,cmd_output = subprocess.getstatusoutput(cmd)
conn.send(cmd_output.encode())
conn.close()
client.py
# coding=utf-8
import socket
s = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
s.connect(('localhost',8899))
while 1:
cmd = input('input cmd(press q to quit): ')
if cmd == 'q':
break
s.send(cmd.encode())
data = s.recv(1024).decode()
print(data)
s.close()