admin.py 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195
  1. # -*- coding: utf-8 -*-
  2. from __future__ import unicode_literals
  3. from django.contrib import admin
  4. from django.contrib.auth import get_user_model
  5. from django.forms import ModelChoiceField
  6. from django.utils import timezone
  7. import autocomplete_light
  8. from .models import ItemType, Item, Loan, Storage
  9. import coin.members.admin
  10. User = get_user_model()
  11. admin.site.register(ItemType)
  12. class OwnerFilter(admin.SimpleListFilter):
  13. title = "Propriétaire"
  14. parameter_name = 'owner'
  15. def lookups(self, request, model_admin):
  16. owners = [
  17. (i.pk, i) for i in User.objects.filter(items__isnull=False)]
  18. return [(None, "L'association")] + owners
  19. def queryset(self, request, queryset):
  20. if self.value():
  21. return queryset.filter(owner__pk=self.value())
  22. else:
  23. return queryset
  24. class AvailabilityFilter(admin.SimpleListFilter):
  25. title = "Disponibilité"
  26. parameter_name = 'availability'
  27. def lookups(self, request, model_admin):
  28. return [
  29. ('available', 'Disponible'),
  30. ('borrowed', 'Emprunté'),
  31. ('deployed', 'Déployé'),
  32. ]
  33. def queryset(self, request, queryset):
  34. if self.value() == 'available':
  35. return queryset.available()
  36. elif self.value() == 'borrowed':
  37. return queryset.borrowed()
  38. elif self.value() == 'deployed':
  39. return queryset.deployed()
  40. else:
  41. return queryset
  42. @admin.register(Item)
  43. class ItemAdmin(admin.ModelAdmin):
  44. list_display = (
  45. 'designation', 'type', 'mac_address', 'serial', 'owner',
  46. 'buy_date', 'deployed', 'is_available', 'storage')
  47. list_filter = (
  48. AvailabilityFilter, 'type__name', 'storage',
  49. 'buy_date', OwnerFilter)
  50. search_fields = (
  51. 'designation', 'mac_address', 'serial',
  52. 'owner__email', 'owner__nickname',
  53. 'owner__first_name', 'owner__last_name')
  54. save_as = True
  55. actions = ['give_back']
  56. form = autocomplete_light.modelform_factory(Loan, fields='__all__')
  57. def give_back(self, request, queryset):
  58. for item in queryset.filter(loans__loan_date_end=None):
  59. item.give_back()
  60. give_back.short_description = 'Rendre le matériel'
  61. class StatusFilter(admin.SimpleListFilter):
  62. title = 'Statut'
  63. parameter_name = 'status'
  64. def lookups(self, request, model_admin):
  65. return [
  66. ('all', 'Tout'),
  67. (None, 'En cours'),
  68. ('finished', 'Passés'),
  69. ]
  70. def choices(self, cl):
  71. for lookup, title in self.lookup_choices:
  72. yield {
  73. 'selected': self.value() == lookup,
  74. 'query_string': cl.get_query_string({
  75. self.parameter_name: lookup,
  76. }, []),
  77. 'display': title,
  78. }
  79. def queryset(self, request, queryset):
  80. v = self.value()
  81. if v in (None, 'running'):
  82. return queryset.running()
  83. elif v == 'finished':
  84. return queryset.finished()
  85. else:
  86. return queryset
  87. class BorrowerFilter(admin.SimpleListFilter):
  88. title = 'Adhérent emprunteur'
  89. parameter_name = 'user'
  90. def lookups(self, request, model_admin):
  91. users = set()
  92. for loan in model_admin.get_queryset(request):
  93. users.add((loan.user.pk, loan.user))
  94. return users
  95. def queryset(self, request, queryset):
  96. if self.value():
  97. return queryset.filter(user=self.value())
  98. else:
  99. return queryset
  100. class ItemChoiceField(ModelChoiceField):
  101. # On surcharge cette méthode pour afficher mac et n° de série dans le menu
  102. # déroulant de sélection d'un objet dans la création d'un prêt.
  103. def label_from_instance(self, obj):
  104. return obj.designation + ' ' + obj.get_mac_and_serial()
  105. @admin.register(Loan)
  106. class LoanAdmin(admin.ModelAdmin):
  107. list_display = ('item', 'get_mac_and_serial', 'user', 'loan_date', 'loan_date_end')
  108. list_filter = (StatusFilter, BorrowerFilter, 'item__designation')
  109. search_fields = (
  110. 'item__designation',
  111. 'user__nickname', 'user__username',
  112. 'user__first_name', 'user__last_name', )
  113. actions = ['end_loan']
  114. def end_loan(self, request, queryset):
  115. queryset.filter(loan_date_end=None).update(
  116. loan_date_end=datetime.now())
  117. end_loan.short_description = 'Mettre fin au prêt'
  118. form = autocomplete_light.modelform_factory(Loan, fields='__all__')
  119. def formfield_for_foreignkey(self, db_field, request, **kwargs):
  120. if db_field.name == 'item':
  121. kwargs['queryset'] = Item.objects.all()
  122. return ItemChoiceField(**kwargs)
  123. else:
  124. return super(LoanAdmin, self).formfield_for_foreignkey(db_field, request, **kwargs)
  125. @admin.register(Storage)
  126. class StorageAdmin(admin.ModelAdmin):
  127. list_display = ('name', 'truncated_notes', 'items_count')
  128. def truncated_notes(self, obj):
  129. if len(obj.notes) > 50:
  130. return '{}…'.format(obj.notes[:50])
  131. else:
  132. return obj.notes
  133. truncated_notes.short_description = 'notes'
  134. class LoanInline(admin.TabularInline):
  135. model = Loan
  136. extra = 0
  137. exclude = ('notes',)
  138. readonly_fields = ('item', 'get_mac_and_serial', 'loan_date', 'loan_date_end', 'is_running')
  139. show_change_link = True
  140. def get_queryset(self, request):
  141. qs = super(LoanInline, self).get_queryset(request)
  142. return qs.order_by('-loan_date_end')
  143. def has_add_permission(self, request, obj=None):
  144. return False
  145. def has_delete_permission(self, request, obj=None):
  146. return False
  147. class MemberAdmin(coin.members.admin.MemberAdmin):
  148. inlines = coin.members.admin.MemberAdmin.inlines + [LoanInline]
  149. admin.site.unregister(coin.members.admin.Member)
  150. admin.site.register(coin.members.admin.Member, MemberAdmin)