Reputation: 901
I'm writing a project in Python that will have two diffrent (separate) apps.
My project will do something like this:
To test the project I put the to apps on my localhost:
The project worked fine when the two apps where written thanks to Tornado framework but for personal reasons I want to make the PROXY a litte more low - level -> using sockets.
So to do this I've rewitten the Proxy app to a pure Python code and I got a little problem. The problem is that when I create a socket and I want to receive a JSON from the database API the database app gives me a 404 error (while if I access that URL on the database it works fine). I don't know what can be the problem.
My proxy class with the send_json and socket creation method:
class Proxy(object):
u"""The PROXY class."""
(...)
def get_remote_response(self, host, port, data):
u"""Method that creates a socket to the remote_address and gets the response.
:param host: remote_host,
:param port: remote_port,
:param data: data to send.
:return response: the response without the headers.
"""
response_text = ''
try:
remote_sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
print "Trying to connect to:%s : %s \n\n" % (host, port)
remote_sock.connect((host, port))
remote_sock.send(data)
remote_sock.settimeout(0.5)
while True:
try:
response = remote_sock.recv(self.buffor_size)
if len(response) == 0:
break
except socket.error:
break
response_text += response
except socket.error, msg:
print str(msg)
remote_sock.close()
response = response_text[response_text.index('\r\n\r\n') + 1:]
return response
def get_filters(self, filter_id, **kwargs):
u"""Method that gets a JSON with filters from the remote server
:param filter_id: filter id.
:return filters: list of filters from the remote server.
"""
filters = list()
remote_host = '127.0.0.1'
remote_port = 9000
request_url = 'http://%s:%s/api/send-to-world/%s/' % (remote_host, str(remote_port), filter_id)
first_line_of_request = 'GET ' + request_url + ' HTTP/1.1\r\n'
headers = {
'Host': remote_host,
'Content-Type': 'application/json',
'Accept': 'application/json'
}
request = first_line_of_request
for header in headers:
request += '%s: %s\r\n' % (header, headers[header])
request += '\r\n'
print "request:\n", request
response = self.get_remote_response(remote_host, remote_port, request)
print "response:\n", response
if response:
data = None
try:
my_json = response
data = json.loads(my_json.decode('utf-8'))
except ValueError:
message = 'Cannot parse JSON.'
# self.send_error(400, message=message)
filters = []
for one_filter in data:
filters.append((one_filter.get('filter_id'), one_filter.get('filter_name')))
return filters
The binding, listening and accepting on the PROXY is done, so I think that I don't need to upload it here. If so, just say so :)
I've leaved the prints so you can see what is going to the database app:
The request:
request: GET http://127.0.0.1:9000/api/send-to-world/2/ HTTP/1.1 Host: 127.0.0.1 Content-Type: application/json Accept: application/json
And the response:
Trying to connect to:127.0.0.1 : 9000 response: Traceback (most recent call last): File "/home/dave/.virtualenvs/teleV1/local/lib/python2.7/site-packages/tornado/web.py", line 1446, in _execute result = self.prepare() File "/home/dave/.virtualenvs/teleV1/local/lib/python2.7/site-packages/tornado/web.py", line 2174, in prepare raise HTTPError(self._status_code) HTTPError: HTTP 404: Not Found
The logs from the database app while trying to get the filters:
tornado working on port 9000 WARNING:tornado.access:404 GET http://127.0.0.1:9000/api/send-to-world/2/ (127.0.0.1) 2.75ms
While I access it via the web browser it gives me the JSON.
So to sum up: How can I receive a JSON from my database app using a socket connection? I think that if the servers work on diffrent ports then the problem shouldn't be with the host: 127.0.0.1
. If I'm wrong and I can't do some thing like this on one computer then please correct me :)
Upvotes: 0
Views: 199
Reputation: 1157
I doubt this is the problem, but you said your database app listens on port 900, yet your proxy is connecting to port 9000...
Don't include the protocol, hostname and port in the HTTP request headers, so change
request_url = 'http://%s:%s/api/send-to-world/%s/' % (remote_host, str(remote_port), filter_id)
to
request_url = '/api/send-to-world/%s/' %filter_id
For example to make your proxy fetch this article from stackoverflow.com:
remote_host = 'stackoverflow.com'
remote_port = 80
request_url = 'posts/43481916'
first_line_of_request = 'GET ' + request_url + ' HTTP/1.1\r\n'
headers = {
'Host': remote_host,
'Content-Type': 'text/html',
'Accept': 'text/html'
}
request = first_line_of_request
for header in headers:
request += '%s: %s\r\n' % (header, headers[header])
request += '\r\n'
response = self.get_remote_response(remote_host, remote_port, request)
Upvotes: 1