473,406 Members | 2,377 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,406 software developers and data experts.

Code feedback

Hi, all I would like some feedback on a multithreaded HTTP server I've
written. The server serves python-scripts by dynamically loading scripts
in the same directory as itself. When a request is made to one of these
scripts the script is executed and its output is returned to the
requester.

Here is the server code, HTTPServer.py:

# Basic, threaded HTTP server, serving requests via python scripts
# Author: Tor Erik Soenvisen

# Std lib imports
import BaseHTTPServer, os, threading, Queue

class HTTPServer(BaseHTTPServer.HTTPServer):
""" A threaded HTTP server """

port = 80
# Maximum requests on hold
request_queue_size = 250
# Maximum requests serviced concurrently
workers = 20

def __init__(self, port=None, reqSize=None, workers=None):

if port is not None: self.port = port
if reqSize is not None: self.request_queue_size = reqSize
if workers is not None: self.workers = workers

self.sharedPath = os.path.dirname(os.path.abspath(__file__))
# self.sharedPath must be set before calling self.getHandlers
self.handler = self.getHandlers()
self.jobQueue = Queue.Queue(self.request_queue_size)
addr = ('', self.port)
BaseHTTPServer.HTTPServer.__init__(self, addr,
HTTPRequestHandler)

# Exit threads when application exits
self.daemon_threads = True

self.createThreadPool()
self.serve_forever()

def getHandlers(self):
""" Imports all python scripts in the current directory except
this one.
These scripts are the response generators corresponding to
all valid
path requests. The idea is to comprise something similar to
a
lightweight CGI, where each script generate HTTP responses
to HTTP requests
"""
import inspect
# 1. List all files in current directory
# 2. Skip files not having a .py extension, in addition to this
file
# 3. Slice of .py extension
handler = dict.fromkeys([x[:-3] for x in os.listdir
(self.sharedPath) \
if x.endswith('.py') and \
x != os.path.basename(__file__)])
for name in handler:
handler[name] = __import__(name)
# Make sure the handler contains a run function accepting at
least
# one parameter
if not hasattr(handler[name], 'run') or \
len(inspect.getargspec(handler[name].run)[0]) != 2:
print 'Handler %s.py dropped because it lacks ' % name +
\
'a function named run accepting two arguments'
del handler[name]

return handler

def createThreadPool(self):
""" Creates pool of worker threads, servicing requests """
self.tpool = []
for i in range(self.workers):
self.tpool.append(threading.Thread
(target=self.process_request_thread,
args=()))
if self.daemon_threads:
self.tpool[-1].setDaemon(1)
self.tpool[-1].start()

def serve_forever(self):
""" Handle requests "forever" """
while 1:
self.handle_request()

def process_request(self, request, client_address):
""" Task source: dispath requests to job queue """
self.jobQueue.put((request, client_address))

def process_request_thread(self):
""" Task sink: process requests from job queue """
while 1:
request, client_address = self.jobQueue.get()
try:
self.finish_request(request, client_address)
self.close_request(request)
except:
self.handle_error(request, client_address)
self.close_request(request)

class HTTPRequestHandler(BaseHTTPServer.BaseHTTPRequestH andler):
""" Handles HTTP requests. GET is the only method currently
supported """

# Set HTTP protocol version 1.1
protocol_version = 'HTTP/1.1'
# Set default response headers
responseHeaders = {'Content-Type': 'text/html',
'Content-Length': '',
'Connection': 'close'}

def log_message(self, format, *args):
""" Log function: see BaseHTTPServer.py for info on arguments
"""
pass

def do_GET(self):
""" Handles HTTP GET requests """

name = self.path.lstrip('/')
try:
handler = self.server.handler[name].run
except KeyError:
self.send_error(code=404, message='File %s not found' %
name)
else:
data = handler(self.headers, self.responseHeaders)
# Set Content-Length header
self.responseHeaders['Content-Length'] = str(len(data))
# Send headers and content
self.send_response(200, message='OK')
for name, value in self.responseHeaders.items():
self.send_header(name, value)
self.end_headers()
self.wfile.write(data)

if __name__ == '__main__':
""" For testing purposes """
HTTPServer(port=8081)
Pointing the browser to http://localhost:8081/index yields Hello, world!
when the script index.py is contained in the same directory as the
server.

index.py:

def run(request, response):
""" Entrypoint function, called by web-server
Argument request is the request headers as a mimetools.Message
instance, while response is a dictionary containing the default
response headers.
"""
html = '<html><head><title></title></head><body>Hello, world!</body>
</html>'
return html

Suggestions for making the server faster, more secure, more general,
and/or more compact will be appreciated.

Regards, Tor Erik

PS: Yes, I know there exist heaps of web-servers out there.
Nov 17 '06 #1
0 1108

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

0
by: Dafella | last post by:
The following is code from Xeoport. It is suppose to access my pop3 account and load email into Mysql database. It's not inserting and there is no log or anything to tell me why. Here is the...
26
by: Michael Strorm | last post by:
Hi! I posted a message a while back asking for project suggestions, and decided to go with the idea of creating an adventure game (although it was never intended to be a 'proper' game, rather an...
2
by: Sergio del Amo | last post by:
Hi, I wrote some functionality for a Web Page with Javascript. My code works perfectly for Firefox but not for IE. I become some errors apparently all based in the same problem wich scapes to my...
2
by: Kavitha Rao | last post by:
Hi, I am getting the following errors while trying to run this snippet in Microsoft Visual C++.Can't seem to print the crc value stored. /* +++Date last modified: 05-Jul-1997 */ /* Crc - 32...
192
by: Vortex Soft | last post by:
http://www.junglecreatures.com/ Try it and tell me what's happenning in the Microsoft Corporation. Notes: VB, C# are CLS compliant
1
by: Terry Olsen | last post by:
No offense to anyone in this group, particularly Tom Shelton, Michael M, or Newbie Coder. But who the hell is Crouchie1998 and why is he accusing every submission I make to Planet Source Code to be...
2
by: DrNoose | last post by:
Hi! I'm working on code for a feedback form. I want the data from the user that is taken from the form to be emailed back to me. I'm using vb with visual studios 2005. I have most of the...
9
by: gs | last post by:
the feedback for the install of c#2008 places 97 to 99% cpu load for way too long on athlon x64 3800+ PC. 3/4 an hour later its only about 80% complete, continuing with 98% CPU load! Next time...
27
by: George2 | last post by:
Hello everyone, Should I delete memory pointed by pointer a if there is bad_alloc when allocating memory in memory pointed by pointer b? I am not sure whether there will be memory leak if I do...
8
by: Brian | last post by:
What's the best way to debug code that is being run during garbage collection? We are getting AccessViolationExceptions that seem to be happening during garbage collection. But when it hits the...
0
BarryA
by: BarryA | last post by:
What are the essential steps and strategies outlined in the Data Structures and Algorithms (DSA) roadmap for aspiring data scientists? How can individuals effectively utilize this roadmap to progress...
1
by: nemocccc | last post by:
hello, everyone, I want to develop a software for my android phone for daily needs, any suggestions?
1
by: Sonnysonu | last post by:
This is the data of csv file 1 2 3 1 2 3 1 2 3 1 2 3 2 3 2 3 3 the lengths should be different i have to store the data by column-wise with in the specific length. suppose the i have to...
0
by: Hystou | last post by:
Most computers default to English, but sometimes we require a different language, especially when relocating. Forgot to request a specific language before your computer shipped? No problem! You can...
0
Oralloy
by: Oralloy | last post by:
Hello folks, I am unable to find appropriate documentation on the type promotion of bit-fields when using the generalised comparison operator "<=>". The problem is that using the GNU compilers,...
0
jinu1996
by: jinu1996 | last post by:
In today's digital age, having a compelling online presence is paramount for businesses aiming to thrive in a competitive landscape. At the heart of this digital strategy lies an intricately woven...
0
tracyyun
by: tracyyun | last post by:
Dear forum friends, With the development of smart home technology, a variety of wireless communication protocols have appeared on the market, such as Zigbee, Z-Wave, Wi-Fi, Bluetooth, etc. Each...
0
agi2029
by: agi2029 | last post by:
Let's talk about the concept of autonomous AI software engineers and no-code agents. These AIs are designed to manage the entire lifecycle of a software development project—planning, coding, testing,...
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 1 May 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome a new...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.