Docker - Can't get user webcam: getUserMedia() no longer works on insecure origins

585 views Asked by At

WHAT WORKS

I created a simple Web Application in Flask that takes care of operating a simple return render_template("index.html") when the root node is accessed by a Web Browser.

# app.py
from flask import Flask, render_template
app = Flask(__name__)

@app.route("/")
def show_index():
    return render_template("index.html")

if __name__ == "__main__":
    app.run(port=80)

The index.html is a simple page that uses tracking.js in order to get the user webcam and track his/her face in the live video stream.

Opening cmd and typing python app.py results in Running on http://127.0.0.1:80/

Accessing the above mentioned URL results in the correct display of the page, that asks me for permission to use the camera, opens it and correctly tracks my face in the live video feed. So it's all working fine till here.

WHAT DOES NOT WORKS

The problem I'm experiencing arises when I dockerize my application using Docker. docker-machine ip is 192.168.99.100

Opening cmd and typing: docker run -p 4000:80 my_face_track_app results in: Running on http://0.0.0.0:80/

Accessing 192.168.99.100:4000 results in the correct display of index.html but I am not asked anymore for permission on the camera and inspecting the JS console I read the following exception:

getUserMedia() no longer works on insecure origins

Here the full error log:

enter image description here

I know the error is telling me I'm not serving the page in HTTPS.

Has anyone else encountered this problem? What would be the proper solution to the issue or a possible walkaround? Any help will be highly appreciated, thank you a lot in advance

WHAT I HAVE TRIED TO DO IN ORDER TO SOLVE THE PROBLEM

Since an HTTPS serving of the page is needed in order for JS to execute the function getUserMedia() I tought about serving my Flask application with an SSL certificate by modifying app.py like this:

# app.py
from flask import Flask, render_template
import OpenSSL

app = Flask(__name__)

@app.route("/")
def show_index():
    return render_template("index.html")

if __name__ == "__main__":
    app.run(port=80, ssl_context="adhoc")

I then dockerized the app building a new image. Typing:

docker run -p 443:80 facetrackapphttps

Results in

 Running on https://127.0.0.1:80

So yeah, here HTTPS is ON: the problem is that the port 80 of the HTTPS Flask App is mapped to the port 443 of the docker-machine ip 192.168.99.100.

Trying to access 192.168.99.100:443 does not work and nothing is shown.

Does anybody have an idea about how to do this?

1

There are 1 answers

1
larsks On BEST ANSWER

If your application is bound to 127.0.0.1 inside the container, you're not going to be able to access it from your host. According to the flask docs, flask will bind to 127.0.0.1 by default.

You'll need to modify your service so that it binds to 0.0.0.0 inside the container:

if __name__ == "__main__":
    app.run(host='0.0.0.0', port=80, ssl_context="adhoc")