Giriş.
Django’nun yerleşik gelen admin paneli, uygulamanız genelinde bulunan modelleri yönetmek için işlevsel ve ihtiyaçlar doğrultusunda özelleştirilmeye çok açık.
Bugün, Django admin panelinde modeller üzerinde daha önce muhtemelen kullandığınız aksiyonlar üzerine konuşacağız. Aksiyonlar modeller üzerinde toplu işlemler yapmanıza olanak verir ve varsayılan olarak sadece seçilen nesneleri toplu silme işlemi tanımlıdır.
Isınma turu.
Toplu işlemlerde kullanılmak üzere modeladmin sınıfına aksiyon yazmanın 2 farklı yolu bulunmakta.
- Aksiyonu, model adminden bağımsız bir fonksiyon olarak yazmak ve model admine kayıt etmek.
- Aksiyonu doğrudan model admin sınıfının bir metodu olarak tanımlamak, ve model admine kayıt etmek.
2 yöntemi de hızlıca inceleyeceğiz fakat, örnek olması açısından iş takibi yaptığımız bir uygulamamız ve aşağıdaki gibi bir modelimiz olduğunu varsayalım.
models.py
from django.db import models from django.conf import settings class TicketStatuses(models.IntegerChoices): APPROVED = 1 IN_PROGRESS = 2 TEST = 3 RELEASED = 4 CLOSED = 5 class Ticket(models.Model): reporter = models.ForeignKey( settings.AUTH_USER_MODEL, on_delete=models.SET_NULL, null=True, limit_choices_to={"is_staff": True}, related_name="reported_tickets", ) assignee = models.ForeignKey( settings.AUTH_USER_MODEL, on_delete=models.SET_DEFAULT, default=1, related_name="assigned_tickets", ) title = models.CharField(max_length=255) description = models.TextField() status = models.PositiveSmallIntegerField( choices=TicketStatuses.choices, default=TicketStatuses.APPROVED ) created = models.DateTimeField(auto_now_add=True) modified = models.DateTimeField(auto_now=True) def __str__(self) -> str: return self.title
admin.py
from your_app.models import Ticket from django.contrib import admin class TicketAdmin(admin.ModelAdmin): list_display = ["title", "assignee", "reporter", "status"] admin.site.register(Ticket, TicketAdmin)
Yukarıdaki gibi basit bir model admin oluşturup kayıt ettikten sonra aşağıdaki gibi bir görünüm elde ettik.
Aksiyon yazmak.
Aksiyon yazmanın 2 farklı yolu olduğundan bahsetmiştik. İki kullanımı da görebilme adına aşağıdaki gibi 2 adet yeni ihtiyacımız olsun ve bu ihtiyaçları çözecek aksiyonları yazalım.
- Seçilen tüm ticketları CLOSED statüsüne çekmek istiyoruz.
- Seçilen tüm ticketları kendi üzerimize assigne etmek istiyoruz.
Aksiyonu fonksiyon olarak yazmak.
Fonksiyon olarak yazılan aksiyonlar 3 parametre alır. Bunları sırası ile üzerinde çalışılan modeladmin sınıfı, request nesnesi, ve üzerinde çalışılacak olan queryset.
from django.db.models import QuerySet from django.http.request import HttpRequest from tickets.models import Ticket, TicketStatuses from django.contrib import admin def close_tickets(modeladmin: admin.ModelAdmin, request: HttpRequest, queryset: QuerySet): queryset.update(status=TicketStatuses.CLOSED) close_tickets.short_description = "Close the selected tickets."
Aksiyon fonksiyonunu yazdıktan sonra model admin sınıfına kayıt işlemini yapmamız gerekmekte. Aksi halde aksiyon kullanılmaz durumda olacaktır.
class TicketAdmin(admin.ModelAdmin): list_display = ["title", "assignee", "reporter", "status"] actions = [close_tickets]
Bu işlemden sonra admin paneline dönecek olursak ve seçilen ticketlarda bu aksiyonu koşturur isek toplu olarak statülerin CLOSED ile değiştiğini görebilirsiniz.
Eğer aksiyonunuza short_description olarak okunabilir bir açıklama vermez iseniz Django fonksiyon isminizi _ (alttan tire) ayıracak ve okunabilir açıklama türetmeye çalışacaktır.
Aksiyonu modeladmin metodu olarak yazmak.
Bir diğer yöntem olarak doğrudan model admine, bir metod olarak yazmaya göz atalım. Açıkcası ben bu kullanımı daha temiz buluyorum. Devam edelim.
Seçilen tüm ticketları işlemi yapan kullanıcıya atamak istiyoruz. Aşağıdak gibi bir metod yazalım ve kayıt edelim.
# above has not changed. class TicketAdmin(admin.ModelAdmin): list_display = ["title", "assignee", "reporter", "status"] actions = [close_tickets, "assign_to_me"] def assign_to_me(self, request: HttpRequest, queryset: QuerySet): user = request.user queryset.update(assignee=user) assign_to_me.short_description = "Assign selected tickets to me."
Kayıt ederken metod isminin string olduğuna ve parametre olarak, model admin yerine doğrudan içinde bulunduğu modeladmin sınıfını self ile belirttiğimizi dikkat edelim.
İpucu.
Eğer işlem sonucunda işlemi yapan kullanıcıya mesaj ile bir geri bildirim sağlamak isterseniz metodu şu şekilde güncelleyebilirisiniz. Aynı işlemi fonksiyon olarak yazdığımız aksiyonda modeladmin nesnesi üzerinden de yapabilirsiniz.
# not changed. def assign_to_me(self, request: HttpRequest, queryset: QuerySet): user = request.user queryset.update(assignee=user) self.message_user( request, f"{queryset.count()} tickets have been successfully assigned to you.", )
Test edelim.
Sonuç.
Django admin paneli ihtiyaçlara göre kolayca özelleştirilebiliyor. Fakat tabi ki yapılabilecekler bu kadar ile sınırlı değil. Daha fazla bilgi almak isterseniz dökümantasyon linki burada.
Bunun yanında aksiyonlar ile bir export mekanizması kurgulamak isterseniz, şu yazıdaki adımları takip ederek export mekanizmasını oluşturup bir aksiyona bağlayabilirsiniz.
Görüşmek üzere!
İlk Yorumu Siz Yapın