I built a reverse proxy to handle requests from my frontend and redirect them to backend microservices based on an appended string in the URL. It works when I run the app normally in vs code on localhost (the frontend microservice can send the request to the reverse proxy, which forwards it to the backend and returns the response to the frontend), but won't work when I build a docker image from it and run it. I'm really stumped. I'm inclined to think the problem lies with the Dockerfile but honestly I am not sure.
from flask import request
from flask import Response
from flask import Flask
from flask_cors import CORS
import requests
app = Flask(__name__)
CORS(app)
app.config['CORS_HEADERS'] = 'Content-Type'
#App settings ---
SITE_NAME_1 = 'http://localhost:90/'
APP_NAME_1 = 'maxmin'
SITE_NAME_2 = 'http://localhost:100/'
APP_NAME_2 = 'sort'
@app.route('/',methods=['GET','POST'])
def proxy():
input_text = request.args.get('input_text')
global SITE_NAME_1
global APP_NAME_1
global SITE_NAME_2
global APP_NAME_2
SITE_NAME = ''
APP_NAME = ''
# Deciding between the apps..
if input_text.split('-')[1] == 'maxmin':
SITE_NAME = SITE_NAME_1
APP_NAME = APP_NAME_1
elif input_text.split('-')[1] == 'sort':
SITE_NAME = SITE_NAME_2
APP_NAME = APP_NAME_2
input_text = input_text.split('-')[0]
# sending request to backend and awaiting response
if request.method=='GET':
args = {'input_text': input_text}
url = SITE_NAME
resp = requests.get(url, params=args)
# resp = requests.get(f'{SITE_NAME}{APP_NAME}', params=args)
excluded_headers = ['content-encoding', 'content-length', 'transfer-encoding', 'connection']
headers = [(name, value) for (name, value) in resp.raw.headers.items() if name.lower() not in excluded_headers]
response = Response(resp.content, resp.status_code, headers)
return response
if __name__ == '__main__':
app.run(host="0.0.0.0", port=5000)
# app.run(host="localhost",port=5000)
Dockerfile: (tried two different ones, hence why one half is commented out)
# FROM python:3.6.1-alpine
# WORKDIR /app
# ADD . /app
# RUN pip install --upgrade pip
# RUN pip install -r requirements.txt
# EXPOSE 5003
# ENTRYPOINT ["python3"]
# CMD ["src/proxy.py"]
FROM ubuntu:18.04
RUN apt-get update -y && apt-get install -y python3-pip python3
COPY ./requirements.txt /app/requirements.txt
WORKDIR /app
RUN pip3 install -r requirements.txt
COPY ./src /app
EXPOSE 5000
ENTRYPOINT ["python3"]
CMD ["proxy.py"]
Error Log:
[2022-08-22 01:07:36,878] ERROR in app: Exception on / [GET]
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connection.py", line 137, in _new_conn
(self.host, self.port), self.timeout, **extra_kw)
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/util/connection.py", line 91, in create_connection
raise err
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/util/connection.py", line 81, in create_connection
sock.connect(sa)
OSError: [Errno 99] Cannot assign requested address
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connectionpool.py", line 559, in urlopen
body=body, headers=headers)
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connectionpool.py", line 353, in _make_request
conn.request(method, url, **httplib_request_kw)
File "/usr/lib/python3.6/http/client.py", line 1285, in request
self._send_request(method, url, body, headers, encode_chunked)
File "/usr/lib/python3.6/http/client.py", line 1331, in _send_request
self.endheaders(body, encode_chunked=encode_chunked)
File "/usr/lib/python3.6/http/client.py", line 1280, in endheaders
self._send_output(message_body, encode_chunked=encode_chunked)
File "/usr/lib/python3.6/http/client.py", line 1046, in _send_output
self.send(msg)
File "/usr/lib/python3.6/http/client.py", line 984, in send
self.connect()
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connection.py", line 162, in connect
conn = self._new_conn()
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connection.py", line 146, in _new_conn
self, "Failed to establish a new connection: %s" % e)
requests.packages.urllib3.exceptions.NewConnectionError: <requests.packages.urllib3.connection.HTTPConnection object at 0x7f6346cec128>: Failed to establish a new connection: [Errno 99] Cannot assign requested address
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/requests/adapters.py", line 376, in send
timeout=timeout
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connectionpool.py", line 609, in urlopen
_stacktrace=sys.exc_info()[2])
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/util/retry.py", line 273, in increment
raise MaxRetryError(_pool, url, error or ResponseError(cause))
requests.packages.urllib3.exceptions.MaxRetryError: HTTPConnectionPool(host='localhost', port=90): Max retries exceeded with url: /?input_text=DB%2C70newlinePG%2C90 (Caused by NewConnectionError('<requests.packages.urllib3.connection.HTTPConnection object at 0x7f6346cec128>: Failed to establish a new connection: [Errno 99] Cannot assign requested address',))
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1982, in wsgi_app
response = self.full_dispatch_request()
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1614, in full_dispatch_request
rv = self.handle_user_exception(e)
File "/usr/local/lib/python3.6/dist-packages/flask_cors/extension.py", line 161, in wrapped_function
return cors_after_request(app.make_response(f(*args, **kwargs)))
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1517, in handle_user_exception
reraise(exc_type, exc_value, tb)
File "/usr/local/lib/python3.6/dist-packages/flask/_compat.py", line 33, in reraise
raise value
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1612, in full_dispatch_request
rv = self.dispatch_request()
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1598, in dispatch_request
return self.view_functions[rule.endpoint](**req.view_args)
File "proxy.py", line 41, in proxy
resp = requests.get(url, params=args)
File "/usr/local/lib/python3.6/dist-packages/requests/api.py", line 67, in get
return request('get', url, params=params, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/api.py", line 53, in request
return session.request(method=method, url=url, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/sessions.py", line 468, in request
resp = self.send(prep, **send_kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/sessions.py", line 576, in send
r = adapter.send(request, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/adapters.py", line 437, in send
raise ConnectionError(e, request=request)
requests.exceptions.ConnectionError: HTTPConnectionPool(host='localhost', port=90): Max retries exceeded with url: /?input_text=DB%2C70newlinePG%2C90 (Caused by NewConnectionError('<requests.packages.urllib3.connection.HTTPConnection object at 0x7f6346cec128>: Failed to establish a new connection: [Errno 99] Cannot assign requested address',))
172.17.0.1 - - [22/Aug/2022 01:07:36] "GET /?input_text=DB,70newlinePG,90-maxmin HTTP/1.1" 500 -
[2022-08-22 01:07:36,878] ERROR in app: Exception on / [GET]
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connection.py", line 137, in _new_conn
(self.host, self.port), self.timeout, **extra_kw)
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/util/connection.py", line 91, in create_connection
raise err
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/util/connection.py", line 81, in create_connection
sock.connect(sa)
OSError: [Errno 99] Cannot assign requested address
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connectionpool.py", line 559, in urlopen
body=body, headers=headers)
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connectionpool.py", line 353, in _make_request
conn.request(method, url, **httplib_request_kw)
File "/usr/lib/python3.6/http/client.py", line 1285, in request
self._send_request(method, url, body, headers, encode_chunked)
File "/usr/lib/python3.6/http/client.py", line 1331, in _send_request
self.endheaders(body, encode_chunked=encode_chunked)
File "/usr/lib/python3.6/http/client.py", line 1280, in endheaders
self._send_output(message_body, encode_chunked=encode_chunked)
File "/usr/lib/python3.6/http/client.py", line 1046, in _send_output
self.send(msg)
File "/usr/lib/python3.6/http/client.py", line 984, in send
self.connect()
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connection.py", line 162, in connect
conn = self._new_conn()
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connection.py", line 146, in _new_conn
self, "Failed to establish a new connection: %s" % e)
requests.packages.urllib3.exceptions.NewConnectionError: <requests.packages.urllib3.connection.HTTPConnection object at 0x7f6346cec128>: Failed to establish a new connection: [Errno 99] Cannot assign requested address
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/requests/adapters.py", line 376, in send
timeout=timeout
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/connectionpool.py", line 609, in urlopen
_stacktrace=sys.exc_info()[2])
File "/usr/local/lib/python3.6/dist-packages/requests/packages/urllib3/util/retry.py", line 273, in increment
raise MaxRetryError(_pool, url, error or ResponseError(cause))
requests.packages.urllib3.exceptions.MaxRetryError: HTTPConnectionPool(host='localhost', port=90): Max retries exceeded with url: /?input_text=DB%2C70newlinePG%2C90 (Caused by NewConnectionError('<requests.packages.urllib3.connection.HTTPConnection object at 0x7f6346cec128>: Failed to establish a new connection: [Errno 99] Cannot assign requested address',))
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1982, in wsgi_app
response = self.full_dispatch_request()
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1614, in full_dispatch_request
rv = self.handle_user_exception(e)
File "/usr/local/lib/python3.6/dist-packages/flask_cors/extension.py", line 161, in wrapped_function
return cors_after_request(app.make_response(f(*args, **kwargs)))
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1517, in handle_user_exception
reraise(exc_type, exc_value, tb)
File "/usr/local/lib/python3.6/dist-packages/flask/_compat.py", line 33, in reraise
raise value
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1612, in full_dispatch_request
rv = self.dispatch_request()
File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1598, in dispatch_request
return self.view_functions[rule.endpoint](**req.view_args)
File "proxy.py", line 41, in proxy
resp = requests.get(url, params=args)
File "/usr/local/lib/python3.6/dist-packages/requests/api.py", line 67, in get
return request('get', url, params=params, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/api.py", line 53, in request
return session.request(method=method, url=url, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/sessions.py", line 468, in request
resp = self.send(prep, **send_kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/sessions.py", line 576, in send
r = adapter.send(request, **kwargs)
File "/usr/local/lib/python3.6/dist-packages/requests/adapters.py", line 437, in send
raise ConnectionError(e, request=request)
requests.exceptions.ConnectionError: HTTPConnectionPool(host='localhost', port=90): Max retries exceeded with url: /?input_text=DB%2C70newlinePG%2C90 (Caused by NewConnectionError('<requests.packages.urllib3.connection.HTTPConnection object at 0x7f6346cec128>: Failed to establish a new connection: [Errno 99] Cannot assign requested address',))
172.17.0.1 - - [22/Aug/2022 01:07:36] "GET /?input_text=DB,70newlinePG,90-maxmin HTTP/1.1" 500 -
A little more contextual info. I am using port mapping from the host to the containers. The frontend was able to seamlessly send the requests directly to the backend(s) and receive the responses. It was also able to route the request through this proxy router (when it was running locally, uncontainerized) and receive the responses. The backend service in question sits on localhost 90 and maps to container port 80. The run commands I used are:
docker run -d --name=fronend-app -p 80:80 frontend-image
docker run -d --name=back-app-1 -p 90:80 backend-image-1
docker run -d --name=back-app-2 -p 100:80 backend-image-2
docker run -d --name=proxy-app -p 5000:5000 proxy-image
Does this shed any more light?
Sorry for the long post, wanted to get everything in. Grateful for any assistance.