Ketika saya meminta manajer model untuk mendapatkan objek, itu muncul DoesNotExist
ketika tidak ada objek yang cocok.
go = Content.objects.get(name="baby")
Alih-alih DoesNotExist
, bagaimana saya bisa go
menjadi None
gantinya?
python
django
django-queryset
TIMEX
sumber
sumber
SomeModel.objects.filter(foo='bar').first()
ini mengembalikan pertandingan pertama, atau Tidak Ada. Tidak gagal jika ada beberapa contoh sepertiqueryset.get()
filter().first()
saya pikir pengecualian adalah cara untuk pergi.Sejak django 1.6 Anda dapat menggunakan metode first () seperti:
sumber
Dari django docs
Anda dapat menangkap pengecualian dan menetapkan
None
untuk pergi.sumber
Anda dapat membuat fungsi generik untuk ini.
Gunakan ini seperti di bawah ini:
go akan menjadi None jika tidak ada entri yang cocok dengan yang lain akan mengembalikan entri Konten.
Catatan: Ini akan memunculkan pengecualian MultipleObjectsReturned jika lebih dari satu entri dikembalikan untuk name = "baby"
sumber
Anda bisa melakukannya dengan cara ini:
Variabel go sekarang bisa berupa objek yang Anda inginkan atau Tidak Ada
Ref: https://docs.djangoproject.com/en/1.8/ref/models/querysets/#django.db.models.query.QuerySet.first
sumber
Untuk mempermudah, berikut cuplikan kode yang saya tulis, berdasarkan masukan dari balasan yang indah di sini:
Dan kemudian dalam model Anda:
Itu dia. Sekarang Anda memiliki MyModel.objects.get () serta MyModel.objetcs.get_or_none ()
sumber
Anda dapat menggunakan
exists
dengan filter:hanya alternatif untuk jika Anda hanya ingin tahu apakah itu ada
sumber
Note: If you only want to determine if at least one result exists (and don’t need the actual objects), it’s more efficient to use exists().
exists()
akan digunakan denganif
klausa sebelum mengambil objek sehingga menyebabkan pukulan ganda ke db. Saya akan tetap menyimpan komentar kalau-kalau itu membantu orang lain.Menangani pengecualian pada titik yang berbeda dalam tampilan Anda bisa sangat merepotkan..Bagaimana dengan mendefinisikan Manajer Model kustom, dalam file models.py, seperti
dan kemudian memasukkannya ke dalam kelas Model konten
Dengan cara ini dapat dengan mudah ditangani dalam pandangan yaitu
sumber
return self.get(**kwargs)
agar berfungsi untuk saya. Bukan untuk mengatakan ada yang salah dengan jawabannya, hanya tip bagi siapa pun yang mencoba menggunakannya dengan versi yang lebih baru (atau dengan apa pun yang membuatnya tidak bekerja untuk saya).Ini salah satu fungsi menjengkelkan yang mungkin tidak ingin Anda laksanakan kembali:
sumber
get_object_or_None
tetapi ternyata masih naikMultipleObjectsReturned
jika lebih dari satu objek. Jadi, pengguna mungkin mempertimbangkan untuk mengelilinginya dengantry-except
(yang fungsinya sendiritry-except
sudah ada).Jika Anda menginginkan solusi satu baris sederhana yang tidak melibatkan penanganan pengecualian, pernyataan bersyarat atau persyaratan Django 1.6+, lakukan ini sebagai gantinya:
sumber
Saya pikir itu bukan ide yang buruk untuk digunakan
get_object_or_404()
Contoh ini setara dengan:
Anda dapat membaca lebih lanjut tentang get_object_or_404 () di dokumentasi online Django.
sumber
Dari django 1.7 dan selanjutnya Anda dapat melakukan seperti:
Keuntungan dari "MyQuerySet.as_manager ()" adalah bahwa kedua hal berikut ini akan berfungsi:
sumber
Berikut adalah variasi pada fungsi helper yang memungkinkan Anda untuk secara opsional mengirimkan
QuerySet
contoh, jika Anda ingin mendapatkan objek unik (jika ada) dari queryset selain modelall
objek queryset (misalnya dari subset item anak yang dimiliki oleh sebuah instance induk):Ini dapat digunakan dalam dua cara, misalnya:
obj = get_unique_or_none(Model, **kwargs)
seperti yang telah dibahas sebelumnyaobj = get_unique_or_none(Model, parent.children, **kwargs)
sumber
Tanpa pengecualian:
Menggunakan pengecualian:
Ada sedikit argumen tentang kapan seseorang harus menggunakan pengecualian dalam python. Di satu sisi, "lebih mudah untuk meminta maaf daripada izin". Sementara saya setuju dengan ini, saya percaya bahwa pengecualian harus tetap, well, pengecualian, dan "kasus ideal" harus berjalan tanpa memukul satu pun.
sumber
Kita dapat menggunakan pengecualian builtin Django yang melekat pada model bernama
.DoesNotExist
. Jadi, kita tidak perlu mengimporObjectDoesNotExist
pengecualian.Alih-alih melakukan:
Kita bisa melakukan ini:
sumber
Ini adalah peniru dari get_object_or_404 Django kecuali bahwa metode mengembalikan Tidak ada. Ini sangat berguna ketika kita harus menggunakan
only()
kueri untuk hanya mengambil bidang tertentu. Metode ini dapat menerima model atau queryset.sumber
Mungkin lebih baik Anda gunakan:
sumber