How do I display a PIL Image object in a template? - python

If a user uploads an image, and I resize it using PIL, I get a PIL Image object.
How do I display a PIL Image file in a template, before it has been saved to the database? Can it even be passed in as an image and rendered?

For a limited set of browsers, you can base64 encode the image and use inline images. See Embedding Base64 Images.
A solution that works for all browsers is an image tag referencing a view that returns the image.
[update]
All I want is for the user to submit the original image, and then be prompted by another form to input a caption for the image (with the resized image to the left of the caption field). Then when the user hits "submit" the image and the caption get saved in a model instance.
Well... When you use <img src="foo">, foo is always retrieved by a GET perhaps that is why it is not working - request.FILES will not be available in a GET request. If you open firebug or the chrome debug toolbar, in the network tab, you will see the POST request with the uploaded image and after that a GET request to fetch the image.
You have to save the image somewhere between both steps.
how else could i save it? I would love for it to be temporary. Do you think there's a really easy way to do this, or should I go look into those options?
Popular choices are redis and memcached. You can think of them as giant shared python dict with an expire date. If the images are small, like an avatar, you can also save the image data in a session variable.

Yes and no.
Yes, you can put the images as raw Base64 data. Here's a little script you can use to test this:
import Image
import base64
import StringIO
output = StringIO.StringIO()
im = Image.open("test.png") # Your image here!
im.save(output, format='PNG')
output.seek(0)
output_s = output.read()
b64 = base64.b64encode(output_s)
open("test.html","w+").write('<img src="data:image/png;base64,{0}"/>'.format(b64))
However, this is a really bad idea. With multiple thumbnails, your single HTML page might be 10MB+.
What you really should be doing is using a separate Django view to return images from PIL objects as PNG files, and then referencing that view in the img href attributes on your page.

You can embed base64 encoded images into an tag. So you could convert PIL image to base64 and then display it.
from PIL import Image
import StringIO
x = Image.new('RGB',(400,400))
output = StringIO.StringIO()
x.save(output, "PNG")
contents = output.getvalue().encode("base64")
output.close()
contents = contents.split('\n')[0]
Then show with:
<img src="data:image/png;base64,' + contents + ' />
Look to an example output.

Related

The extension in image url is different from actual format

I downloaded an image from a url such as "https://www.xxxx.com/filename.jpeg. I expected that that image is a jpeg image whose format is acceptable for Computer Vision Annotation Tool (CVAT). However, it was saved as filename.heif or filename.jpeg.heif, so it causes an error when I tried to create a task with that image because heif format is not acceptable in CVAT. (CVAT automatically downloads images and create a task once I put image urls and submit them.)
I usually put more than 1000 image urls to create a task, and it is really hard to find invalid url or image among them.
Is there any way to find the "actual format" only by looking at the image url? Or can I just skip invalid urls in CVAT?
Thank you.

How to break "select different image" CAPTCHA with Python

So I have this code in Python3 that scraps data from websites through object recongnition (I used this to automate the download process inside a flash player based website) and Selenium. The problem is that I'm stuck with this website that have a custom made Captcha where the user have to select the different image from the group and I donĀ“t know how to download or get these images from the site in order to identify the different one, has anyone solved a problem like this? or have an idea on how to solve this captcha with any other technique or method?
This is the login that has the CAPTCHA
And here's the link to the site which is in spanish. The captcha basically says "Select the different image"
https://portalempresas.sb.cl/login.php
Thanks!
To download those images as png files you could do:
from io import BytesIO
from PIL import Image
# Download image function
def downloadImage(element,imgName):
img = element.screenshot_as_png
stream = BytesIO(img)
image = Image.open(stream).convert("RGB")
image.save(imgName)
# Find all the web elements of the captcha images
image_elements = driver.find_elements_by_xpath("*//div[contains(#class,'captcha-image')]")
# Output name for the images
image_base_name = "Imagen_[idx].png"
# Download each image
for i in range(len(image_elements)):
downloadImage(image_elements[i],image_base_name.replace("[idx]","%s"%i))
Edit 1:
If you want to compare 2 images to see if they are equal you could try with this post
Edit 2:
Using the solution edited above, these are the results:

Open Image from requests.response.content

What I am trying to do is quite simple when dealing with a local file, but the problem comes when I try to do it with a remote URL.
Basically, I am trying to create a PIL image object from a file extracted from a URL. Of course, I could always fetch the URL and store it in a temporary file, then open it in an image object, but that seems very inefficient.
Here is what I have:
from PIL import Image
import requests
from io import BytesIO
response = requests.get(url)
img = Image.open(BytesIO(response.content))
So the Code is not returning the image if anyone knows.

How does Facebook share image base64 from Google App Engine

Im working with Google App Engine Project and I want use facebook share like this.
http://i.stack.imgur.com/uz52n.png
Im already read this
How does Facebook Sharer select Images and other metadata when sharing my URL?
but GAE cant upload physical Image, all image store in blob property in database as base64 so facebook share cant get the image :(
anyone had another idea for this problem ??
Facebook reads the og:image meta to resolve the image from your webpage. og:image don't allow data-URI image (base64 encoded).
You have to provide an image url in og:image, but with that url, you can make a workaround to simulate the behaviour of a direct image resolution and get the image from your appengine database.
This is a solution in python using Django, but the concept works for everything. The name of the image is here "key.png" where key is the key of the object containing the base64 stored image.
First, add an url to the list of django urls for your image resolution:
(r'^image/(?P<key>[^\.^/]+)\.png$', 'yourapp.views.image'),
Then in your views, get the key from the url, retrieve your object, base64 decode and send it back with the correct mimetype:
import base64
def image(request, key):
# get your object from database
f = YourImageObject.get(key)
# f.pic is the base64 encoded image
pic = f.pic[len("data:image/png;base64,"):] # remove the header
# base64 decode and respond with correct mimetype
return HttpResponse(base64.b64decode(pic), mimetype="image/png")

Uploading profile image with twitter api and python

I want to upload an image from my hard drive, using an html form:
Image file: <input name="imageupload" id="imageupload" type="file" />
Then I upload it to twitter with:
image=self.request.get('imageupload')
image2=base64.b64encode(image)
twitapi.Update_profile_image(image=image2)
given twitapi.Update_profile_image:
def Update_profile_image(self,image):
if not self._oauth_consumer:
raise TwitterError("The twitter.Api instance must be authenticated.")
url = '%s/account/update_profile_image.json' % (self.base_url)
data = {'image':image}
json = self._FetchUrl(url, post_data=data)
data = self._ParseAndCheckTwitter(json)
return data
Given _FetchUrl from twitter-api
I always get
TwitterError: There was a problem with your picture. Probably too big.
Any ideas whee it comes from? Thanks!
To submit ah image correctly via a form, you have to include
enctype="multipart/form-data"
eg
<form enctype="multipart/form-data" action='/' method="POST">
Twitter RESTful API Document is not correct.
Do NOT encode image binary to base64!
Remove base64 encode section from your source.
If you encode image binary to base64 string, twitter api says
"... was a problem with your picture probably too big. (...) (code 131)"
As per the documentation, your image:
Must be a valid GIF, JPG, or PNG image of less than 700 kilobytes in size.
So make sure your image fits within these constraints. Maybe you need to scale down your image, or convert it to a different format.
If that doesn't work, try uploading another very tiny image that meets the constraints above. At least you can then verify whether or not the problem lays with the particular image you are using.
Perhaps the image you are receiving via the form upload is already base64 encoded ?
You are then applying a double encoding which could confuse the validation on the twitter server side because it would be unable to find a typical image header in your uploaded file.

Categories