用Python修改图片格式

请使用Pillow中Image类的format属性查看图片类型,save()方法转换格式,全文完→_→

都怪iOS这个弱鸡不支持WebP图片

最近做了个需求,运营把微信公众号登各种来源的文章直接粘到我们的富文本编辑器上面。但是图片因为源站的防盗链挂掉了。于是需要把图片上传到又拍云上面:用BeautifulSoup把html中的图片链接解析出来,伪造HTTP_REFERER把图片下载到内存再上传到CDN

某天报了个奇怪的bug:文章图片被替换后,只有iOS设备无法正常加载图片,其他设备都正常。查了大半天错之后终于发现是iOS不是原生支持WebP格式图片的,而文章来源的微信公众号文章的图片都是WebP格式

讲道理虽然WebP是Google发明并推广的,不支持的浏览器也不少。但是当今Chrome内核已经是事实上的垄断了……于是兼容性被忽视了

有趣的是源站的文章图片显示正常,应该是微信公众号新闻根据不同设备的UA把图片转换格式了吧(大厂的黑科技真多→_→

自动转换图片格式

一开始查到了imghdr模块,使用起来倒是很简单:

1
2
3
4
5
6
7
In [1]: import imghdr

In [2]: imghdr.what('/Users/kdwycz/Desktop/pillow.jpg')
Out[2]: 'jpeg'

In [3]: imghdr.what(open('/Users/kdwycz/Desktop/pillow.jpg'))
Out[3]: 'jpeg'

只是这个库对文件类型的支持比较弱鸡,只识别以下格式。新一点的格式都无法识别

  • ‘rgb’ SGI ImgLib Files
  • ‘gif’ GIF 87a and 89a Files
  • ‘pbm’ Portable Bitmap Files
  • ‘pgm’ Portable Graymap Files
  • ‘ppm’ Portable Pixmap Files
  • ‘tiff’ TIFF Files
  • ‘rast’ Sun Raster Files
  • ‘xbm’ X Bitmap Files
  • ‘jpeg’ JPEG data in JFIF or Exif formats
  • ‘bmp’ BMP files
  • ‘png’ Portable Network Graphics

随后看了下Pillow的文档,很惊喜的发现了

Python Imaging Library 支持绝大多数的图片格式. 囊括了30多种. 虽然对写的支持稍微少了一些, 但是大部分的交换格式都是支持的.

open() 方法使用文件内容来区分不同的文件, 除非你指定格式, 否则 save() 方法使用文件名来识别所需格式.

真是图片处理的瑞士军刀,话说当时在学校玩图像识别的时候为什么没有多看看Pillow的文档→_→

1
2
3
4
5
6
7
8
9
10
11
12
In [1]: from PIL import Image

In [2]: from cStringIO import StringIO

In [3]: image = Image.open('/Users/kdwycz/Desktop/pillow.jpg')

In [4]: image.format
Out[4]: 'JPEG'

In [5]: output = StringIO()

In [6]: image.save(output, format='WEBP')

代码上线到生产环境报错,看了下生产环境的Pillow版本是2.5.1,升级到最新版后解决

参考


用Python修改图片格式
https://blog.kdwycz.com/archives/change-image-format/
作者
kdwycz
发布于
2017年5月8日
许可协议