4

ModelForm の特定のフィールドを更新しようとしていますが、これらのフィールドは修正されていません。(tutorビューによって自動入力されるのはそれだけです)

モデル:

class Session(models.Model):
  tutor = models.ForeignKey(User)
  start_time = models.DateTimeField()
  end_time = models.DateTimeField()
  status = models.CharField(max_length=1)

形:

class SessionForm(forms.ModelForm):
  class Meta:
    model = Session
    exclude = ['tutor']

特定のセッションでは、 のみを更新する必要がある場合もあればend_timestart_time&のみを更新する必要がある場合もありend_timeます。

ビューでそれを行うにはどうすればよいですか?


編集

例を示しましたが、これらの例に限定されません。更新する必要があるフィールドは事前定義されていません。任意のフィールドを更新できる必要があります

4

4 に答える 4

10

私は以前に似たようなことをしなければならなかった. 実行時に型を動的に作成し、その型を使用する必要があります。一部のドキュメントについては、django の DynamicModels を参照してください。

さあ、あなたの要件。

  • フォームを使用してモデルを更新できるようにしたい
  • 実行時に更新するフィールドを選択的に指定したい

したがって、いくつかのコード:

def create_form(model, field_names):
    # the inner class is the only useful bit of your ModelForm
    class Meta:
        pass
    setattr(Meta, 'model', model)
    setattr(Meta, 'include', field_names)
    attrs = {'Meta': Meta}

    name = 'DynamicForm'
    baseclasses = (forms.ModelForm,)
    form = type('DynamicForm', baseclasses, attrs)
    return form

def my_awesome_view(request):
    fields = ['start_time', 'end_time']
    form = create_form(Session, fields)
    # work with your form!
于 2012-04-19T14:19:13.713 に答える
1

フォーム フィールドを null 許容として配置し、「クリーンな」メソッドを使用してフィールドにロジックを追加できます。例:

class SessionForm(forms.ModelForm):
    def clean_end_date(self):
        cd = self.cleaned_data
        if (cd["start_date"] and cd["end_date"]) and cd["end_date"] < cd["start_date"]:
            raise forms.ValidationError("WTF?!")
        if not (cd["start_date"] or cd["end_date"]):
            raise forms.ValidationError("need one date")
        return cd['end_date']

値を変更する場合は、return ステートメントに別の値を使用します。

これは、検証に必要な場合があります。

必要に応じて、ビューで GET 辞書をコピーし、フォームをインスタンス化する前に値を更新できます。

def my_view(request):
    r_data = request.GET.copy()
    r_data.merge(request.POST)

    data = dict([(key, my_function(key, value)) for key, value in r_data.iteritems() if key in MyForm.fields])
    form = MyForm(data=data)
    [...]

それが役立つことを願っています。

于 2012-04-19T08:22:03.573 に答える
0

次のようにフォームのコンストラクターを呼び出すことができます。

class SessionForm(forms.ModelForm):
    class Meta:
        model = Session
        exclude = ['tutor', 'start_time']

    def __init__(self, your_extra_args, *args, **kwargs):
        super(SessionForm, self).__init__(*args, **kwargs)
        if need_end_time_start_time(your_extra_args):
            self.fields['start_time'] = forms.DateTimeField()     

このクラスを使用するには、引数「your_extra_args」をフォームに渡す必要があります。

session_form = SessionForm('foo')
于 2012-04-19T09:16:54.843 に答える
0

Your question suggests that you have a requirement that uses same model but different fields are hidden in your ModelForm, based on your needs.

If I understand your question, then you need to Create two different ModelForm based class, both these classes have same model value inside the Meta class. Exclude and include the fields you need. So now you have different ModelForm classes which you can call inside your view logic.

With this you will have two different forms that depend on same model, with different default fields.

With clever url and view design you will be able to use the above idea to serve multiple forms from same model.

于 2014-02-03T13:11:04.683 に答える