skip to Main Content

I’m new to python and have been put on a task of building out a spreadsheet parser. I’ve created a python script that reads an xlsx file and parses the data. I have an Nginx server set up that this will be hosted on. I need this script to be an API endpoint so I can pass the parsed data back as JSON. I have been reading about WSGI for production server and have tried to follow the route of building that out. I am able to serve a path on the server and have it output the wsgi python script. The script has the following:

def application(environ, start_response):
status = '200 OK'
html = '<html>n' 
       '<body>n' 
       ' Hooray, mod_wsgi is workingn' 
       '</body>n' 
       '</html>n'
response_header = [('Content-type','text/html')]
start_response(status, response_header)
return [html]

I’m a little confused as to how to receive a request and send back json with my excel parser class? Thanks and I hope I’m being clear. I do have a flask server that works, but I do not know how to have it constantly running to serve my endpoint:

app = Flask(__name__)

@app.route(‘/parser/direct_energy’, methods=[‘GET’])

def get_data():
return jsonify(commissions_data)

if name == ‘main‘:
app.run(host=’0.0.0.0’)

4

Answers


  1. Chosen as BEST ANSWER

    UPDATE

    I got things working throug NGinx, flask, and GUnicorn. However, my flask app is only working when I go to '/'. If I go to a route such as /parser/de/v1 I get a 404 Not Found.
    Here is my setup for NGinx:

    server {
        listen 80 default_server;
        listen [::]:80 default_server;
    
        # SSL configuration
        #
        # listen 443 ssl default_server;
        # listen [::]:443 ssl default_server;
        #
        # Note: You should disable gzip for SSL traffic.
        # See: https://bugs.debian.org/773332
        #
        # Read up on ssl_ciphers to ensure a secure configuration.
        # See: https://bugs.debian.org/765782
        #
        # Self signed certs generated by the ssl-cert package
        # Don't use them in a production server!
        #
        # include snippets/snakeoil.conf;
    
        root /var/www/html/excel_parser;
    
        # Add index.php to the list if you are using PHP
        index index.html index.htm index.nginx-debian.html index.php;
    
        server_name 208.97.141.147;
    
        location / {
                # First attempt to serve request as file, then
                # as directory, then fall back to displaying a 404.
                proxy_pass http://127.0.0.1:5000;
                proxy_connect_timeout 75s;
                proxy_read_timeout 300s;
                try_files $uri $uri/ =404;
        }
    
        # pass PHP scripts to FastCGI server
        #
        #location ~ .php$ {
        #       include snippets/fastcgi-php.conf;
        #
        #       # With php-fpm (or other unix sockets):
        #       fastcgi_pass unix:/var/run/php/php7.0-fpm.sock;
        #       # With php-cgi (or other tcp sockets):
        #       fastcgi_pass 127.0.0.1:9000;
        #}
    
        # deny access to .htaccess files, if Apache's document root
        # concurs with nginx's one
        #
        #location ~ /.ht {
        #       deny all;
        #}
    
           
    

  2. You don’t want to use raw WSGI for this.

    Use a package such as FastAPI (or Flask) to make everything easier for you.

    For instance, using FastAPI, an app with an endpoint to receive a binary (Excel) file and return a JSON response is approximately

    from fastapi import FastAPI, File, UploadFile
    
    app = FastAPI()
    
    
    @app.post("/process")
    def process_file(file: UploadFile = File()):
        response = my_data_processing_function(data)
        return {"response": response}
    

    See:

    Login or Signup to reply.
  3. I use python/flask for development & gunicorn for production.

    To get it to accept HTTP requests, I use function decorators. Its the most common way.

    @application.route('/epp/api/v1.0/request', methods=['POST'])
    def eppJSON():
        if flask.request.json is None:
            return abort(400, "No JSON data was POSTed")
        return jsonRequest(flask.request.json, flask.request.remote_addr)
    

    So here, the url /epp/api/v1.0/request accepts POSTed JSON and returns JSON

    When you run flask in dev mode it listens on http://127.0.0.1:5000

    https://github.com/james-stevens/epp-restapi/blob/master/epprest.py
    https://github.com/james-stevens/dnsflsk/blob/master/dnsflsk.py

    These are both python/flask projects of mine. Feel free to copy. They each run multiple instances of the python code in a single container load-balanced by nginx – pretty neat combination.

    Login or Signup to reply.
  4. my nginx.conf looks slightly different, partly becuase I am running multiple WSGI instances, then getting nginx to load-balance over them

    worker_processes  3;
    events {
        worker_connections  1024;
    }
    user daemon;
    http {
        access_log      off;
        error_log       stderr error;
        include         mime.types;
        default_type    application/octet-stream;
        sendfile        on;
        keepalive_timeout  65;
        upstream dns_servers {
            server unix:/ram/dnsflsk_1.sock;
            server unix:/ram/dnsflsk_2.sock;
            server unix:/ram/dnsflsk_3.sock;
            }
    
        server {
            listen 800 ssl;
            server_name localhost;
            ssl_certificate      certkey.pem;
            ssl_certificate_key  certkey.pem;
            ssl_session_cache    shared:SSL:1m;
            ssl_session_timeout  5m;
            ssl_ciphers  HIGH:!aNULL:!MD5;
            ssl_prefer_server_ciphers  on;
            location / {
                proxy_pass http://dns_servers;
            }
        }
    }
    

    But with this, all the URLs are passed to the python/wsgi

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search