2
0
mirror of https://github.com/inventree/InvenTree.git synced 2025-07-01 03:00:54 +00:00

Refctor image downloader (#3393)

* Adds configurable setting for maximum remote image size

* Add helper function for downloading image from remote URL

- Will replace existing function
- Performs more thorough sanity checking

* Replace existing image downloading code

- part image uses new generic function
- company image uses new generic function

* Rearrange settings

* Refactor and cleanup existing views / forms

* Add unit testing for image downloader function

* Refactor image downloader forms

- Part image download now uses the API
- Company image download now uses the API
- Remove outdated forms / views / templates

* Increment API version

* Prevent remote image download via API if the setting is not enabled

* Do not attempt to validate or extract image from blank URL

* Fix custom save() serializer methods
This commit is contained in:
Oliver
2022-07-25 11:17:59 +10:00
committed by GitHub
parent d32054b53b
commit eecb26676e
18 changed files with 279 additions and 301 deletions

View File

@ -1,8 +1,10 @@
"""DRF data serializers for Part app."""
import imghdr
import io
from decimal import Decimal
from django.core.files.base import ContentFile
from django.db import models, transaction
from django.db.models import ExpressionWrapper, F, FloatField, Q
from django.db.models.functions import Coalesce
@ -22,7 +24,7 @@ from InvenTree.serializers import (DataFileExtractSerializer,
InvenTreeDecimalField,
InvenTreeImageSerializerField,
InvenTreeModelSerializer,
InvenTreeMoneySerializer)
InvenTreeMoneySerializer, RemoteImageMixin)
from InvenTree.status_codes import BuildStatus
from .models import (BomItem, BomItemSubstitute, Part, PartAttachment,
@ -273,7 +275,7 @@ class PartBriefSerializer(InvenTreeModelSerializer):
]
class PartSerializer(InvenTreeModelSerializer):
class PartSerializer(RemoteImageMixin, InvenTreeModelSerializer):
"""Serializer for complete detail information of a part.
Used when displaying all details of a single component.
@ -424,6 +426,7 @@ class PartSerializer(InvenTreeModelSerializer):
'parameters',
'pk',
'purchaseable',
'remote_image',
'revision',
'salable',
'starred',
@ -437,6 +440,31 @@ class PartSerializer(InvenTreeModelSerializer):
'virtual',
]
def save(self):
"""Save the Part instance"""
super().save()
part = self.instance
# Check if an image was downloaded from a remote URL
remote_img = getattr(self, 'remote_image_file', None)
if remote_img and part:
fmt = remote_img.format or 'PNG'
buffer = io.BytesIO()
remote_img.save(buffer, format=fmt)
# Construct a simplified name for the image
filename = f"part_{part.pk}_image.{fmt.lower()}"
part.image.save(
filename,
ContentFile(buffer.getvalue()),
)
return self.instance
class PartRelationSerializer(InvenTreeModelSerializer):
"""Serializer for a PartRelated model."""