使用WebP Server Go来加速站点本地图片访问速度

尚寂新
尚寂新
2022/11/30 13:47

临近毕业,要到自己为站点续命的时候了。想减少开销,减少一些潜在的意外,故挪掉了一直在用的云存储(大部分文件是反代uploads目录并静态内容迁移以使用 CDN 节点进行加速,小部分文件为自上传的云存储)。这样一来,之前那些随手传上去的图片不是那么小,没有了 CDN 端上的 WebP 自动转换,图片加载速度的确是慢了不少。

WebP Server Go
WebP Server Go

然后经过搜索,找到了这么个基于 Go 语言写的这么一个服务端程序,可以自动把普通格式的图片转为 WebP 或者是 AVIF 格式的图片(但 AVIF 的转换对服务器的性能要求极高,详见后文)

Loading...

安装步骤

  1. 安装用于转换 AVIF 的依赖(建议别装,性能要求高,虽说就几行终端指令的事,但事后感觉还是白弄,具体命令见 Github)
  2. 版本发布页下载最新的构建
  3. 按照下面的方法生成配置文件(Linux 终端)
./webp-server -dump-config > config.json

config.json内的文件默认如下:

{
  "HOST": "127.0.0.1",
  "PORT": "3333",
  "QUALITY": "80",
  "IMG_PATH": "/path/to/pics",
  "EXHAUST_PATH": "/path/to/exhaust",
  "ALLOWED_TYPES": ["jpg","png","jpeg","bmp"],
  "ENABLE_AVIF": false
}

其中,HOST地址建议保持这个本地回环地址,只让Nginx本地反代这个服务端就行,比较优雅。端口可以自定,但其实禁了公网访问保持默认也行。关于两个路径,感觉官方文档写的挺明白的,下面简单翻译一下。

Config 文件示例

下面的示例,分别是图片的存储路径与网站 URL 的路径的示例

In the following example, the image path and website URL.
Image Path(图片的存储路径)Website Path(网站 URL 路径)
/var/www/img.webp.sh/path/tsuki.jpghttps://img.webp.sh/path/tsuki.jpg

config.json配置文件里的IMG_PATH项应该这样像下面这种填法

The IMG_PATH inside config.json should be like:
IMG_PATH
/var/www/img.webp.sh

EXHAUST_PATH是程序用于生成webp文件的缓存文件夹。如果将缓存文件夹的路径EXHAUST_PATH设置为/var/cache/webp,那么示例中的这张图片的缓存文件就会被存到/var/cache/webp/pics/tsuki.jpg.1582558990.webp

EXHAUST_PATH is cache folder for output webp images, with EXHAUST_PATH set to /var/cache/webp
in the example above, your webp image will be saved at /var/cache/webp/pics/tsuki.jpg.1582558990.webp.

AVIF 强烈建议设置为false

  1. 启动 WebP Server(/path/to/config.json替换为真实的路径)
./webp-server --config=/path/to/config.json
  1. Nginx 反代,直接在你自己的站点配置文件里,追加规则。注:Nginx 的配置文件更改之后,需要重载配置文件或者是重启 Nginx 才会生效(一般只重载配置文件就行)
location ~* \.(?:jpg|jpeg|gif|png)$ {
    proxy_pass http://127.0.0.1:3333;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_hide_header X-Powered-By;
    proxy_set_header HOST $http_host;
    add_header Cache-Control 'no-store, no-cache, must-revalidate, proxy-revalidate, max-age=0';
}

更多内容,详见官方文档:https://docs.webp.sh/usage/basic-usage/

为什么我不推荐开启 AVIF

起初看项目的 README 里,是这样写的:

AVIF support is disabled by default as converting images to AVIF is CPU consuming.

心想,可能只是在高并发的时候对性能有影响吧,于是开启了。因为自己一直用的 Edge 浏览器是不支持 AVIF 的,电脑端的 Chrome 和我手机上的 Safari 是支持 AVIF 的。直到我拿起我的手机,才发现问题所在,然后又下载了 Chrome,也复现了这个问题。进缓存目录一看,生成的 AVIF 文件的大小为 0kb,并且有报错:

time="2022-11-30 12:16:21" level=warning msg="Can't encode source image: encoder error: codec init error to AVIF" func="[120:main.avifEncoder()]"
time="2022-11-30 12:16:21" level=info msg="AVIF@80.00%: /resource/avatar.jpg->/resource/avatar.jpg.1663669630.avif 30850->0 0.00% deflated" func="[153:main.convertLog()]"

找了一圈,不是因为缺少刚才最开始那个依赖而报错,接着搜,搜到了另一个类似项目的 issues 的评论区,结果...

还是因为性能问题
还是因为性能问题

当初是知道性能开销大,并且还有提醒写出来,但我没想到性能开销居然这么大...

于是关掉了 AVIF 转换,只用 WebP 转换也挺香。虽说我知道这个和 CDN 与云存储并不是平替关系,但的确是让我摆脱云存储与 CDN 的途径,以后不出意外的话会长期使用这个方案,感觉挺香的。

已有 3 条评论 (旧评论在前)
  1. 森木志 友链
    回复
    2022-12-01 15:56 广东省 南博 4.1.4

    现在好像还在用的腾讯云的webp@[滑稽]

    1. 尚寂新 博主
      回复
      2022-12-01 23:31 吉林省 iOS 16.1.1

      因为要摆脱第三方云存储、心想两者的目的都是加快访问速度,用第三方云存储是通过厂商强大的集群,自己优化源站减少网络开销,两者都能提高速度,全都拿在自己手里感觉会好一些,当然也是利弊的取舍吧

  2. 怼他
    回复
    怼他
    2023-07-26 23:31 陕西省 Windows NT10

    半年多都不动弹了@[吃瓜]

添加新评论 (Markdown Supported)
(ノ°ο°)ノ