diff --git a/inventree_bulk_plugin/bulkcreate_objects.py b/inventree_bulk_plugin/bulkcreate_objects.py index 1e21f80..5ace594 100644 --- a/inventree_bulk_plugin/bulkcreate_objects.py +++ b/inventree_bulk_plugin/bulkcreate_objects.py @@ -16,7 +16,7 @@ from djmoney.contrib.exchange.models import Rate from stock.models import StockLocation -from part.models import PartCategory, Part, PartParameter, PartParameterTemplate, PartCategoryParameterTemplate, PartAttachment, PartRelated +from part.models import PartCategory, Part, PartParameter, PartParameterTemplate, PartCategoryParameterTemplate, PartRelated from company.models import Company, ManufacturerPart, SupplierPart from stock.models import StockItem from common.models import InvenTreeSetting @@ -503,12 +503,11 @@ def create_object(self, data: ParseChildReturnElement, *, parent: Optional[Part] # create attachments for attachment in attachments: - PartAttachment.objects.create( + self.add_attachment( part=part, link=attachment.get("link", None), comment=attachment["comment"], attachment=self.attachments.get(attachment.get("file_url", None), None), - user=self.request.user, ) # create manufacturer part @@ -625,6 +624,40 @@ def get_stock_status_options(self): def get_currency_default(self): return InvenTreeSetting.get_setting('INVENTREE_DEFAULT_CURRENCY', 'USD') + + def add_attachment(self, part: Part, *, comment: str, link: str, attachment: File): + """Add an attachment to a part. + + Note: This supports the 'legacy' and 'modern' attachment system. + Ref: https://github.com/inventree/InvenTree/pull/7420 + """ + + # first try the modern attachment system + try: + from common.models import Attachment + + Attachment.objects.create( + model_type="part", + model_id=part.pk, + comment=comment, + link=link, + attachment=attachment, + upload_user=self.request.user, + ) + return + except ImportError: # pragma: no cover + # fallback to the legacy attachment system + from part.models import PartAttachment + + PartAttachment.objects.create( + part=part, + link=link, + comment=comment, + attachment=attachment, + user=self.request.user, + ) + except Exception as e: # pragma: no cover + raise e bulkcreate_objects: dict[str, type[BulkCreateObject]] = { diff --git a/inventree_bulk_plugin/tests/integration/test_bulkcreate_objects.py b/inventree_bulk_plugin/tests/integration/test_bulkcreate_objects.py index 4367dd1..793265a 100644 --- a/inventree_bulk_plugin/tests/integration/test_bulkcreate_objects.py +++ b/inventree_bulk_plugin/tests/integration/test_bulkcreate_objects.py @@ -8,12 +8,18 @@ from mptt.models import MPTTModel from company.models import Company, ManufacturerPart, SupplierPart -from part.models import Part, PartCategory, PartParameterTemplate, PartParameter, PartAttachment, PartRelated +from part.models import Part, PartCategory, PartParameterTemplate, PartParameter, PartRelated from stock.models import StockLocation, StockItem from common.models import InvenTreeSetting from ...bulkcreate_objects import get_model, get_model_instance, cast_model, cast_select, FieldDefinition, BulkCreateObject, StockLocationBulkCreateObject, PartCategoryBulkCreateObject, PartBulkCreateObject +# import modern Attachment model, if it exists otherwise fallback to the legacy attachment system +try: + from common.models import Attachment +except ImportError: + from part.models import PartAttachment as Attachment + # custom request factory, used to patch query_params which were not defined by default class CustomRequestFactory(RequestFactory): @@ -399,11 +405,11 @@ def extra_model_tests(self, obj): )) issues.extend(self.model_test( - PartAttachment, + Attachment, obj.fields["attachments"].items_type.fields, f"{obj.template_type}.attachments.[x]", ignore_fields=["file_url", "file_name", "file_headers"], - ignore_model_required_fields=["part"], + ignore_model_required_fields=["part", "model_type", "model_id"], )) issues.extend(self.model_test( @@ -475,7 +481,7 @@ def test_create_objects(self): (ManufacturerPart, 1), (SupplierPart, 1), (StockItem, 1), - (PartAttachment, 3) + (Attachment, 3) ] for model, count in expected_objs: