2013-08-15 1 views
4

ModelForm에 인스턴스가 주어진 것처럼 사용자가 initial에 제공 한 모든 값을 무시하고 대신 인스턴스의 값으로 설정합니다 인스턴스는 빈 모델 레코드입니다.인스턴스가 주어질 때 ModelForm의 초기 값을 설정하는 방법

인스턴스가 인 양식을 만드는 방법은 초기 데이터를 설정 했습니까?

관련 레코드를 저장하고있어 ModelForm에 인스턴스를 만들지 않으면 올바르게 저장되지 않기 때문에이 파일이 필요합니다.

나는 이것에 대한 답이 간단하고 확실한 무엇인가를 놓치고 있다고 확신한다. 뷰

:

여기서 중요한 코드

form = form_class(person=person, conference=conference, initial=initial, instance=registration) 
form_class은 RegistrationForm 후 등록 형태

:

class RegisterForm(forms.ModelForm): 
    ... fields here ... 

    def __init__(self, *args, **kwargs): 
     ... other code ... 
     self.person = kwargs.pop('person') 
     super(RegisterForm, self).__init__(*args, **kwargs) 
     for key, in self.fields.keys(): 
      if hasattr(self.person, key): 
       self.fields[k].initial = getattr(self.person, key) 

그럼 필드를 호출 할 때 관련 필드는 비어 있습니다.

답변

4

Google 검색 결과 조금만 나온 것입니다.

super을 호출하기 전에 초기 값을 설정해야합니다.

그래서 그 대신 self.fields.keys() 통해 반복, 내가 원하는과를 통해 루프 필드의 목록을 입력했다 그 대신 :

class RegisterForm(forms.ModelForm): 
    ... fields here ... 
    initial_fields = ['first_name', 'last_name', ... ] 

    def __init__(self, *args, **kwargs): 
     ... other code ... 
     self.person = kwargs.pop('person') 
     for key in self.initial_fields: 
      if hasattr(self.person, key): 
       self.fields[k].initial = getattr(self.person, key) 
     super(RegisterForm, self).__init__(*args, **kwargs) 

@Daria은 당연히 당신이 호출하기 전에 self.fields이 없다는 지적 감독자. 나는이 작동 확신 :.이 버전에서

class RegisterForm(forms.ModelForm): 
    ... fields here ... 
    initial_fields = ['first_name', 'last_name', ... ] 

    def __init__(self, *args, **kwargs): 
     ... other code ... 
     initial = kwargs.pop('initial', {}) 
     self.person = kwargs.pop('person') 
     for key in self.initial_fields: 
      if hasattr(self.person, key): 
       initial[key] = initial.get(key) or getattr(self.person, key) 
     kwargs['initial'] = initial 
     super(RegisterForm, self).__init__(*args, **kwargs) 

, 우리는의 값을 전달하는 initial 인수를 사용 또한 쓰여 그래서 우리는 이미, 우리 돈 해당 필드의 초기에 값이있는 경우 그것을 덮어 쓰지 않습니다.

+1

그런 다음 당신이 당신의 자신의 대답 – karthikr

+1

을 받아 들여야 "당신은 두 가지의 답변을 받아 들일 수 일. " :) –

+0

슈퍼 생성자를 호출하기 전에 self.fields가 없습니다. – Daria

0

초기화 할 때 클래스에 추가 변수를 전달할 수도 있습니다. 전달한 값은 초기 또는 POST 데이터를 대체 할 수 있습니다.

class RegisterForm(forms.ModelForm): 
    ... fields here ... 

    def __init__(self, person, conference, *args, **kwargs): 
     ... other code ... 
     super(RegisterForm, self).__init__(*args, **kwargs) 
     self.fields['person'] = person 
     self.fields['conference'] = conference 

form = RegisterForm(person, conference, initial=initial, instance=registration) 
+0

이것을 잘못 읽지 않는 한, 필드를 모델의 값으로 바꿉니다. 실제로이 작업을 수행하려는 유스 케이스는 생각할 수 없습니다. –

+0

초기 및 인스턴스 데이터는 뷰에서 (또는 폼 인스턴스가 생성되는 모든 곳에서) 명시 적으로 전달 된 값인'super (RegisterForm, self) .__ init __ (* args, ** kwargs)'로 전달됩니다. 'conference'는'initial'과'instance'를 모두 오버라이드 할 것입니다. – Tom

+3

코드를 읽으십시오. 'self.fields [ 'person']'를'person'에 포함 된 값으로 설정합니다. 'self.fields [ 'person']'는 필드였습니다. '사람 '은 아니었다. 아마 당신은 자기를 의미 했나? '사람'. 왜냐하면 폼의 필드 중 하나를 레코드로 바꾸려는 상황을 생각할 수 없기 때문입니다. –

0

제본 된 양식을 찾고있을 수도 있습니다. 확실하지는 않지만 유사한 문제를 해결하려고합니다.

장고 양식은 이러한 종류의 것을 제어하는 ​​두 개의 인수로 인스턴스화 할 수 있습니다. I 그것을 이해 :

form = MyForm(initial={...}, data={...}, ...) 

최초의 필드와 같은 폼의 실제 (또는 선택) 값을 설정하고, 결합 양식을 작성하는 queryset-에게 데이터 설정 용 가능한 값을 설정한다. 어쩌면 그게 네가 원하는거야.흥미로운 찾을 수있는 또 다른, tangental, 포인트는 생성자가 아닌 공장 방법을 고려하는 것입니다, 내가 생각하는 구문이 더 자연 :

class MyForm(forms.ModelForm): 

    ... 

    @staticmethod 
    def makeBoundForm(user): 
     myObjSet = MyObject.objects.filter(some_attr__user=user) 
     if len(myObjSet) is not 0: 
      data = {'myObject': myObjSet[0]} 
     else: 
      raise ValueError() 
     initial = {'myObject': myObjSet} 
     return MyForm(initial=initial, data=data) 
+0

정확히는 아닙니다. 이 경우 다른 모델의 입력란을 사용하여 한 종류의 모델에 대해 일부 입력란을 미리 채우는 것처럼 보입니다. 예를 들어 해당 사용자의 기존 주소를 기반으로 한 주문의 주소 필드를 채 웁니다. –

+0

글쎄요, 글쎄요, 제가 생각하기에 당신이 여전히 기본적인 부분을 적용 할 수있을 것 같아요. 이 [페이지] (http://stackoverflow.com/questions/21925671/convert-django-model-object-to-dict-with-all-of-the-fields-intact)는 모델을 사전은 일반적인 방법으로 (어려운 문제는 아니지만 약간의 시간을 절약해야 함) 일단 사전이 있으면 원하지 않는 필드를 제거하고 _data_ 인수로 제공 할 수 있습니다. 이것은 _instance_에 대한 대안이라고 생각합니다.이 초기화는 사용 된 양식 초기화 데이터를보다 잘 제어합니다. –

관련 문제