我对admin通用内联表单有一些奇怪的问题。我有两个模型,主要项目和视频与 ManyToMany关系通过VideoLink,因为我需要能够将不同数量的视频链接到项目和许多项目到视频:
class VideoLink(models.Model):
content_type = models.ForeignKey(ContentType)
object_id = models.PositiveIntegerField()
content_object = generic.GenericForeignKey('content_type', 'object_id')
video = models.ForeignKey(Video)
class Project(models.Model):
name = models.CharField(max_length=50)
image_set = generic.GenericRelation('Image')
我没有在这里展示视频模型,但这对我的问题并不重要。
我需要的是以两种方式定义链接到主对象(Project)的新相关对象(VideoLink):
对于第二种情况,我需要设置中间功能。它将处理新视频的网址(如http://www.youtube.com/watch?v=WIXVzeB0DUo),创建新的视频对象并与youtube.com同步。我认为最好的方法 - 把它放到AdminVideoLink的表单 clean method 中,我是对的吗?
所以,我写了这段代码:
class VideoForm(forms.ModelForm):
# new field for absolute video urls
video_url = forms.CharField()
def clean(self):
cleaned_data = self.cleaned_data
if not cleaned_data.get('id') and not cleaned_data.get('video') and cleaned_data.get('video_url'):
... some extra functionality:
1) get id from video_url
2) create new Video object with id
3) define cleaned_data['video'] = <Video object>
....
return cleaned_data
class VideoInline(generic.GenericTabularInline):
model = VideoLink
form = VideoForm
class ProjectAdmin(admin.ModelAdmin):
inlines = [VideoInline]
但是每次表单保存后,我都会在管理内联表单中看到错误:在视频对象附近选择 - “字段是必需的”(我的翻译)。但我在我的干净方法中设置了这个字段。我检查一下:self.cleaned_data ['video']包含刚刚创建的新视频对象 和同步。
另一个非常奇怪的问题:我在 clean方法中找不到父实例(主Project对象)。如果我使用简单的ManyToMany对象(没有泛型关系和generic.GenericTabularInline表单)做同样的事情,我会在我的内联表单中看到视频和项目字段,但在通用情况下我没有它。
我检查了相关的post,但未找到答案。
答案 0 :(得分:0)
解决这个问题非常简单,只需将 required = False 添加到内联表单中:
class VideoForm(forms.ModelForm):
video_url = forms.CharField(required=False, widget=AdminVideoPreviewWidget())
def __init__(self, *args, **kwargs):
super(VideoForm, self).__init__(*args, **kwargs)
self.fields['video'].required = False
....
有了它,我可以在创建和同步新的Video对象后手动填充视频字段。