2

Summary

I have a flask application deployed to Kubernetes with python 2.7.12, Flask 0.12.2 and using requests library. I'm getting a SSLError while using requests.session to send a POST Request inside the container. When using requests sessions to connect to a https url , requests throws a SSLError

Some background

  • I have not added any certificates
  • The project works when I run a docker image locally but after deployment to kubernetes, from inside the container - the post request is not being sent to the url verify=false does not work either

System Info - What I am using: Python 2.7.12, Flask==0.12.2, Kubernetes, python-requests-2.18.4

Expected Result

Get HTTP Response code 200 after sending a POST request

Error Logs

r = adapter.send(request, **kwargs)
File "/usr/local/lib/python2.7/site-packages/requests/adapters.py", line 511, in send
raise SSLError(e, request=request)
SSLError: HTTPSConnectionPool(host='dev.domain.nl', port=443): Max retries exceeded with url: /ingestion?LrnDevEui=0059AC0000152A03&LrnFPort=1&LrnInfos=TWA_100006356.873.AS-1-135680630&AS_ID=testserver&Time=2018-06-22T11%3A41%3A08.163%2B02%3A00&Token=1765b08354dfdec (Caused by SSLError(SSLEOFError(8, u'EOF occurred in violation of protocol (_ssl.c:661)'),))

/usr/local/lib/python2.7/site-packages/urllib3/connectionpool.py:858: InsecureRequestWarning: Unverified HTTPS request is being made. Adding certificate verification is strongly advised. See: https://urllib3.readthedocs.io/en/latest/advanced-usage.html#ssl-warnings InsecureRequestWarning)

Reproduction Steps

import requests
from flask import Flask, request, jsonify
from requests import Request, Session

sess = requests.Session()
adapter = requests.adapters.HTTPAdapter(max_retries = 200)
sess.mount('http://', adapter)
sess.mount('https://', adapter)
sess.cert ='/usr/local/lib/python2.7/site-packages/certifi/cacert.pem'


def test_post():
    url = 'https://dev.domain.nl/ingestion/?'
    header = {'Content-Type': 'application/json', 'Accept': 'application/json'}
    response = sess.post(url, headers= header, params= somepara, data= json.dumps(data),verify=True)
    print response.status_code
    return response.status_code

def main():
    threading.Timer(10.0, main).start()
    test_post()

if __name__ == '__main__':
    main()
    app.run(host="0.0.0.0", debug=True, port=5001, threaded=True)

Docker File

FROM python:2.7-alpine
COPY ./web /web
WORKDIR /web
RUN pip install -r requirements.txt

ENV FLASK_APP app.py

EXPOSE 5001
EXPOSE 443

CMD ["python", "app.py"]
5
  • When you say that project works locally do you mean you run code from your workstation or you build Docker container and run this Docker container from workstation? Commented Jun 22, 2018 at 13:38
  • Could you please publish the Dockerfile you use to build the container image? Commented Jun 22, 2018 at 13:39
  • "EOF occurred in violation of protocol" - looks like the server has closed the connection for unknown reason which means the client can not continue. Maybe you'll find the reason if you look more closely at the server side (error logs etc) instead of only at the client. Commented Jun 22, 2018 at 14:06
  • 1
    @lexsys Included the docker file above. Yes, the project runs on a local flask setup on localhost:5001/flask Commented Jun 22, 2018 at 14:15
  • @CloudJedi try to reproduce problem running Docker container locally. I guess the problem is in the Alpine image that has no CA certificates installed not in k8s itself Commented Jun 22, 2018 at 15:03

1 Answer 1

1

The problem may be in the Alpine Docker image that lacks CA certificates. On your laptop code works as it uses CA certs from you local workstation. I would think that running Docker image locally will fail too - so the problem is not k8s.

Try to add the following line to the Dockerfile:

RUN apk update && apk add ca-certificates && rm -rf /var/cache/apk/*

It will install CA certs inside the container.

Sign up to request clarification or add additional context in comments.

5 Comments

When I build and run the docker image locally, the post requests are being sent with the write response code. So for some reason it's only in kubernetes, that it's not making a POST call.
Certificate #1: RSA 2048 bits | TLS 1.2, Full Results here ssllabs.com/ssltest/…
Ok, something interesting: there are two certificates. One A-level correct and one self-signed Common names: Kubernetes Ingress Controller Fake Certificate. If code inside k8s gets the second one it will through an error.
When I do a curl POST call from the flask container to the pod containing the endpoint, I see the following error OpenSSL SSL_connect: SSL_ERROR_SYSCALL in connection to dev.domain.nl:443
I get the below error now /usr/local/lib/python2.7/site-packages/urllib3/connectionpool.py:858: InsecureRequestWarning: Unverified HTTPS request is being made. Adding certificate verification is strongly advised. See: urllib3.readthedocs.io/en/latest/… InsecureRequestWarning)

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.