如何在django-import-export中传递外键gestion至ModelResource并保存
解决方案
要把当前创建的Gestion实例传递给ModelResource并赋值给ItemGestion的外键字段,你可以通过以下步骤实现:
1. 修改Resource类,添加外部参数接收gestion实例
在resources.py中,给ItemResourceResource添加初始化方法接收gestion,并通过before_save钩子在保存每个导入实例前设置该外键:
from import_export import resources, fields from import_export.widgets import ForeignKeyWidget from .models import ItemGestion, Asignacion, Gestion class ItemResourceResource(resources.ModelResource): id_orden = fields.Field( column_name='id_orden', attribute='id_orden', widget=ForeignKeyWidget(Asignacion, 'id_orden') ) def __init__(self, gestion=None): super().__init__() self.gestion = gestion def before_save(self, instance, using_transactions, dry_run): # 给每个导入的ItemGestion实例设置gestion外键 if self.gestion: instance.gestion = self.gestion return super().before_save(instance, using_transactions, dry_run) class Meta: model = ItemGestion import_id_fields = ('id_orden',) exclude = ('idgestion', 'gestion') # 排除gestion,避免从Excel读取
2. 在View中实例化Resource时传入gestion参数
修改view.py的form_valid方法,创建ItemResourceResource实例时把当前的gestion对象传进去:
def form_valid(self, form): isvalid = super().form_valid(form) obj = form.save() # 直接使用form返回的实例,无需重复查询数据库 gestion = obj file = self.request.FILES['file'] # 传入gestion实例初始化Resource item_gestion = ItemResourceResource(gestion=gestion) dataset = Dataset() imported_data = dataset.load(file.read(), format='xls') result = item_gestion.import_data(dataset, dry_run=True) if not result.has_errors(): item_gestion.import_data(dataset, dry_run=False) return isvalid
关键说明
__init__方法:让Resource可以接收外部传入的gestion实例并保存为实例属性。before_save钩子:django-import-export提供的生命周期方法,会在每个模型实例保存前触发,这里用来给ItemGestion实例设置gestion外键。Meta.exclude:把gestion加入排除列表,避免导入时尝试从Excel文件中读取该字段的值(因为它来自外部,不是Excel内容)。- 优化点:原代码中
gestion= Gestion.objects.get(idgestion=obj.pk)可以直接替换为gestion=obj,因为form.save()已经返回了刚保存的Gestion实例,无需再次查询数据库。
内容的提问来源于stack exchange,提问作者cudris
相关产品推荐
相关产品推荐

