Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Querying model in Flask-APScheduler job raises app context RuntimeError

I want to run a job with Flask-APScheduler that queries a Flask-SQLAlchemy model. When the job runs, I get RuntimeError: application not registered on db instance and no application bound to current context. How can I run a job that queries the database.

from flask_apscheduler import APScheduler

scheduler = APScheduler()
scheduler.init_app(app)
scheduler.start()
from models import User

def my_job():
    user = User.query.first()
    print(user)

The error occurs during the query, before it can be printed. The database is working in the rest of the application for other queries.

I tried to add with app.app_context(): while setting up the extension but that didn't work.

with app.app_context()
    scheduler = APScheduler()
    scheduler.init_app(app)
    scheduler.start()

The full traceback is:

ERROR:apscheduler.executors.default:Job "run_in (trigger: interval[0:00:10], next run at: 2016-10-18 23:00:53 CEST)" raised an exception
Traceback (most recent call last):
  File "/Users/user/.virtualenvs/myfolder/lib/python2.7/site-packages/apscheduler/executors/base.py", line 125, in run_job
    retval = job.func(*job.args, **job.kwargs)
  File "/Users/user/Documents/myfolder/myfolder/myfile.py", line 19, in myjob
    user = User.query.all()
  File "/Users/user/.virtualenvs/myfolder/lib/python2.7/site-packages/flask_sqlalchemy/__init__.py", line 454, in __get__
    return type.query_class(mapper, session=self.sa.session())
  File "/Users/user/.virtualenvs/myfolder/lib/python2.7/site-packages/sqlalchemy/orm/scoping.py", line 71, in __call__
    return self.registry()
  File "/Users/user/.virtualenvs/myfolder/lib/python2.7/site-packages/sqlalchemy/util/_collections.py", line 878, in __call__
    return self.registry.setdefault(key, self.createfunc())
  File "/Users/user/.virtualenvs/myfolder/lib/python2.7/site-packages/flask_sqlalchemy/__init__.py", line 704, in create_session
    return SignallingSession(self, **options)
  File "/Users/user/.virtualenvs/myfolder/lib/python2.7/site-packages/flask_sqlalchemy/__init__.py", line 149, in __init__
    self.app = db.get_app()
  File "/Users/user/.virtualenvs/myfolder/lib/python2.7/site-packages/flask_sqlalchemy/__init__.py", line 845, in get_app
    raise RuntimeError('application not registered on db '
RuntimeError: application not registered on db instance and no application bound to current context
like image 233
Tone Avatar asked Oct 18 '16 20:10

Tone


1 Answers

Flask-SQLAlchemy requires an active app context to execute queries. While Flask-APScheduler does integrate APScheduler with Flask, it does not push an application context when running each job.

You'll need to push an app context in your job. Pushing an app context when setting up the extension doesn't do anything.

def my_job():
    with app.app_context():
        ...

You probably want an app context for all jobs. You can subclass the extension and override run_job.

from flask_apscheduler import APScheduler as _BaseAPScheduler

class APScheduler(_BaseAPScheduler):
    def run_job(self, id, jobstore=None):
        with self.app.app_context():
            super().run_job(id=id, jobstore=jobstore)
            # super(APScheduler, self) in Python 2
like image 76
davidism Avatar answered Sep 19 '22 11:09

davidism