Fixed re-adding of previously deleted host and labels from the Django
admin interface.

Risk: low
Visibility: medium (bug fix)

Signed-off-by: James Ren <jamesren@google.com>


git-svn-id: http://test.kernel.org/svn/autotest/trunk@3626 592f7852-d20e-0410-864c-8624ca9c26a4
diff --git a/frontend/afe/admin.py b/frontend/afe/admin.py
index 2123f38..efc97f8 100644
--- a/frontend/afe/admin.py
+++ b/frontend/afe/admin.py
@@ -1,5 +1,6 @@
 """Django 1.0 admin interface declarations."""
 
+from django import forms
 from django.contrib import admin
 from django.db import models as dbmodels
 
@@ -18,18 +19,48 @@
         return field
 
 
+class ModelWithInvalidForm(forms.ModelForm):
+    def validate_unique(self):
+        # Don't validate name uniqueness if the duplicate model is invalid
+        model = self.Meta.model
+        filter_data = {
+                model.name_field : self.cleaned_data[model.name_field],
+                'invalid' : True
+                }
+        needs_remove = bool(self.Meta.model.objects.filter(**filter_data))
+        if needs_remove:
+            name_field = self.fields.pop(model.name_field)
+        super(ModelWithInvalidForm, self).validate_unique()
+        if needs_remove:
+            self.fields[model.name_field] = name_field
+
+
+class AtomicGroupForm(ModelWithInvalidForm):
+    class Meta:
+        model = models.AtomicGroup
+
+
 class AtomicGroupAdmin(SiteAdmin):
     list_display = ('name', 'description', 'max_number_of_machines')
 
+    form = AtomicGroupForm
+
     def queryset(self, request):
         return models.AtomicGroup.valid_objects
 
 admin.site.register(models.AtomicGroup, AtomicGroupAdmin)
 
 
+class LabelForm(ModelWithInvalidForm):
+    class Meta:
+        model = models.Label
+
+
 class LabelAdmin(SiteAdmin):
     list_display = ('name', 'kernel_config')
 
+    form = LabelForm
+
     def queryset(self, request):
         return models.Label.valid_objects
 
@@ -43,6 +74,11 @@
 admin.site.register(models.User, UserAdmin)
 
 
+class HostForm(ModelWithInvalidForm):
+    class Meta:
+        model = models.Host
+
+
 class HostAdmin(SiteAdmin):
     # TODO(showard) - showing platform requires a SQL query for
     # each row (since labels are many-to-many) - should we remove
@@ -52,6 +88,8 @@
     search_fields = ('hostname', 'status')
     filter_horizontal = ('labels',)
 
+    form = HostForm
+
     def queryset(self, request):
         return models.Host.valid_objects
 
@@ -92,11 +130,13 @@
 
     admin.site.register(models.Job, JobAdmin)
 
+
     class IneligibleHostQueueAdmin(SiteAdmin):
         list_display = ('id', 'job', 'host')
 
     admin.site.register(models.IneligibleHostQueue, IneligibleHostQueueAdmin)
 
+
     class HostQueueEntryAdmin(SiteAdmin):
         list_display = ('id', 'job', 'host', 'status',
                         'meta_host')