2
0
mirror of https://github.com/inventree/InvenTree.git synced 2025-04-29 20:16:44 +00:00
This commit is contained in:
Oliver Walters 2021-03-17 08:28:28 +11:00
parent 3900f9b1b6
commit 5b7d35e6f7
2 changed files with 77 additions and 0 deletions

View File

@ -75,6 +75,7 @@ part_detail_urls = [
# Normal thumbnail with form # Normal thumbnail with form
url(r'^thumbnail/?', views.PartImageUpload.as_view(), name='part-image-upload'), url(r'^thumbnail/?', views.PartImageUpload.as_view(), name='part-image-upload'),
url(r'^thumb-select/?', views.PartImageSelect.as_view(), name='part-image-select'), url(r'^thumb-select/?', views.PartImageSelect.as_view(), name='part-image-select'),
url(r'^thumb-download/', views.PartImageDownloadFromURL.as_view(), name='part-image-download'),
# Any other URLs go to the part detail page # Any other URLs go to the part detail page
url(r'^.*$', views.PartDetail.as_view(), name='part-detail'), url(r'^.*$', views.PartDetail.as_view(), name='part-detail'),

View File

@ -5,6 +5,7 @@ Django views for interacting with Part app
# -*- coding: utf-8 -*- # -*- coding: utf-8 -*-
from __future__ import unicode_literals from __future__ import unicode_literals
from django.core.files import File
from django.core.exceptions import ValidationError from django.core.exceptions import ValidationError
from django.db import transaction from django.db import transaction
from django.db.utils import IntegrityError from django.db.utils import IntegrityError
@ -19,6 +20,9 @@ from django.conf import settings
from moneyed import CURRENCIES from moneyed import CURRENCIES
from urllib.parse import urlsplit
from tempfile import TemporaryFile
import requests
import os import os
from rapidfuzz import fuzz from rapidfuzz import fuzz
@ -47,6 +51,7 @@ from InvenTree.views import QRCodeView
from InvenTree.views import InvenTreeRoleMixin from InvenTree.views import InvenTreeRoleMixin
from InvenTree.helpers import DownloadFile, str2bool from InvenTree.helpers import DownloadFile, str2bool
from InvenTree.helpers import TestIfImageURL, TestIfImage
class PartIndex(InvenTreeRoleMixin, ListView): class PartIndex(InvenTreeRoleMixin, ListView):
@ -831,6 +836,77 @@ class PartQRCode(QRCodeView):
return None return None
class PartImageDownloadFromURL(AjaxUpdateView):
"""
View for downloading an image from a provided URL
"""
model = Part
form_class = part_forms.PartImageDownloadForm
ajax_form_title = _('Download Image')
def validate(self, part, form):
"""
Validate that the image data are correct.
- Try to download the image!
"""
# First ensure that the normal validation routines pass
if not form.is_valid():
return
# We can now extract a valid URL from the form data
url = form.cleaned_data.get('url', None)
response = requests.get(url, stream=True)
# Check that the URL "looks" like an image URL
if not TestIfImageURL(url):
form.add_error('url', _('Supplied URL is not one of the supported image formats'))
return
# Check for valid response code
if not response.status_code == 200:
form.add_error('url', f"{_('Invalid response')}: {response.status_code}")
return
# Validate that the returned object is a valid image file
if not TestIfImage(response.raw):
form.add_error('url', _('Supplied URL is not a valid image file'))
return
# Save the image object
self.image_response = response
def save(self, part, form, **kwargs):
"""
Save the downloaded image to the part
"""
response = getattr(self, 'image_response', None)
if not response:
return
with TemporaryFile() as tf:
#for chunk in response.iter_content(chunk_size=2048):
# tf.write(chunk)
img_data = response.raw.read()
tf.write(img_data)
print("Saved to temp file:", tf.name)
tf.seek(0)
part.image.save(
os.path.basename(urlsplit(response.url).path),
File(tf),
)
class PartImageUpload(AjaxUpdateView): class PartImageUpload(AjaxUpdateView):
""" View for uploading a new Part image """ """ View for uploading a new Part image """