2010-10-04 19 views
6

Si prega di consultare il codice qui sotto. Fondamentalmente, quando l'utente crea un oggetto di questa classe, è necessario specificare lo value_type. Se value_type==2 (percentuale), quindi percentage_calculated_on (che è un CheckboxSelectMultiple sul lato modulo/modello deve avere uno o più elementi controllati. La convalida del modello non mi consente di convalidare come sto provando, fondamentalmente genera un eccezione che mi dice che l'istanza deve avere un valore di chiave primaria prima di poter usare una relazione molti-a-molti.Ma devo prima convalidare l'oggetto prima di salvarlo.Ho provato questa convalida sul lato form (modelform) (utilizzando il metodo pulito del form), ma la stessa cosa accade anche lì.django manytomany validation

Come posso fare per il raggiungimento di questo convalida?

INHERENT_TYPE_CHOICES = ((1, 'Payable'), (2, 'Deductible')) 
VALUE_TYPE_CHOICES = ((1, 'Amount'), (2, 'Percentage')) 

class Payable(models.Model): 
    name = models.CharField() 
    short_name = models.CharField() 
    inherent_type = models.PositiveSmallIntegerField(choices=INHERENT_TYPE_CHOICES) 
    value = models.DecimalField(max_digits=12,decimal_places=2) 
    value_type = models.PositiveSmallIntegerField(choices=VALUE_TYPE_CHOICES) 
    percentage_calculated_on = models.ManyToManyField('self', symmetrical=False) 

    def clean(self): 
     from django.core.exceptions import ValidationError 
     if self.value_type == 2 and not self.percentage_calculated_on: 
      raise ValidationError("If this is a percentage, please specify on what payables/deductibles this percentage should be calculated on.") 
+0

Ho segnato la risposta di Manoj Govindan come "accettata" in quanto risolve il problema. Tuttavia, mi piacerebbe averlo convalidato usando la convalida del modello di Django. Quindi se qualcuno ha qualche idea, fai lo sforzo di postarlo qui. Grazie. – chefsmart

+0

stessa domanda: http://stackoverflow.com/questions/7986510/django-manytomany-model-validation – user920391

risposta

2

ho provato il codice in uno dei miei proje app amministratore di cts. Sono stato in grado di eseguire la convalida richiesta utilizzando un numero personalizzato ModelForm. Vedi sotto.

# forms.py 
class MyPayableForm(forms.ModelForm): 
    class Meta: 
     model = Payable 

    def clean(self): 
     super(MyPayableForm, self).clean() # Thanks, @chefsmart 
     value_type = self.cleaned_data.get('value_type', None) 
     percentage_calculated_on = self.cleaned_data.get(
      'percentage_calculated_on', None) 
     if value_type == 2 and not percentage_calculated_on: 
      message = "Please specify on what payables/deductibles ..." 
      raise forms.ValidationError(message) 
     return self.cleaned_data 

# admin.py 
class PayableAdmin(admin.ModelAdmin): 
    form = MyPayableForm 

admin.site.register(Payable, PayableAdmin) 

L'applicazione Admin utilizza il widget SelectMultiple (piuttosto che CheckboxSelectMultiple come si fa) per rappresentare molti a molti rapporti. Credo che questo non dovrebbe avere importanza.

+0

Errr ... è 'model' davvero un attributo di' admin.ModelAdmin'? –

+0

@Dominic: Certamente non lo è: P Grazie per avermelo fatto notare. L'ho risolto –

+0

Sto facendo qualcosa di simile all'interno del mio ModelForm, tranne che prima chiamo super (MyPayableForm, self) .clean() e uso invece self.instance.value_type e self.instance.percentage_calculated_on. – chefsmart