[记录]Python的master-worker和epoll模式
#master-worker模型:
#coding:utf-8
import os
import sys
import socket
import time
import traceback
import errno
import signal class Worker(object):
def __init__(self, sock):
self.sock = sock def accept(self):
client, addr = self.sock.accept()
client.setblocking(True)
self.handle(client, addr) def init_process(self):
self.sock.setblocking(False)
while True:
try:
time.sleep(1)
self.accept()
continue
except Exception as e:
msg = traceback.format_exc()
with open("sub_"+str(os.getpid())+".txt","a") as f:
f.write(msg+"\n")
if hasattr(e, "errno"):
if e.errno not in (errno.EAGAIN, errno.ECONNABORTED, errno.EWOULDBLOCK):
msg = traceback.format_exc()
else:
raise def handle(self, client, addr):
data = client.recv(1024)
pid = os.getpid()
data += str(pid)
# print("receive:{} pid:{}".format(data, pid))
client.send("back:"+data)
client.close() class Server(object):
def __init__(self):
self.port = ("127.0.0.1", 8004)
self.sock = socket.socket()
self.sock.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
self.sock.bind(self.port)
self.sock.setblocking(False)
self.sock.listen(5)
self.WORKERS = {} def run(self):
self.init_signals()
for i in range(2):
self.spawn_worker()
print(i)
# self.spawn_worker()
for k in self.WORKERS:
print(k, self.WORKERS[k])
while True:
import time
time.sleep(3)
try:
pid, status = os.waitpid(-1, os.WNOHANG)
print("kill pid: {}, status: {}".format(pid, status))
except os.error:
print("error") def init_signals(self):
signal.signal(signal.SIGTTIN, self.incr_one)
signal.signal(signal.SIGTTOU, self.decr_one) def incr_one(self, signo, frame):
self.spawn_worker()
for k in self.WORKERS:
print(k, self.WORKERS[k]) def decr_one(self, signo, frame):
for k in self.WORKERS:
os.kill(k, signal.SIGKILL)
break def spawn_worker(self):
worker = Worker(self.sock) pid = os.fork()
if pid != 0:
worker.pid = pid
self.WORKERS[pid] = worker
return pid worker.pid = os.getpid()
worker.init_process()
sys.exit(0) if __name__ == "__main__":
server = Server()
server.run() =======================================================================
epoll模型:
server:
#-*- coding:utf8 -*-
import socket
import select
import os address = "0.0.0.0"
port = 10001
sock = socket.socket(socket.AF_INET,socket.SOCK_STREAM) def main():
global address,port,sock
epoll = select.epoll()
#获取创建好的sock的文件描述符
fd = sock.fileno()
sock.bind((address,port))
sock_dict = {}
sock_dict[fd] = sock
#对该sock进行注册
epoll.register(fd,select.EPOLLIN)
sock.listen(5)
while True:
events = epoll.poll(1)
for fileno,event in events:
#获取到的文件描述符和sock的相同就说明是一个新的连接
if fileno == fd:
(client,address) = sock.accept()
print address
client.setblocking(0)
#将新的连接进行注册,用来接收消息
epoll.register(client.fileno(),select.EPOLLIN)
sock_dict[client.fileno()] = client
elif event & select.EPOLLIN:
print "fileno:",fileno
data = sock_dict[fileno].recv(128)
if data == '你好':
print "Data:",data.decode('UTF-8')
sock_dict[fileno].send("你好")
elif len(data) == 0:
print "线路%d已下线"%fileno
epoll.unregister(fileno)
else:
print "Data:",data
if __name__ == '__main__':
main() client:
#coding: UTF-8 import socket
import select address = "127.0.0.1"
port = 10001
sock = socket.socket(socket.AF_INET,socket.SOCK_STREAM) def main():
global address,port,sock
sock.connect((address,port))
epoll = select.epoll()
fd = sock.fileno()
#这里的epoll注册只是用来异步接收服务端发过来的消息
epoll.register(fd,select.EPOLLIN)
while True:
events = epoll.poll(1)
for fileno,event in events:
if fileno == fd:
if event & select.EPOLLIN:
data = sock.recv(128)
print data
data = raw_input(">")
if data == 'q':
break
elif data == '':
print "不能发送空消息"
continue
sock.send(data)
sock.close()
main()
[记录]Python的master-worker和epoll模式的更多相关文章
- 记录Python学习中的几个小问题
记录Python学习中的几个小问题,和C#\JAVA的习惯都不太一样. 1.Django模板中比较两个值是否相等 错误的做法 <option value="{{group.id}}&q ...
- Python进阶:设计模式之迭代器模式
在软件开发领域中,人们经常会用到这一个概念——“设计模式”(design pattern),它是一种针对软件设计的共性问题而提出的解决方案.在一本圣经级的书籍<设计模式:可复用面向对象软件的基础 ...
- python celery多worker、多队列、定时任务
python celery多worker.多队列.定时任务
- python中文件操作的六种模式及对文件某一行进行修改的方法
一.python中文件操作的六种模式分为:r,w,a,r+,w+,a+ r叫做只读模式,只可以读取,不可以写入 w叫做写入模式,只可以写入,不可以读取 a叫做追加写入模式,只可以在末尾追加内容,不可以 ...
- python打开文件可以有多种模式
一.python打开文件可以有多种模式,读模式.写模式.追加模式,同时读写的模式等等,这里主要介绍同时进行读写的模式r+ python通过open方法打开文件 file_handler = open( ...
- 应对百万访问量的epoll模式
写在前面 select/poll与epoll select/poll模型工作机理 select/poll模型的局限 epoll模型工作机理 epoll的局限 golang中的epoll golang源 ...
- python设计模式之模型-视图-控制器模式
python设计模式之模型-视图-控制器模式 关注点分离( Separation of Concerns, SoC)原则是软件工程相关的设计原则之一. SoC原则背后的思想是将一个应用切分成不同的部分 ...
- 使用配置文件方式记录Python程序日志
开发者可以通过三种方式配置日志记录: 调用配置方法的Python代码显式创建记录器.处理程序和格式化程序. 创建日志配置文件并使用fileConfig() 函数读取. 创建配置信息字典并将其传递给di ...
- Beats:使用 Elastic Stack 记录 Python 应用日志
文章转载自:https://elasticstack.blog.csdn.net/article/details/112259500 日志记录实际上是每个应用程序都必须具备的功能.无论你选择基于哪种技 ...
随机推荐
- 深度网络中的Tricks
数据增强(Data augmentation) 预处理(Pre-processing) 初始化(Initializations) 训练中的Tricks 激活函数(Activation function ...
- CUDA配置
你问这个有多恶心,是真的很恶心!!! 首先推出一个博客上的内容,里面内容很不错,都是前车之鉴,很有用.http://blog.csdn.net/masa_fish/article/details/51 ...
- web开发常用正则表达式
整数或者小数:^[0-9]+\.{0,1}[0-9]{0,2}$只能输入数字:"^[0-9]*$".只能输入n位的数字:"^\d{n}$".只能输入至少n位的数 ...
- 孟岩:技术路线的选择重要但不具有决定性(什么是核心竞争力?是你独特的个性知识经验组合,正确的态度应该是着重于你要干的事情,然后认真把这件事情做好,然后融会贯通)good
转自 http://blog.csdn.net/myan/article/details/3247071 孟岩 2008 年的文章,现在看来还是挺有启发, 送给大家,也送给自己. 最近微软在技术上 ...
- [2017.02.23] Java8 函数式编程
以前学过Haskell,前几天又复习了其中的部分内容. 函数式编程与命令式编程有着不一样的地方,函数式编程中函数是第一等公民,通过使用少量的几个数据结构如list.map.set,以及在这些数据结构上 ...
- Ionic Framework 4 介绍
Ionic Framework 4是一个开源UI工具包,用于使用Web技术(HTML,CSS和JavaScript)构建高性能的高质量移动和桌面应用程序.Ionic Framework专注于前端用户体 ...
- HBase 学习之路(二)—— HBase系统架构及数据结构
一.基本概念 一个典型的Hbase Table 表如下: 1.1 Row Key (行键) Row Key是用来检索记录的主键.想要访问HBase Table中的数据,只有以下三种方式: 通过指定的R ...
- js 数组去重方法
var arr = ['a',1,2,3,'a',4,2,3,1,4,2,8,10,null,'a']; // 方法一 var newArr = [...new Set(arr)]; console. ...
- JAVA复习笔记02
16.interface中的成员变量默认为public static final类型,方法只能是public(默认为public) 17.内部类访问外部类成员: Outer.this.num; 18. ...
- Java多线程(三):volatile
volatile volatile是一种轻量同步机制.请看例子 MyThread25类 public class MyThread25 extends Thread{ private boolean ...