How to accept and handle incoming calls - python

I was able to start up a simple python server from here
import SimpleHTTPServer
import SocketServer
PORT = 8000
Handler = SimpleHTTPServer.SimpleHTTPRequestHandler
httpd = SocketServer.TCPServer(("", PORT), Handler)
print "serving at port", PORT
httpd.serve_forever()
I was able to use a curl command and see that it does respond with a listing of my directory. I was able to see a 200 GET message pop up on my running server, but no other information. However, is there a way of actually seeing the data in the request come in on the server and parsing it? If someone was to post some information to my server (say in JSON format), how can I actually see all this data.. or even an URL?
Are there any examples which actually build on the above code which show how to handle data coming in? A use case would be someone posting information to the server.

When a GET request comes in (as is sent to your server by curl), SimpleHTTPRequestHandler.do_GET is called behind the scenes. SimpleHTTPRequestHandler is itself a subclass of BaseHTTPRequestHandler.
You can define your own subclass of SimpleHTTPRequestHandler:
class MyHandler(SimpleHTTPServer.SimpleHTTPRequestHandler):
def do_GET():
# your code here
super(MyHandler, self).do_GET()
httpd = SocketServer.TCPServer(("", PORT), MyHandler)
In place of # your code here, you can inspect properties defined by BaseHTTPRequestHandler e.g. self.path and print them or do whatever you want with them.

Related

307 Redirect to save HTTP method changes method to GET unexpectedly

Hey guys I tried to implement a POST based redirect with 307 or 308 status codes, as written in the RFC it should save the HTTP Method and body. Although, it does change the HTTP method to GET instead of the desired POST request.
I tried to use python simplehttpserver and also flask. This is my code (the programming language does not matter to me, I just need it to work):
import SocketServer
class myHandler(SimpleHTTPServer.SimpleHTTPRequestHandler):
def do_POST(self):
self.redirect()
def redirect(self):
self.send_response(307)
self.send_header('Location','http://www.example.com')
self.end_headers()
PORT = 8000
handler = SocketServer.TCPServer(("", PORT), myHandler)
print ( "serving at port " + str(PORT) )
handler.serve_forever()
Thank you so much in advance!!

I'm using http.server with python3 and I want to store a request as a variable

I have this code
httpd = HTTPServer(('127.0.0.1', 8000),SimpleHTTPRequestHandler)
httpd.handle_request()
httpd.handle_request() serves one request and then kills the server like intended. I want to capture this request as a variable so I can parse it later on.
Something like
Request_Variable = httpd.handle_request()
*This code above doesn't work. But I'm looking for something similar
Thanks
You could extend the BaseHTTPRequestHandler and implement your own do_GET (resp. do_POST) method which is called when the server receives a GET (resp. POST) request.
Check out the documentation to see what instance variables a BaseHTTPRequestHandler object you can use. The variables path, headers, rfile and wfile may be of your interest.
from http.server import BaseHTTPRequestHandler, HTTPServer
class MyRequestHandler(BaseHTTPRequestHandler):
def do_GET(self):
print(self.path)
def do_POST(self):
content_length = int(self.headers.get('Content-Length'))
print(self.rfile.read(content_length))
httpd = HTTPServer(('127.0.0.1', 8000), MyRequestHandler)
httpd.handle_request()
# make your GET/POST request

How to get client IP from SimpleHTTPServer

Building a simple file server using the SimpleHTTPServer module in Python, however I'm running into issues when trying to get the IP from a connecting client. Here is what I have..
import SimpleHTTPServer
Handler = SimpleHTTPServer.SimpleHTTPRequestHandler
httpd = SocketServer.TCPServer(("", 8080), Handler)
print "Serving local directory"
while True:
httpd.handle_request()
print Handler.client_address[0]
When a client connects I get..
AttributeError: class SimpleHTTPRequestHandler has no attribute 'client_address'
I know this is because I haven't instantiated the class yet, but is there another way to get the IP from the client without having to create a handler instance? The client's IP is outputted to the console when a connection is made, I just need a way to grab that IP within my script.
Thanks!
Indeed, the Handler class object is unrelated to specific instances. Set up your own handler class, like this:
import SimpleHTTPServer
import SocketServer
class MyHandler(SimpleHTTPServer.SimpleHTTPRequestHandler):
def handle_one_request(self):
print(self.client_address[0])
return SimpleHTTPServer.SimpleHTTPRequestHandler.handle_one_request(self)
print("Serving local directory")
httpd = SocketServer.TCPServer(("", 8080), MyHandler)
while True:
httpd.handle_request()

How to send URL back as reply by web server in python

I have written this HTTP web server in python which simply sends reply "Website Coming Soon!" to the browser/client, but I want that this web server should sends back the URL given by the client, like if I write
http://localhost:13555/ChessBoard_x16_y16.bmp
then server should reply back the same url instead of "Website Coming Soon!" message.
please tell how can I do this?
Server Code:
import sys
import http.server
from http.server import HTTPServer
from http.server import SimpleHTTPRequestHandler
#import usb.core
class MyHandler(SimpleHTTPRequestHandler): #handles client requests (by me)
#def init(self,req,client_addr,server):
# SimpleHTTPRequestHandler.__init__(self,req,client_addr,server)
def do_GET(self):
response="Website Coming Soon!"
self.send_response(200)
self.send_header("Content-type", "application/json;charset=utf-8")
self.send_header("Content-length", len(response))
self.end_headers()
self.wfile.write(response.encode("utf-8"))
self.wfile.flush()
print(response)
HandlerClass = MyHandler
Protocol = "HTTP/1.1"
port = 13555
server_address = ('localhost', port)
HandlerClass.protocol_version = Protocol
try:
httpd = HTTPServer(server_address, MyHandler)
print ("Server Started")
httpd.serve_forever()
except:
print('Shutting down server due to some problems!')
httpd.socket.close()
You can do what you're asking, sort of, but it's a little complicated.
When a client (e.g., a web browser) connects to your web server, it sends a request that look like this:
GET /ChessBoard_x16_y16.bmp HTTP/1.1
Host: localhost:13555
This assumes your client is using HTTP/1.1, which is likely true of anything you'll find these days. If you expect HTTP/1.0 or earlier clients, life is much more difficult because there is no Host: header.
Using the value of the Host header and the path passed as an argument to the GET request, you can construct a URL that in many cases will match the URL the client was using.
But it won't necessarily match in all cases:
There may be a proxy in between the client and your server, in which case both the path and hostname/port seen by your code may be different from that used by the client.
There may be packet manipulation rules in place that modify the destination ip address and/or port, so that the connection seen by your code does not match the parameters used by the client.
In your do_GET method, you can access request headers via the
self.headers attribute and the request path via self.path. For example:
def do_GET(self):
response='http://%s/%s' % (self.headers['host'],
self.path)

How to send an html string from a python http web server?

I found a python http web server from http://www.linuxjournal.com/content/tech-tip-really-simple-http-server-python
import sys
import BaseHTTPServer
from SimpleHTTPServer import SimpleHTTPRequestHandler
HandlerClass = SimpleHTTPRequestHandler
ServerClass = BaseHTTPServer.HTTPServer
Protocol = "HTTP/1.0"
if sys.argv[1:]:
port = int(sys.argv[1])
else:
port = 8000
server_address = ('127.0.0.1', port)
HandlerClass.protocol_version = Protocol
httpd = ServerClass(server_address, HandlerClass)
sa = httpd.socket.getsockname()
print "Serving HTTP on", sa[0], "port", sa[1], "..."
httpd.serve_forever()
If the directory has a file named index.html, that file will be served as the initial file. If there is no index.html, then the files in the directory will be listed.
How do I modify the script so that I send a custom html to the browser?
As the name and documentation imply, SimpleHTTPServer is dead-simple, and intended to be used as sample code for building your own servers on top of the frameworks in the standard library.
So, if you want to do anything with it, you probably want to copy and modify the source, or just use it as inspiration.
And if you want to do anything serious, you probably want to use a framework made for writing real HTTP servers like tornado or twisted, or just use a stock HTTP server and delegate the dynamic pages to Python via, say, WSGI.
But if you really want to do this, you can. There's nothing stopping you from subclassing SimpleHTTPServer.SimpleHTTPRequestHandler and overriding its methods. For example:
class MyHandler(SimpleHTTPRequestHandler):
def send_head(self):
if self.translate_path(self.path).endswith('/foo'):
body = gaping_security_hole(self.path)
self.send_response(200)
self.send_header("Content-type", "text/html; charset=utf-8")
self.send_header("Content-Length", str(len(body)))
self.end_headers()
return StringIO(body)
else:
return super(MyHandler, self).send_head()
Obviously you can check whatever you want there instead of endswith('/foo'). For example, as you can see from the source, the default implementation checks os.path.isdir, and if it's true checks whether it endswith('/'), and whether the directory has anything named index.html or index.htm, before deciding what to do.

Categories

Resources