[PATCH 1 of 6] socketserver: backport a less sucky socketserver from python 3.5.1
Jun Wu
quark at fb.com
Thu May 12 19:12:54 EDT 2016
On 05/12/2016 10:47 PM, Jun Wu wrote:
> On 05/12/2016 12:02 AM, Yuya Nishihara wrote:
>>> I think SocketServer won't make that harder, is it?
>>
>> Yeah, I guess it will be harder to write a PreForkingMixIn since IMHO
>> pre-forking works very differently from fork-per-request or
>> thread-per-request.
>>
>> That's why I don't care for the SocketServer compatibility.
>
> I tried to implement the preforking model in a quick and dirty way, and got this:
>
> https://gist.github.com/quark-zju/015c448b548bc6fbad4105868e2028ac
>
> which does not look bad and socketserver does save a lot lines here.
> Most of the lines are necessary to implement a preforked server anyway.
>
> (I haven't tried to convert them into MixIns but it's at least possible
> for the master).
The MixIn version is 34 lines (and I have updated the gist):
class PreforkMixIn:
max_nchildren = 3
children = None
def spawn_workers_forever(self, interval=0.5):
if self.children is None:
self.children = set()
while not os.path.exists('/tmp/exit'):
self.create_workers()
self.reap_workers()
time.sleep(interval)
def create_workers(self, interval=0.5):
while len(self.children) < self.max_nchildren:
pid = os.fork()
assert pid >= 0
if pid == 0:
try:
self.serve_forever()
finally:
sys.exit(0)
else:
self.children.add(pid)
time.sleep(interval)
def reap_workers(self):
for pid in self.children.copy():
try:
pid, _ = os.waitpid(pid, os.WNOHANG)
self.children.discard(pid)
except ChildProcessError:
self.children.discard(pid)
except OSError:
pass
To use it:
class echohandler(socketserver.StreamRequestHandler):
def handle(self):
while 1:
data = self.rfile.read(1)
if not data:
break
self.wfile.write(data)
class myserver(PreforkMixIn, socketserver.UnixStreamServer):
pass
myserver('/tmp/server', echohandler).spawn_workers_forever()
Pretty neat, isn't it?
More information about the Mercurial-devel
mailing list