python socket epoll_socket使用epoll的一个问题

代码如下,使用epoll创建的一个异步socket的服务器(代码基本为http://scotdoyle.com/python-epoll-howto....中的Example 3,只不过加了一些日志打印)

import os

import select

import socket

import logging

import time

eventmasks = {

"EPOLLERR": 8,

"EPOLLET": 2147483648,

"EPOLLHUP": 16,

"EPOLLIN": 1,

"EPOLLMSG": 1024,

"EPOLLONESHOT": 1073741824,

"EPOLLOUT": 4,

"EPOLLPRI": 2,

"EPOLLRDBAND": 128,

"EPOLLRDNORM": 64,

"EPOLLWRBAND": 512,

"EPOLLWRNORM": 256,

}

eventmask_ids = {

1: "EPOLLIN",

2: "EPOLLPRI",

4: "EPOLLOUT",

8: "EPOLLERR",

16: "EPOLLHUP",

64: "EPOLLRDNORM",

128: "EPOLLRDBAND",

256: "EPOLLWRNORM",

512: "EPOLLWRBAND",

1024: "EPOLLMSG",

1073741824: "EPOLLONESHOT",

2147483648: "EPOLLET"

}

formatter = "[%(asctime)-15s] [%(levelname)s] %(message)s"

logging.basicConfig(level=logging.DEBUG, format=formatter)

EOL1 = b'\n\n'

EOL2 = b'\n\r\n'

response = b'HTTP/1.0 200 OK\r\nDate: %s\r\n'

response += b'Content-Type: text/plain\r\nContent-Length: %s\r\n\r\n%s'

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

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

s.bind(("0.0.0.0", 9999))

s.listen(1024)

s.setblocking(0)

epoll = select.epoll()

s_fileno = s.fileno()

epoll.register(s, select.EPOLLIN)

try:

connections = {}

request_data = {}

response_data = {}

actions = {}

while True:

events = epoll.poll(24)

for fileno, event in events:

logging.debug(">>>>>" * 12)

logging.debug("Event file number is %s and event mask is %s(%s)", fileno, bin(event), eventmask_ids.get(event, 0))

if fileno == s_fileno:

# create new socket connection from client

conn, address = s.accept()

conn.setblocking(0)

c_fileno = conn.fileno()

logging.debug("Connection from client%s file number is %s", address, c_fileno)

epoll.register(c_fileno, select.EPOLLIN)

connections[c_fileno] = conn

request_data[c_fileno] = b""

response_data[c_fileno] = b""

actions[c_fileno] = []

elif event & select.EPOLLIN:

logging.info("Recive data epoll socket file number is %s, actions are: %s", fileno, actions[fileno])

actions[fileno].append("recv")

# data come in

data_piece = connections[fileno].recv(1024)

# logging.debug("Recive client data piece is:\n%s", data_piece)

request_data[fileno] += data_piece

if EOL1 in request_data[fileno] or EOL2 in request_data[fileno]:

resp = str(os.environ)

response_data[fileno] = response % (time.strftime("%a, %d %b %Y %H:%M:%S GMT", time.gmtime()), len(resp), resp)

epoll.modify(fileno, select.EPOLLOUT)

# logging.debug("Data from client is: \n%s", request_data[fileno])

if request_data[fileno] == b"":

logging.error("Recive empty data")

epoll.unregister(fileno)

connections[fileno].close()

elif event & select.EPOLLOUT:

actions[fileno].append("send")

# send data to client

# logging.warn("Full connections are %s", connections)

logging.info("Send data epoll socket file number is %s", fileno)

send_bytes = connections[fileno].send(response_data[fileno])

response_data[fileno] = response_data[fileno][send_bytes:]

if len(response_data[fileno]) == 0:

actions[fileno].append("shutdown")

epoll.modify(fileno, 0)

logging.info("I will shutdown socket(%s), actions are: %s", connections[fileno], actions[fileno])

connections[fileno].shutdown(socket.SHUT_RDWR)

del response_data[fileno]

elif event & select.EPOLLHUP:

actions[fileno].append("close")

logging.info("Close data epoll scoket file number is %s, actions are: %s", fileno, actions[fileno])

# connection close by client

epoll.unregister(fileno)

connections[fileno].close()

del connections[fileno]

del actions[fileno]

logging.debug("<<<<

finally:

logging.error("Exception happend, closing server...")

epoll.unregister(s_fileno)

epoll.close()

s.close()

运行以后可以访问,但使用压测软件测试会抛出[Errno 107] Transport endpoint is not connected这样的异常

压测命令为siege -c 100 -i -b --delay=0 --time=1s http://172.17.0.1:9999,而压测结果显示可用100%

** SIEGE 3.0.5

** Preparing 100 concurrent users for battle.

The server is now under siege...

Lifting the server siege... done.

Transactions: 868 hits

Availability: 100.00 %

Elapsed time: 0.93 secs

Data transferred: 1.49 MB

Response time: 0.09 secs

Transaction rate: 933.33 trans/sec

Throughput: 1.60 MB/sec

Concurrency: 87.33

Successful transactions: 868

Failed transactions: 0

Longest transaction: 0.12

Shortest transaction: 0.01

关于[Errno 107] Transport endpoint is not connected这个错误,应该是tcp连接并没有建立,但是,我上面的代码和日志显示连接已经建立,为什么还会抛出这个异常

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值