我有一个Flask应用程序,其中芹菜工作正常,Flask-Mail本身的工作也很好。
from celery import Celery
from flask_mail import Mail, Message
app = Flask(__name__)
mail = Mail(app)
celery = Celery('main_app',
broker='mongodb://localhost',
backend='mongodb://localhost')
@celery.task
def cel_test():
return 'cel_test'
@app.route('/works_maybe')
def works_maybe():
return cel_test.delay()
cel_test与芹菜工人合作得很好;一切都出现在蒙戈。
但是这里变得奇怪。 “注册”加邮件方法在没有@celery.task
的情况下100%工作,但在成为任务时会爆炸。
@celery.task
def send_email(some_arg, name, email):
msg = Message(…message details..)
return mail.send(msg)
@app.route("/signup", methods=['POST'])
def signup():
return send_email.delay(...stuff for the message…)
R = retval = fun(*args, **kwargs)
File "/Users/username/pymods/virtualenvs/directory/lib/python2.7/site-packages/celery-3.0.15-py2.7.egg/celery/task/trace.py", line 415, in __protected_call__
return self.run(*args, **kwargs)
File "/Users/username/pymods/directory/directory/main_app/main_app.py", line 43, in send_email
something = 'a string in the Message'),
File "/Users/username/pymods/virtualenvs/directory/lib/python2.7/site-packages/flask/templating.py", line 123, in render_template
ctx.app.update_template_context(context)
AttributeError: 'NoneType' object has no attribute 'app'
有人可以解释为什么在一个案例中芹菜效果很好但是当我涉及mail.send(msg)它会破坏吗?
也许我需要更多地学习python?
任何想法,如果至少如何处理这类问题将不胜感激。
答案 0 :(得分:0)
该错误位于send_email
任务的render_template部分。
@celery.task
def send_email(some_arg, name, email):
msg = Message(
subject='hello',
body=render_template('email.txt',
name=name,
some_arg=some_arg),
recipients=[email]
)
return mail.send(msg)
当我删除body=render_template
, kablaam 时,它可以正常工作。
我有from flask import render_template
。也许render_template
不能像这样工作?
奇怪的是,没有 Celery,send_email
加上render_template
就完美了。
当我用另一个函数强制app_context
时,一切正常:
def create_email(some_arg, name, email):
with app.test_request_context('/send_email'):
return render_template('email.txt',
name=name,
some_arg=some_arg)
然后将其投放到send_email
任务中
body = render_template('email.txt'…
成为
body= create_email(some_arg, name)
我们在家免费。
答案 1 :(得分:0)
烧瓶中完成的许多事情都绑定到应用程序上下文。例如,render_template
函数需要知道您的应用程序在何处存储其模板。 session
变量希望了解您的应用程序的数据存储或缓存系统。 request
对象和您的mail.send
在被调用时需要一些应用程序上下文。
如果要在flask应用程序范围之外调用它们(例如在celery任务中),请在应用程序上下文中进行操作,如下所示:
...
with app.app_context():
do_some_context_bound_actions()
msg = Messgae(...)
user_name = app.session["user"].name
msg.html = render_template("mail/welcome.html", name=user_name)
mail.send(msg)
...