Forums

PythonAnywhere flask WSGI app: ModuleNotFoundError

I am a beginner using Flask on PythonAnywhere.com to run an application "mwpi.py" to be displayed as a web page "MWPI.html" from my web site "KenPryor67.pythonanywhere.com". Please see my code examples at StackOverflow.com: http://stackoverflow.com/questions/43191772/pythonanywhere-flask-wsgi-app-modulenotfounderror

Whenever I attempt to access my web site, an error page appears with the following error: Error code: Unhandled Exception. Checking the error log reveals the following errors: Error running WSGI application ModuleNotFoundError: No module named 'app' File "/var/www/kenpryor67_pythonanywhere_com_wsgi.py", line 16, in from app import app as application

How can I fix my app code and/or the WSGI application to display my web page properly? Thanks in advance for your help!

I changed the import statement in the WSGI file to read "from mwpi import app as application". That apparently worked, but, now I receive an internal server error when I try to access my web page. Checking the error log, the following errors appear:

2017-04-03 20:24:20,836 :[2017-04-03 20:24:20,832] ERROR in app: Exception on / [HEAD]
2017-04-03 20:24:20,838 :Traceback (most recent call last):
2017-04-03 20:24:20,838 :  File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1982, in wsgi_app
2017-04-03 20:24:20,838 :    response = self.full_dispatch_request()
2017-04-03 20:24:20,838 :  File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1615, in full_dispatch_request
2017-04-03 20:24:20,838 :    return self.finalize_request(rv)
2017-04-03 20:24:20,839 :  File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1630, in finalize_request
2017-04-03 20:24:20,839 :    response = self.make_response(rv)
2017-04-03 20:24:20,839 :  File "/usr/local/lib/python3.6/dist-packages/flask/app.py", line 1740, in make_response
2017-04-03 20:24:20,839 :    rv = self.response_class.force_type(rv, request.environ)
2017-04-03 20:24:20,839 :  File "/usr/local/lib/python3.6/dist-packages/werkzeug/wrappers.py", line 847, in force_type
2017-04-03 20:24:20,839 :    response = BaseResponse(*_run_wsgi_app(response, environ))
2017-04-03 20:24:20,839 :  File "/usr/local/lib/python3.6/dist-packages/werkzeug/test.py", line 871, in run_wsgi_app
2017-04-03 20:24:20,839 :    app_rv = app(environ, start_response)
2017-04-03 20:24:20,839 :TypeError: 'InputForm' object is not callable

[edit by admin: formatting]

What that error message is saying is that it's trying to execute the statement

app_rv = app(environ, start_response)

...which calls the function that is the value of the variable app with the given parameters, and then assigns the result to app_rv. The error message is TypeError: 'InputForm' object is not callable, and there is only one call in the line, which means that the variable app must be an InputForm object. This is strange, because it should (as you would expect) be a Flask app, not a form.

Now let's take a look at your code, copied and pasted from Stack Overflow:

from wtforms import Form, FloatField
from flask import Flask, render_template, request

app = Flask(__name__)

@app.route('/', methods=['GET', 'POST'])

class InputForm(Form):
    P_level_upper = FloatField(label='Upper pressure level (mb)', 
    default=650.0)
    P_level_lower = FloatField(label='Upper pressure level (mb)', 
    default=850.0)
    Z_upper = FloatField(label='Upper boundary height', default=3.5)
    Z_upper = FloatField(label='Lower boundary height', default=1.5)
    T_upper = FloatField(label='Upper boundary temperature', default=0)
    T_lower = FloatField(label='Lower boundary temperature', default=25)
    TD_upper = FloatField(label='Upper boundary dewpoint', default=0)
    TD_lower = FloatField(label='Lower boundary dewpoint', default=10)
    CAPE = FloatField(label='CAPE', default=1000)

def index():
    form = InputForm(request.form)
    def MWPI(P_level_upper, P_level_lower, Z_upper, Z_lower, T_upper, 
    T_lower, TD_upper, TD_lower, CAPE):
        gamma = (T_lower - T_upper)/(Z_upper - Z_lower)
        DD_upper = T_upper - TD_upper
        DD_lower = T_lower - TD_lower
        DDD = DD_lower - DD_upper
        MWPI = CAPE/100 + gamma + DDD
        WGP = (0.4553 * MWPI) + 28.769
        return MWPI, WGP
    if request.method == 'POST':
        result = MWPI(form.P_level_upper.data, form.P_level_lower.data, 
        form.Z_upper.data, form.Z_lower.data, form.T_upper.data,
        form.T_lower.data, form.TD_upper.data, form.TD_lower.data, 
        form.CAPE.data)
    else:
        result = None

    return render_template('MWPI.html', form=form, result=result)

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

There's something very strange there. The app.route decorator is applied to the thing that immediately follows it. The is normally the function that handles the URL that you specify in the decorator. However, you've put it just before your class InputForm instead. This will confuse Flask, as it's trying to work out which function to send a request to, and it's getting something that isn't a function -- hence the error.

What you need to do is move the @app.route down so that it applies to your view function instead of to the InputForm class, like this:

from wtforms import Form, FloatField
from flask import Flask, render_template, request

app = Flask(__name__)


class InputForm(Form):
    P_level_upper = FloatField(label='Upper pressure level (mb)', 
    default=650.0)
    P_level_lower = FloatField(label='Upper pressure level (mb)', 
    default=850.0)
    Z_upper = FloatField(label='Upper boundary height', default=3.5)
    Z_upper = FloatField(label='Lower boundary height', default=1.5)
    T_upper = FloatField(label='Upper boundary temperature', default=0)
    T_lower = FloatField(label='Lower boundary temperature', default=25)
    TD_upper = FloatField(label='Upper boundary dewpoint', default=0)
    TD_lower = FloatField(label='Lower boundary dewpoint', default=10)
    CAPE = FloatField(label='CAPE', default=1000)


@app.route('/', methods=['GET', 'POST'])
def index():
    form = InputForm(request.form)
    def MWPI(P_level_upper, P_level_lower, Z_upper, Z_lower, T_upper, 
    T_lower, TD_upper, TD_lower, CAPE):
        gamma = (T_lower - T_upper)/(Z_upper - Z_lower)
        DD_upper = T_upper - TD_upper
        DD_lower = T_lower - TD_lower
        DDD = DD_lower - DD_upper
        MWPI = CAPE/100 + gamma + DDD
        WGP = (0.4553 * MWPI) + 28.769
        return MWPI, WGP
    if request.method == 'POST':
        result = MWPI(form.P_level_upper.data, form.P_level_lower.data, 
        form.Z_upper.data, form.Z_lower.data, form.T_upper.data,
        form.T_lower.data, form.TD_upper.data, form.TD_lower.data, 
        form.CAPE.data)
    else:
        result = None

    return render_template('MWPI.html', form=form, result=result)

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

Giles, Thanks very much for the quick and thorough response. I followed your direction about the @app.route statement and now my web page displays correctly. However, when I execute the MWPI app, the following error now appears:

Traceback (most recent call last):
  File "/home/KenPryor67/mysite/mwpi.py", line 42, in <module>
    app.run()
  File "/usr/local/lib/python3.5/dist-packages/flask/app.py", line 843, in run
    run_simple(host, port, self, **options)
  File "/usr/local/lib/python3.5/dist-packages/werkzeug/serving.py", line 694, in run_simple
    inner()
  File "/usr/local/lib/python3.5/dist-packages/werkzeug/serving.py", line 656, in inner
    fd=fd)
  File "/usr/local/lib/python3.5/dist-packages/werkzeug/serving.py", line 550, in make_server
    passthrough_errors, ssl_context, fd=fd)
  File "/usr/local/lib/python3.5/dist-packages/werkzeug/serving.py", line 464, in __init__
    HTTPServer.__init__(self, (host, int(port)), handler)
  File "/usr/lib/python3.5/socketserver.py", line 440, in __init__
    self.server_bind()
  File "/usr/lib/python3.5/http/server.py", line 138, in server_bind
    socketserver.TCPServer.server_bind(self)
  File "/usr/lib/python3.5/socketserver.py", line 454, in server_bind
self.socket.bind(self.server_address)
OSError: [Errno 98] Address already in use

What is "Address" referring to, and how can I fix this error? Thanks again for all your help!

Please disregard my last message. My web page and MWPI app are working great now! Again, I really appreciate all your time and assistance. PythonAnywhere is an outstanding resource. I'm using PythonAnywhere at my work as a NOAA scientist and as a graduate student in Physics at University of Maryland, Baltimore County.

:)