Проблема кругового импорта при работе с отправкой почты при регистрации пользователя на Flask - PullRequest
0 голосов
/ 02 ноября 2018

В настоящее время я работаю с колбой и пытаюсь отправить электронные письма, как только пользователь зарегистрируется на сайте. У меня возникают проблемы с циклическим импортом между main.py, где создается экземпляр приложения, и data_inserts.py, где данные передаются в базу данных и пароль отправляется обратно пользователю. Для работы с электронной почтой я использую расширение Flask-mail. Ошибка, которую я получаю, приведена ниже:

ImportError: Cannot import name from 'DataInserts' from relevant_folder.data_inserts

Ниже приведены подробности:

main.py:

from relevant_folder.data_inserts import DataInserts
from flask import Flask
from flask_mail import Mail
from conf.mail_settings.py import mail_settings

app = Flask(__name__)
app.config.update[mail_settings]
mail = Mail(app)

@app.route("/register")
def register():
    params = request.json
    DataInserts.add_user(params)

relevant_folder.data_inserts.py:

from main import app
from main.app import mail
from flask_mail import message 

class DataInserts():
    def add_user(self, new_user_json):
        ''' add user name and email to db logic goes here'''
        msg = Message(subject="Subject",
                  sender=app.config.get("MAIL_USERNAME"),
                  recipients=[new_user_json["email"]],
                  body="Hello " + new_user_json["name"] + ", your password is password")
        mail.send(msg)

Мне кажется, я неправильно структурировал свое приложение. Любая помощь с благодарностью

1 Ответ

0 голосов
/ 02 ноября 2018

Достаточно переместить импорт DataInserts ...

from flask import Flask
from flask_mail import Mail
from conf.mail_settings.py import mail_settings

app = Flask(__name__)
app.config.update[mail_settings]
mail = Mail(app)

from relevant_folder.data_inserts import DataInserts

@app.route("/register")
def register():
    params = request.json
    DataInserts.add_user(params)

В качестве альтернативы вы можете передавать экземпляры приложения и почты в класс DataInsert вместо импорта глобальных переменных ...

Обновление: другим подходом будет использование "flask.current_app".

from relevant_folder.data_inserts import DataInserts
from flask import Flask
from flask_mail import Mail
from conf.mail_settings.py import mail_settings

app = Flask(__name__)
app.config.update[mail_settings]
mail = Mail(app)
app.mail = mail

@app.route("/register")
def register():
    params = request.json
    DataInserts.add_user(params)

Обратите внимание, что я сохранил почтовый экземпляр в app.mail для быстрого доступа позже.

relevant_folder.data_inserts.py:

from flask import current_app
from flask_mail import message 

class DataInserts():
    def add_user(self, new_user_json):
        ''' add user name and email to db logic goes here'''
        msg = Message(subject="Subject",
                  sender=current_app.config.get("MAIL_USERNAME"),
                  recipients=[new_user_json["email"]],
                  body="Hello " + new_user_json["name"] + ", your password is password")
        current_app.mail.send(msg)

Но имейте в виду, что current_app нужен активный контекст приложения. при работе с запросом всегда должен быть контекст, в противном случае вы можете создать контекст вручную, например, используя with app.app_context():

Подробнее об этом см. Документацию по колбе: http://flask.pocoo.org/docs/1.0/appcontext/

...