python - flask中current_app._get_current_object()与current_app有什么区别?
伊谢尔伦
伊谢尔伦 2017-04-17 17:59:56
0
2
1055

在学习flask开发,书中一段异步发送邮件的代码是这样写的:

from threading import Thread
from flask import current_app, render_template
from flask.ext.mail import Message
from . import mail


def send_async_email(app, msg):
    with app.app_context():
        mail.send(msg)


def send_email(to, subject, template, **kwargs):
    app = current_app._get_current_object()
    msg = Message(app.config['FLASKY_MAIL_SUBJECT_PREFIX'] + ' ' + subject,
                  sender=app.config['FLASKY_MAIL_SENDER'], recipients=[to])
    msg.body = render_template(template + '.txt', **kwargs)
    msg.html = render_template(template + '.html', **kwargs)
    thr = Thread(target=send_async_email, args=[app, msg])
    thr.start()
    return thr

send_mail函数中,程序使用了current_app._get_current_object()赋值给app作为当前程序的实例。此处为什么不直接使用current_app呢?

flask官方文档中是这样解释这个方法_get_current_object()的:

Return the current object. This is useful if you want the real object behind the proxy at a time for performance reasons or because you want to pass the object into a different context.

看了这个我还是没懂书中的代码为什么要这样= =。。。

伊谢尔伦
伊谢尔伦

小伙看你根骨奇佳,潜力无限,来学PHP伐。

membalas semua(2)
PHPzhong

Kunci kepada soalan ini terletak pada ayat ketiga dari bawah:

thr = Thread(target=send_async_email, args=[app, msg])

Oleh kerana benang berasingan dibuka di sini, anda mungkin tertanya-tanya, kenapa anda tidak boleh menggunakan current_app selepas membuka benang? betul! Hanya buka benang dan anda tidak boleh menggunakan current_app. Sebabnya terletak pada pelaksanaan current_app.

current_app ialah proksi dalam Flask Jika anda melihat kod sumber Flask, anda akan mendapati bahawa ia sebenarnya dibalut seperti ini:
Baris alamat kod sumber: 48-58

def _find_app():
    top = _app_ctx_stack.top
    if top is None:
        raise RuntimeError(_app_ctx_err_msg)
    return top.app

...

current_app = LocalProxy(_find_app)
Saya tidak akan menerangkan secara terperinci tentang ini

, tetapi saya boleh memberitahu anda bahawa fungsi LocalProxy ini adalah untuk mengembalikan objek yang sepadan dengan coroutine/benang semasa mengikut benang/coroutine, iaitu untuk mengatakan LocalProxy

  • Thread A memasukkan A

    ke dalam LocalProxy
  • Benang B memasukkan B ke dalam LocalProxy

Tidak kira di mana anda berada,

  • Thread A akan sentiasa dapat A, thread B akan sentiasa dapat B

Ini ialah sebab asas mengapa pembolehubah seperti

dan Flask boleh digunakan terus dalam kod dalam request. current_app

Jadi, inilah jawapannya, kerana benang baru dibuka di sini Jika anda tidak melalui objek sebenar, maka anda tidak akan dapat mendapatkan objek jika anda menggunakan

dalam utas, kerana ia. tidak mempunyai current_app. Ini adalah satu lagi konsep penting Flask, terlalu banyak untuk dikatakan. flask 上下文

Boleh dikatakan penyoal sepatutnya dapat memahaminya.

伊谢尔伦

Saya melihat kod ini pada masa itu dan fikir ia adalah sama, tetapi mengapa tidak app=current_object?

Jadi lihat sekali lagi, maksud saya ialah perihalan dalam dokumen menyebut bahawa current_app ialah objek aplikasi global, dan current_app._get_current_object ialah objek get (dapatkan objek), serupa dengan kelas Staticmethod dan classmethod berikut. perkara yang berbeza (analogi ini tidak tepat, tetapi tidak sukar untuk mendapatkan apa yang saya maksudkan. Mereka sangat serupa sifatnya).

Lihat penjelasan jawapan ini:

Walau bagaimanapun, adalah salah untuk mengatakan ini. Sila lihat penjelasan _get_current_object

Kembalikan objek semasa Ini berguna jika anda mahu objek sebenar di belakang proksi pada satu masa atas sebab prestasi atau kerana anda ingin menghantar objek ke dalam konteks yang berbeza.

Apa yang ditulis di sini ialah objek sebenar
Adakah ini bermakna ini adalah contoh? Ia boleh difahami dengan cara ini, dan sudah tentu ia boleh menjadi lebih tepat.

Kerana tidak kira apa pun, adalah lebih baik untuk melihat kod sumber, kerana tidak kira apa itu, orang yang mereka bentuk rangka kerja boleh menukarnya dengan menulisnya secara terbalik
Sama ada ia adalah contoh atau objek, kaedah mereka pasti akan berbeza Lagipun, kod itu direka oleh orang, dan rangka kerja ini juga ditulis oleh orang ramai atau contoh, kerana saya rasa pada akhirnya ia tidak juga.

Muat turun terkini
Lagi>
kesan web
Kod sumber laman web
Bahan laman web
Templat hujung hadapan