[fix] handle the case when the image used for thumbnail generation does not have an extension

This commit is contained in:
Anand Doshi 2015-11-25 17:52:29 +05:30
parent cf6e85d4db
commit c14e8b7def

View file

@ -153,43 +153,10 @@ class File(NestedSet):
def make_thumbnail(self):
if self.file_url:
if self.file_url.startswith("/files"):
try:
image = Image.open(frappe.get_site_path("public", self.file_url.lstrip("/")))
filename, extn = self.file_url.rsplit(".", 1)
except IOError:
frappe.msgprint("Unable to read file format for {0}".format(self.file_url))
image, filename, extn = get_local_image(self.file_url)
else:
# downlaod
file_url = frappe.utils.get_url(self.file_url)
r = requests.get(file_url, stream=True)
try:
r.raise_for_status()
except requests.exceptions.HTTPError, e:
if "404" in e.args[0]:
frappe.throw(_("File '{0}' not found").format(self.file_url))
else:
raise
image = Image.open(StringIO.StringIO(r.content))
try:
filename, extn = self.file_url.rsplit("/", 1)[1].rsplit(".", 1)
except ValueError:
# the case when the file url doesn't have filename or extension
# but is fetched due to a query string. example: https://encrypted-tbn3.gstatic.com/images?q=something
filename = get_random_filename()
extn = ""
mimetype = None
if extn:
mimetype = mimetypes.guess_type(filename + "." + extn)[0]
if mimetype is None or not mimetype.startswith("image/"):
# detect file extension by reading image header properties
extn = imghdr.what(filename + "." + extn, h=r.content)
filename = "/files/" + strip(urllib.unquote(filename))
image, filename, extn = get_web_image(self.file_url)
thumbnail = ImageOps.fit(
image,
@ -209,7 +176,6 @@ class File(NestedSet):
return thumbnail_url
def after_delete(self):
self.update_parent_folder_size()
@ -300,3 +266,66 @@ def setup_folder_path(filename, new_parent):
if file.is_folder:
frappe.rename_doc("File", file.name, file.get_name_based_on_parent_folder(), ignore_permissions=True)
def get_extension(filename, extn, content):
mimetype = None
if extn:
mimetype = mimetypes.guess_type(filename + "." + extn)[0]
if mimetype is None or not mimetype.startswith("image/") and content:
# detect file extension by reading image header properties
extn = imghdr.what(filename + "." + (extn or ""), h=content)
return extn
def get_local_image(file_url):
file_path = frappe.get_site_path("public", file_url.lstrip("/"))
try:
image = Image.open(file_path)
except IOError:
frappe.msgprint("Unable to read file format for {0}".format(file_url))
return
content = None
try:
filename, extn = file_url.rsplit(".", 1)
except ValueError:
# no extn
with open(file_path, "r") as f:
content = f.read()
filename = file_url
extn = None
extn = get_extension(filename, extn, content)
return image, filename, extn
def get_web_image(file_url):
# downlaod
file_url = frappe.utils.get_url(file_url)
r = requests.get(file_url, stream=True)
try:
r.raise_for_status()
except requests.exceptions.HTTPError, e:
if "404" in e.args[0]:
frappe.throw(_("File '{0}' not found").format(file_url))
else:
raise
image = Image.open(StringIO.StringIO(r.content))
try:
filename, extn = file_url.rsplit("/", 1)[1].rsplit(".", 1)
except ValueError:
# the case when the file url doesn't have filename or extension
# but is fetched due to a query string. example: https://encrypted-tbn3.gstatic.com/images?q=something
filename = get_random_filename()
extn = None
extn = get_extension(filename, extn, r.content)
filename = "/files/" + strip(urllib.unquote(filename))
return image, filename, extn