title: Docker flask uwsgi 404 on a remote host
body: <p><strong>Update 2</strong></p>
  
  <p>I configure my routes in configure_blueprints called from create_app. I don`t want put all my views handlers in uwsgi.py. They are stored in separate modules. </p>
  
  <pre><code>def configure_blueprints(app):
      from .root import root_bp
      ...
      blueprints = [
          (root_bp, None),
          ...
      ]
      for bp, endpoint in blueprints:
          app.register_blueprint(bp, url_prefix=endpoint)
      return app
  
  
  def create_app(config_fn=None):
      app = Flask(__name__, template_folder='../templates', static_folder='../static')
      ...
      configure_blueprints(app)
      return app
  </code></pre>
  
  <p>app/root/views.py</p>
  
  <pre><code>root_bp = Blueprint('root_bp', __name__)
  
  @root_bp.route('/')
  def root():
      if not current_user.is_authenticated:
          return redirect('/login/')
      return render_template('index.html')
  </code></pre>
  
  <p>Here is output of <code>SIMPLE_SETTINGS=app.config,instance.docker python3 manage.py list_routes</code></p>
  
  <pre><code>2017-03-01 06:48:11,381 - passlib.registry - DEBUG - registered 'sha512_crypt' handler: &lt;class 'passlib.handlers.sha2_crypt.sha512_crypt'&gt;
  ...
  root_bp.root                                       HEAD,OPTIONS,GET     /
  ...
  </code></pre>
  
  <p>This is implementation of the <code>list_routes</code> command</p>
  
  <pre><code>@manager.command
  def list_routes():
      import urllib
      output = []
      for rule in flask.current_app.url_map.iter_rules():
          options = {}
          for arg in rule.arguments:
              options[arg] = '[{0}]'.format(arg)
          methods = ','.join(rule.methods)
          try:
              url = flask.url_for(rule.endpoint, **options)
          except BaseException as e:
              print('Exc={}'.format(e))
          line = urllib.parse.unquote('{:50s} {:20s} {}'.format(rule.endpoint, methods, url))
          output.append(line)
      for line in sorted(output):
          print(line)
  </code></pre>
  
  <p>I do not understand why routes should be placed to a file and can not be configured dynamically. If this does not work, what should I do? </p>
  
  <p><strong>Update</strong></p>
  
  <p>uwsgi.ini </p>
  
  <pre><code>[uwsgi]
  env = SIMPLE_SETTINGS=app.config,instance.docker
  callable = app
  wsgi-file = /var/www/app/uwsgi.py
  uid = www-data
  gid = www-data
  socket = /var/www/app/uwsgi.sock
  chmod-socket = 666
  logto = /var/log/uwsgi/app/app.log
  chdir = /var/www/app
  plugin = python3
  master = true
  processes = 1
  </code></pre>
  
  <p>/var/www/app/uwsgi.py</p>
  
  <pre><code>from app import create_app
  app = create_app()
  </code></pre>
  
  <p>I configure blueprints inside create_app function. I think they should be available at the time of application start. Also I use Flask-script. </p>
  
  <pre><code>SIMPLE_SETTINGS=app.config,instance.docker python3 manage.py shell
  </code></pre>
  
  <p>The shell starts without errors.</p>
  
  <p><strong>Original post</strong></p>
  
  <p>I have studied all related questions. I could not solve my problem. I deploy my project through the docker-machine on the remote host. Here is my configuration:</p>
  
  <p>Dockerfile</p>
  
  <pre><code>FROM ubuntu:latest
  RUN locale-gen en_US.UTF-8
  ENV LANG en_US.UTF-8
  ENV LANG en_US.UTF-8
  ENV LC_ALL en_US.UTF-8
  
  RUN apt-get update &amp;&amp; apt-get install -y \
      python3 python3-pip git libpq-dev libevent-dev uwsgi-plugin-python3 \
      nginx supervisor 
  
  COPY nginx/flask.conf /etc/nginx/sites-available/
  COPY supervisor/supervisord.conf /etc/supervisor/conf.d/supervisord.conf
  COPY . /var/www/app
  
  RUN mkdir -p /var/log/nginx/app /var/log/uwsgi/app /var/log/supervisor \
      &amp;&amp; rm /etc/nginx/sites-enabled/default \
      &amp;&amp; ln -s /etc/nginx/sites-available/flask.conf /etc/nginx/sites-enabled/flask.conf \
      &amp;&amp; echo "daemon off;" &gt;&gt; /etc/nginx/nginx.conf \
      &amp;&amp;  pip3 install -r /var/www/app/python_modules \
      &amp;&amp; chown -R www-data:www-data /var/www/app \
      &amp;&amp; chown -R www-data:www-data /var/log
  
  WORKDIR /var/www/app
  
  CMD ["/usr/bin/supervisord"]
  </code></pre>
  
  <p>docker-compose.yml</p>
  
  <pre><code>version: '2'
  services:
    db:
      image: postgres
      volumes:
        - moderator-db:/var/lib/postgresql/data
    redis:
      image: redis
    rabbitmq:
      image: rabbitmq:3.6
    api:
      build: .
      mem_limit: 1000m
      ports:
        - "80:80"
      depends_on:
        - redis
        - db
        - rabbitmq
  volumes:
    moderator-redis:
      driver: local
    moderator-db:
      driver: local
  </code></pre>
  
  <p>supervisord.conf</p>
  
  <pre><code>[supervisord]
  nodaemon=true
  
  [program:nginx]
  command=/usr/sbin/nginx
  
  [program:uwsgi]
  command=uwsgi --ini /var/www/app/uwsgi.ini
  </code></pre>
  
  <p>flask nginx conf</p>
  
  <pre><code>server {
  
      server_name localhost;
      listen 80 default_server;
  
      charset utf-8;
      sendfile on;
      client_max_body_size 70M;
      keepalive_timeout  0;
  
      proxy_buffering on;
      proxy_buffer_size 8k;
      proxy_buffers 2048 8k;
      proxy_ignore_client_abort on;
  
      location / {
          include uwsgi_params;
          uwsgi_pass unix:///var/www/app/uwsgi.sock;
      }
  
      location /static {
          root /var/www/app/static/;
      }
  }
  </code></pre>
  
  <p>$docker ps</p>
  
  <pre><code>CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                                NAMES
  d9dec354d97e        moderator_api       "/usr/bin/supervisord"   13 seconds ago      Up 9 seconds        0.0.0.0:80-&gt;80/tcp                   moderator_api_1
  243c48dac303        postgres            "docker-entrypoint..."   3 hours ago         Up 14 seconds       5432/tcp                             moderator_db_1
  23901a761ef1        redis               "docker-entrypoint..."   3 hours ago         Up 14 seconds       6379/tcp                             moderator_redis_1
  7cc0683bfe18        rabbitmq:3.6        "docker-entrypoint..."   3 hours ago         Up 16 seconds       4369/tcp, 5671-5672/tcp, 25672/tcp   moderator_rabbitmq_1
  </code></pre>
  
  <p>tail -f /var/log/uwsgi/app/app.log</p>
  
  <pre><code>[pid: 24|app: 0|req: 1/1] 123.23.7.216 () {44 vars in 945 bytes} [Tue Feb 28 14:53:57 2017] GET / =&gt; generated 233 bytes in 10 msecs (HTTP/1.1 404) 3 headers in 311 bytes (1 switches on core 0)
  </code></pre>
  
  <p>If you need any additional information, please let me know. I tried different configurations: nginx-proxy image, gunicorn etc. I have same problem with the remote host. What am I still missing? </p>