Kerangka pesan

Cukup umum dalam aplikasi jaringan, anda butuh memasang pesan pemberitahuan satu-waktu (juga dikenal sebagai "flash message") pada pengguna setelah pengolahan sebuah formulir aau beberapa jenis lain dari masukan pengguna.

Untuk ini, Django menyediakan dukungan penuh untuk oesan berdasarkan-kue dan sesi, untuk kedua pengguna anonim dan terautentifikasi. Kerangka kerja pesan mengizinkan anda secara sementara menyimpan pesan dalam satu permintaan dam mengambil mereka untuk ditampilkan dalam permintaan selanjutnya (biasanya satu selanjutnya). Setiap pesan dietiket dengan level khusus yang menentukan keutamaannya (misalnya, info, warning, atau error).

Mengadakan pesan

Pesan diterapkan melalui middleware class dan bersamaan context processor.

Awalan settings.py dibuat oleh django-admin startproject sudah mengandung semua pengaturan dibutuhkan untuk mengadakan pesan fungsionalitas:

  • 'django.contrib.messages' di INSTALLED_APPS.

  • MIDDLEWARE mengandung 'django.contrib.sessions.middleware.SessionMiddleware' dan 'django.contrib.messages.middleware.MessageMiddleware'.

    storage backend awalan bergantung pada sessions. Itu mengapa SessionMiddleware harus diadakan dan muncul sebelum MessageMiddleware dalam MIDDLEWARE.

  • Pilihan 'context_processors' dari backend DjangoTemplates ditentukan di pengaturan TEMPLATES anda mengandung 'django.contrib.messages.context_processors.messages'.

Jika anda tidak ingin menggunakan pesan-pesan, anda dapat memindahkan 'django.contrib.messages' dari INSTALLED_APPS anda, baris MessageMiddleware dari MIDDLEWARE, dan pengolah konteks messages dari TEMPLATES.

Konfigurasi mesin pesan

Backend Penyimpanan

Kerangka kerja pesan-pesan dapat menggunakan backend berbeda untuk menyimpan pesan-pesan sementara.

Django menyediakan kelas-kelas penyimpanan siap-pakai di django.contrib.messages:

class storage.session.SessionStorage

Kelas ini menyimpan semua pesan didalam sesi permintaan. Karena itu membutuhkan aplikasi contrib.sessions Django.

class storage.cookie.CookieStorage

Kelas ini menyimpan data pesan dalam sebuah kue (ditandai dengan campuran rahasia untuk mencegah perubahan) untuk bertahan pemberitahuan terhadap permintaan. Pesan-pesan lama dibuang jika ukuran data kue akan melebihi 2048 byte.

class storage.fallback.FallbackStorage

Kelas ini pertama menggunakan CookieStorage, dan jatuh kembali menggunakan SessionStorage untuk pesan yang tidak cocok dalam kue tunggal. Itu juga membutuhkan aplikasi contrib.sessions Django.

Perilaku ini menghindari menulis ke sesi bilamana memungkinkan. Itu harus menyediakan penampilan terbaik di kasus umum.

FallbackStorage adalah kelas penyimpanan awalan. Jika itu tidak cocok pada kebutuhan anda, anda dapat memilih kelas penyimpanan lain dengan mengatur MESSAGE_STORAGE ke jalur impor penuhnya, sebagai contoh:

MESSAGE_STORAGE = 'django.contrib.messages.storage.cookie.CookieStorage'
class storage.base.BaseStorage

Untuk menulis kelas penyimpanan sendiri, subkelas kelas BaseStorage di django.contrib.messages.storage.base dan menerapkan metode _get dan _store.

Tingkatan pesan

Kerangka kerja pesan berdasarkan pada tingkat arsitektur dapat dikonfigurasikan mirip pada modul pencatatan Python. Tingkatan pesan mengizinkan anda mengelompokkan pesan berdasarkan jenis sehingga mereka dapat disaring atau ditampilkan berbeda dalam tampilan atau cetakan.

Tingkat siap-pakai, yang dapat diimpor dari django.contrib.messages secar langsung, adalah:

Ketetapan Maksud
DEBUG Pesan-pesan terkait-pengembangan yang akan diabaikan (atau dipindahkan) dalam penyebaran produksi
INFO Pesan informasi untuk pengguna
BERHASIL Sebuah tindakan telah berhasil, misalnya "Profil anda telah berhasil diperbaharui".
PERINGATAN Kegagalan tidak muncul tetapi mungkin sebentar lagi
KESALAHAN Sebuah tindakan tidak berhasil atau beberapa kegagalan lain muncul

Pengaturan MESSAGE_LEVEL dapat digunakan merubah tingkat perekaman minimal (atau itu dapat berupa changed per request). Usaha-usaha untuk menambahkan pesan-pesan dari tingkatan kurang dari ini akan diabaikan.

Etiket pesan

Etiket-etiket pesan adalah sebuah perwakilan string dari tingkat pesan ditambah etiket-etiket tambahan apapun yang telah ditambahkan langsung dalam tampilan (lihat Adding extra message tags dibawah untuk rincian lebih). Etiket disimpan dalam sebuah string dan dipisahkan oleh ruang. Khususnya, etiket-etiket pesan digunakan sebagai kelas-kelas CSS untuk menyesuaikan gaya pesan berdasarkan pada jenis pesan. Secara awalan, setiap tingkat mempunyai etiket tunggal yaitu versi huruf kecil dari ketetapan miliknya.

Tingkat Ketetapan Etiket
DEBUG debug
INFO info
BERHASIL berhasil
PERINGATAN peringatan
KESALAHAN kesalahan

Untuk merubah etiket-etiket awalan untuk sebuah tingkat pesan (antara siap-pakai atau penyesuaian), setel pengaturan MESSAGE_TAGS pada sebuah dictionary mengandung tingkatan anda harap rubah. Ketika ini memperpanjang etiket-etiket awalan, anda hanya butuh menyediakan etiket-etiket untuk tingkatan-tingkatan anda harap timpa:

from django.contrib.messages import constants as messages
MESSAGE_TAGS = {
    messages.INFO: '',
    50: 'critical',
}

Menggunakan pesan di tampilan dan cetakan

add_message(request, level, message, extra_tags='', fail_silently=False)[sumber]

Menambahkan pesan

Untuk menambahkan pesan, panggil:

from django.contrib import messages
messages.add_message(request, messages.INFO, 'Hello world.')

Beberapa metode jalan pintas menyediakan cara standar untuk menambah pesan-pesan dengan umumnya menggunakan etiket-etiket (yang biasanya diwakili sebagai kelas-kelas HTML untuk pesan):

messages.debug(request, '%s SQL statements were executed.' % count)
messages.info(request, 'Three credits remain in your account.')
messages.success(request, 'Profile details updated.')
messages.warning(request, 'Your account expires in three days.')
messages.error(request, 'Document deleted.')

Menampilkan pesan

get_messages(request)[sumber]

Di cetakan anda, gunakan sesuatu seperti:

{% if messages %}
<ul class="messages">
    {% for message in messages %}
    <li{% if message.tags %} class="{{ message.tags }}"{% endif %}>{{ message }}</li>
    {% endfor %}
</ul>
{% endif %}

Jika anda sedang menggunakan pengolah konteks, cetakan anda harus dibangun dengan RequestContext. Sebaliknya, apstikan messages tersedia pada konteks cetakan.

Even if you know there is only one message, you should still iterate over the messages sequence, because otherwise the message storage will not be cleared for the next request.

Pengolah konteks juga menyediakan variabel DEFAULT_MESSAGE_LEVELS yaitu sebuah pemetaan dari nama-nama tingkatan pesan ke nilai numeriknya:

{% if messages %}
<ul class="messages">
    {% for message in messages %}
    <li{% if message.tags %} class="{{ message.tags }}"{% endif %}>
        {% if message.level == DEFAULT_MESSAGE_LEVELS.ERROR %}Important: {% endif %}
        {{ message }}
    </li>
    {% endfor %}
</ul>
{% endif %}

Diluar Cetakan, anda dapat menggunakan get_messages():

from django.contrib.messages import get_messages

storage = get_messages(request)
for message in storage:
    do_something_with_the_message(message)

Sebagai contoh, anda dapat mengambil semua pesan-pesan untuk mengembalikan mereka di JSONResponseMixin daripada TemplateResponseMixin.

get_messages() akan mengembalikan sebuah instance dari backend penyimpanan dikonfigurasi

Kelas Message

class storage.base.Message

When you loop over the list of messages in a template, what you get are instances of the Message class. They have only a few attributes:

  • message: Teks sebenarnya dari pesan.
  • level: Integer menggambarkan jenis dari pesan (lihat bagian message levels diatas).
  • tags: String memadukan semua etiket pesan (extra_tags dan level_tag) dipisahkan oleh ruang.
  • extra_tags: Sebuah string mengandung etiket-etiket penyesuaian untuk pesan ini, dipisahkan oleh ruang. Itu kosong secara awalan.
  • level_tag: Perwakilan string dari tingkatan. Secara awalan, itu adalah versi huruf kecil dari nama dari ketetapan terkait, tetapi ini dapat berubah jika anda butuh dengan menggunakanpengaturan MESSAGE_TAGS.

Membuat penyesuaian tingkatan pesan

Tingkatan pesan tidak lebih dari integer, jadi anda dapat menentukan ketetapan tingkat anda sendiri dan menggunakan mereka membuat umpan balik pengguna penyesuaian lagi, misalnya:

CRITICAL = 50

def my_view(request):
    messages.add_message(request, CRITICAL, 'A serious error occurred.')

Ketika membuat tingkatan-tingkatan pesan penyesuaian anda harus waspada menghindari tingkatan-tingkatan yang ada kelebihan beban. Nilai-nilai untuk tingkatan-tingkatan siap-pakai adalah:

Tingkat Ketetapan Nilai
DEBUG 10
INFO 20
BERHASIL 25
PERINGATAN 30
KESALAHAN 40

Jika anda buth mencirikan tingkatan penyesuaian dalam HTML atau CSS, anda butuh menyediakan sebuah pemetaan melalui pengaturan MESSAGE_TAGS.

Catatan

Jika anda sedang membuat aplikasi digunakan kembali, itu sangat dianjurkan untuk menggunakan hanya message levels siap-pakai dan jangan bergantung pada penyesuaian tingkat apapun

Merubah tingkat terekam minimal per-permintaan

Tingkat terekam minimal dapat disetel per permintaan melalui metode set_level:

from django.contrib import messages

# Change the messages level to ensure the debug message is added.
messages.set_level(request, messages.DEBUG)
messages.debug(request, 'Test message...')

# In another request, record only messages with a level of WARNING and higher
messages.set_level(request, messages.WARNING)
messages.success(request, 'Your profile was updated.') # ignored
messages.warning(request, 'Your account is about to expire.') # recorded

# Set the messages level back to default.
messages.set_level(request, None)

Mirip, tingkat efektif saat ini dapat diambil dengan get_level:

from django.contrib import messages
current_level = messages.get_level(request)

Untuk informasi lebih pada bagaimana fungsi tingkat terekam minimal, lihat Message levels diatas.

Menambahkan etiket pesan tambahan

Untuk lebih kendali langsung melalui etiket pesan, anda dapat secara pilihan menyediakan string mengandung etiket tambahan ke apapun dari metode tambah:

messages.add_message(request, messages.INFO, 'Over 9000!', extra_tags='dragonball')
messages.error(request, 'Email box full', extra_tags='email')

Etiket tambahan ditambahkan sebelum etiket awalan untuk tingkat itu dan ruang terpisah.

Gagal secara diam ketika kerangka kerja pesan ditiadakan

Jika anda sedang menulis sebuah aplikasi digunakan kembali (atau potongan lain dari kode) dan ingin menyertakan kegunaan pesan, tetapi tidak ingin membutuhkan pengguna anda mengadakan itu jika mereka tidak ingin, anda mungkin melewatkan sebuah argumen kata kunci tambahan fail_silently=True ke apapun dari keluarga add_message dari metode-metode. Sebagai contoh:

messages.add_message(
    request, messages.SUCCESS, 'Profile details updated.',
    fail_silently=True,
)
messages.info(request, 'Hello world.', fail_silently=True)

Catatan

Mengatur fail_silently=True hanya menyembunyikan MessageFailure yang akan sebaliknya muncul ketika kerangka kerja pesan-pesan ditiadakan dan satu usaha untuk menggunakan satu dari keluarga add_message dari metode-metode. Itu tidak menyembunyikan kegagalan yang mungkin muncul untuk alasan-alasan lain.

Menambahkan pesan-pesan di tampilan berdasarkan-kelas

class views.SuccessMessageMixin

Menambah sebuah atribut pesan berhasil pada FormView berdasarkan kelas-kelas

get_success_message(cleaned_data)

cleaned_data adalah data dibersihkan dari formulir yang digunakan untuk pembentukan string

Contoh views.py:

from django.contrib.messages.views import SuccessMessageMixin
from django.views.generic.edit import CreateView
from myapp.models import Author

class AuthorCreate(SuccessMessageMixin, CreateView):
    model = Author
    success_url = '/success/'
    success_message = "%(name)s was created successfully"

Data diberishkan dari form tersedia untuk penambahan string menggunakan sintaksis %(field_name)s. Untuk ModelForms, jika anda butuh mengakses ke bidang-bidang ini dari object tersimpan timpa metode get_success_message().

Contoh views.py untuk ModelForms:

from django.contrib.messages.views import SuccessMessageMixin
from django.views.generic.edit import CreateView
from myapp.models import ComplicatedModel

class ComplicatedCreate(SuccessMessageMixin, CreateView):
    model = ComplicatedModel
    success_url = '/success/'
    success_message = "%(calculated_field)s was created successfully"

    def get_success_message(self, cleaned_data):
        return self.success_message % dict(
            cleaned_data,
            calculated_field=self.object.calculated_field,
        )

Pesan berakhir

Pesan-pesan ditandai untuk dibersihkan ketika contoh penyimpanan diulangkan (dan dibersihkan ketika tanggapan diolah).

Untuk menghindari pesan-pesan sedang dibesihkan, anda dapat menyetel penyimpanan pesan-pesan menjadi False setelah perulangan:

storage = messages.get_messages(request)
for message in storage:
    do_something_with(message)
storage.used = False

Perilaku dari permintaan paralel

Disebabkan oleh cara kue (dan karena itu sesi) bekerja, perilaku backend apapun yang menggunakan kue atau sesi tidak ditentukan ketika klien sama membuat banyak permintaan yang mensetel atau mendapatkan pesan-pesan sejajar. Sebagai contoh, jika sebuah klien memulai sebuah permintaan yang membuat sebuah pesan dalam satu jendela (atau tab) dan kemudian yang mengambil pesan-pesan apapun tidak berstatus di jendela lain, sebelum jendela pertama dialihkan, pesan mungkin muncul dalam jendela kedua darpada jendela pertama dimana itu mungkin diharapkan.

Ringkasnya, ketika permintaan-permintaan terus-menerus banyak dari klien sama dilibatkan, pesan-pesan tidak dijamin untuk dikirimkan ke jendela sama yang maupun membuat mereka, dalam beberapa kasus, sama sekali. Catat bahwa ini adalah khususnya bukan sebuah masalah dalam kebanyakan aplikasi dan akan menjadi bukan-masalah dalam HTML5, dimana setiap jendela/tab akan mempunyai konteks menjelajah milik sendiri.

Pengaturan

Sedikit settings memberikan anda kendali terhadap perilaku pesan:

Untuk backend yang menggunakan kue, pengaturan untuk kue diambil dari pengaturan kue sesi:

Back to Top