2011-03-16 20 views
48

tengo una clase definida Forma Django gustos esto en Models:Django ModelChoiceField: filtrado de consulta establecido por defecto y el valor de ajuste como un objeto

class AccountDetailsForm(forms.Form): 
    ... 
    adminuser = forms.ModelChoiceField(queryset=User.objects.all()) 

Esto funciona bien, pero tiene algunas limitaciones me parece que no puede evitar:

(1) me gustaría utilizar un filtro en el queryset, basado en una variable accountid pasado a la forma, como este:

User.objects.filter(account=accountid) 

Esto no puede funcionar en el modelo porque accountid no se puede pasar como una variable, por supuesto.

De esto se deduce que el queryset debe definirse de alguna manera en el Views, pero, por lo que veo, es un campo obligatorio en la clase Form.

(2) Me gustaría hacer la opción por defecto de AccountDetailsForm un objeto en la base de datos, que puedo seleccionar en el Views así:

User.objects.filter(account=accountid).filter(primary_user=1) 

he intentado especificando el adminuser por defecto valor en el formulario, (que trabaja con otros campos del formulario estándar, como CharField):

adminuser = User.objects.filter(account=accountid).filter(primary_user=1) 

... 

form = AccountDetailsForm({'adminuser': adminuser}) 
return render_to_response('accounts/edit/accountdetails.html', 
{'form': form, 'account':account}) 

Pero no hubo suerte.

¿Debo utilizar algo diferente a ModelChoiceField dada la flexibilidad que necesito aquí?

Gracias.

Respuesta

91

reemplazar el método init y aceptar un nuevo argumento de palabra clave

class AccountDetailsForm(forms.Form): 
    ... 
    adminuser = forms.ModelChoiceField(queryset=User.objects.all()) 
    def __init__(self, *args, **kwargs): 
     accountid = kwargs.pop('accountid', None) 
     super(AccountDetailsForm, self).__init__(*args, **kwargs) 

     if accountid: 
      self.fields['adminuser'].queryset = User.objects.filter(account=accountid) 

form = AccountDetailsForm(accountid=3) 

Usted siempre puede configurar las opciones manualmente en la vista también.

form = AccountDetailsForm() 
form.fields['adminuser'].queryset = User.objects.filter(account=accountid) 

se advirtió: usted es no valores por defecto de ajuste por los que pasa en un diccionario a una forma como en su ejemplo.

En realidad está creando un Bound Form, lo que podría desencadenar la validación y todo ese jazz.

Para establecer los valores predeterminados, use the initials argument.

form = AccountDetailsForm(initial={'adminuser':'3'}) 
+0

Hola, gracias por su respuesta. Configurar el queryset en la vista funcionó bien. La parte que no pude resolver es establecer el valor del formulario enlazado (en lugar del valor predeterminado) de ModelChoiceField como _User.objects.filter (account = accountid) .filter (primary_user = 1) _. Gracias. – eli

6

Puede anular el campo en la vista

yourForm = AccountDetailsForm() 

yourForm.fields['accomodation'] = forms.ModelChoiceField(User.objects.filter(account=accountid).filter(primary_user=1)) 
Cuestiones relacionadas