2011-12-18 8 views
1

G'dayあります。私は現在、何よりも邪魔されています。以下のコードは、期待どおり完全に動作します。基本的には、URLで受け取った文字列上にモデルを動的に配置するModelFormや、提供されている場合はインスタンスのクラスに基づいています。Djangoフォームクラス変数を入れ子クラスMetaに渡す方法は?

私の質問は、model_name変数を渡して、これを別のモジュールform.pyに抽象化できるかどうかです。モデル名はClass no problemsという形式に渡すことができますが、それ以降はMetaに渡す方法がわかりません。これを行う簡単な方法はありますか?そうしないと、私のビューコードヒープがきれいになります。

@user_passes_test(lambda u: u.is_staff, login_url="%slogin/" % NINJA_ADMIN_URL_PREFIX) 
def content_form(request, model_name=None, edit=False, call_name=''): 
    if edit: 
     content = Content.objects.get(call_name=call_name) 
     model_name = content.fields.__class__.__name__ 

    class ContentForm(forms.ModelForm): 
     parent = ModelTextField(queryset=Content.objects.all(), widget=JQueryAutocomplete(
         source_url='%sjson/call_names.json' % NINJA_ADMIN_URL_PREFIX, jquery_opts = {'minLength': 2}, 
         override_label='item.fields.call_name', override_value='item.fields.call_name'), 
         required=False) 

     class Meta(): 
      model = get_ninja_type(model_name) 
      widgets = { 
        'ninja_type': forms.widgets.HiddenInput(), 
       } 

     def clean_parent(self): 
      call_name = self.cleaned_data['parent'] 
      if call_name: 
       try: 
        parent = Content.objects.get(call_name=call_name) 
       except Content.DoesNotExist: 
        raise forms.ValidationError("The call name '%s' doesn't exist. Choose another parent." % call_name) 
       return parent 
      else: 
       return None 

    if request.method == 'POST': 
     if edit: 
      form = ContentForm(request.POST, instance=content.fields) 
     else: 
      form = ContentForm(request.POST) 
     if form.is_valid(): 
      content = form.save() 
      messages.success(request, "Your new content has been saved.") 
      return HttpResponseRedirect('%scontent/' % NINJA_ADMIN_URL_PREFIX) 

    else: 
     if edit: 
      form = ContentForm(instance=content.fields) 
     else: 
      form = ContentForm(initial={'ninja_type': model_name.lower(), 
            'author': request.user}) 
    if edit: 
     page_title = 'Edit %s' % model_name 
    else: 
     page_title = 'Create New %s' % model_name 

    return render(request, 'ninja/admin/content_form.html', { 
        'form': form, 
        'ninja_type': model_name, 
        'page_title': page_title, 
        'edit': edit, 
        'meta_field_names': NINJA_META_FIELD_NAMES, 
        }) 
+0

私は考えていましたが、多分フォームをクラスを返す関数にラップし、その関数を呼び出すことができました。私はチャンスを得るときにそれを試みます。 – MalucoMarinero

+0

はい、クラスを返す関数はうまく動作します。私はサイトが私にできるようになると、答えのソースを掲示します。 (評判が低すぎる) – MalucoMarinero

答えて

1

私がそれについて考えたとき、答えはかなり明白でした。クラスを返す関数は正常に動作します。これはviews.pyの最初に残っています。私はこれがこれを行うための最良の方法、または少なくとも最も簡潔であると考えています。

@user_passes_test(lambda u: u.is_staff, login_url="%slogin/" % NINJA_ADMIN_URL_PREFIX) 
def content_form(request, model_name=None, edit=False, call_name=''): 
    if edit: 
     content = Content.objects.get(call_name=call_name) 
     model_name = content.fields.__class__.__name__ 

    ContentForm = get_content_form(model_name) 

    if request.method == 'POST': 
     if edit: 
      form = ContentForm(request.POST, instance=content.fields) 
     else: 

これはforms.pyのエントリです。

def get_content_form(model_name): 
    class DynamicContentForm(forms.ModelForm): 
     parent = ModelTextField(queryset=Content.objects.all(), widget=JQueryAutocomplete(
         source_url='%sjson/call_names.json' % NINJA_ADMIN_URL_PREFIX, jquery_opts = {'minLength': 2}, 
         override_label='item.fields.call_name', override_value='item.fields.call_name'), 
         required=False) 

     class Meta(): 
      model = get_ninja_type(model_name) 
      widgets = { 
        'ninja_type': forms.widgets.HiddenInput(), 
       } 

     def clean_parent(self): 
      call_name = self.cleaned_data['parent'] 
      if call_name: 
       try: 
        parent = Content.objects.get(call_name=call_name) 
       except Content.DoesNotExist: 
        raise forms.ValidationError("The call name '%s' doesn't exist. Choose another parent." % call_name) 
       return parent 
      else: 
       return None 
    return DynamicContentForm 
関連する問題