加载中...

基于Hexo的matery主题搭建博客网络优化篇3


Hexo系列 HexoRSS分类订阅

[三万字教程]基于Hexo的matery主题搭建博客并深度优化完全一站式教程

  • markdown 各种其它语法插件
  • latex公式支持
  • mermaid图表
  • plant uml图表
  • URL卡片
  • bilibili卡片
  • github卡片
  • 豆瓣卡片
  • 插入音乐和视频
  • 插入脑图

经过一系列优化修改后,评分终于可以看了,对于一个web开发外行来说,可以满足了。😄

  • 各种CDN
  • webp
  • gulp 压缩
  • cloudflare parter
  • service worker
  • 部分资源异步加载

page test

page test

经过多次优化之后,新版看板娘资源异步加载体积大拖累的性能分数。其它几乎都是满分了!

保证了第二次打开几乎都是使用缓存,牺牲了第一次加载的体积,异步加载对第一次渲染速度影响不大。

加速NPM安装下载

安装淘宝镜像

npm config set registry https://registry.npm.taobao.org

安装CNPM

npm install -g cnpm --registry=https://registry.npm.taobao.org

CDN 加速

  • 为什么强烈建议启用CDN?

研究表明,用户最满意的打开网页时间,是在 2 秒以下。用户能够忍受的最长等待时间在 6~8 秒之间。就是说,8 秒是一个临界值,如果你的网站打开速度在 8 秒以上,那么你将失去大部分用户。研究显示,如果等待 12 秒以后,网页还是没有载入,那么 99% 以上的用户会选择关闭网页。

Google 做过一个试验,10 条搜索结果的页面载入时间需要 0.4 秒,显示 30 条搜索结果的页面载入时间需要 0.9 秒,结果后者使得 Google 总的流量和收入减少了 20%。Google 地图上线的时候,首页大小有 100KB,后来下降到 70~80KB。结果,流量在第一个星期上升了 10%,接下来的 3 个星期又再上升了 25%。Amazon 的统计也显示了相近的结果,首页打开时间每增加 100 毫秒,网站销售量会减少 1%。

以上数据说明了一个非常重要的问题,如果你的网站速度如果超过 2s 以上,那么你的客户可能在流失和离你而去了。这一点对于电商网站尤其重要,打开速度慢,那么将造成转化率降低,损失将会大量增加。

放在 Github 的资源在国内加载速度比较慢,因此需要使用 CDN 加速来优化网站打开速度,jsDelivr + Github 便是免费且好用的 CDN,非常适合博客网站使用。也可以选择主流云服务商提供的对象存储+CDN 来获得更快速及稳定的访问效果,费用低到几乎可忽略。

用法:

https://cdn.jsdelivr.net/gh/{你的用户名}/{你的仓库名}@{发布的版本号}/{文件路径}

例如:

https://cdn.jsdelivr.net/gh/appotry/[email protected]/data/2022/03/1120220311110247.webp

注意:版本号不是必需的,是为了区分新旧资源,如果不使用版本号,将会直接引用最新资源。

还可以配合 PicGo图床上传工具的自定义域名前缀来上传图片,使用极其方便。具体使用方法可参见我的另一篇文章: 使用 Typora+iPic/PicGo 图床+CDN 实现高效 Markdown 创作

jsdelivr

jsdelivr 是还在目前还在国内运营的可以通过特殊方法免费使用的CDN。

Github开源仓库发布版本才能使用jsdelivr,懂了怎么做了吧。

https://cdn.jsdelivr.net/gh/[name]/[repo]@latest/data/2022/03/1120220311110247.webp

Cloudflare CDN

配置最简单的CDN方式了。在github raw链接地址前面加https://images.weserv.nl/?url=, 就会自动使用cloudflare cdn来加速图片访问。使用发现无法加速gif。

本blog主要使用这个方法,如下所示。

  • 未加速图片地址
https://raw.githubusercontent.com/appotry/cloudimg/main/data/2021/09/1020210910231815.png
  • Cloudflare加速图片地址
# 使用了cloudflare partner 加速
https://cimg1.17lai.site/data/2021/09/1020210910231815.png

配置Service worker

后篇文章基于Hexo的matery主题搭建博客个性定制篇5中提到的 让hexo支持pwa 就是使用的Service worker ,参考个性定制篇,把常用的大体积文件加入Service worker 缓存列表,可以极大的提高访问速度!

原理:在访问时,后台异步加载 SW 缓存文件列表,后面渲染网页,直接使用缓存中的文件,不再从网络中获取。你可以提前把所有常用的大体积资源放到缓存列表中,后面访问其它页面时,很多资源已经提前加载好了,可以极大的提高访问速度!

SEO 优化

  • 搜索引擎优化,又称为 SEO,即 Search Engine Optimization,它是一种通过分析搜索引擎的排名规律,了解各种搜索引擎怎样进行搜索、怎样抓取互联网页面、怎样确定特定关键词的搜索结果排名的技术。Google 自动收录效果还不错,百度就差得远了(GitHub不允许百度的Spider爬取GitHub上的内容)。

  • 如果没有备案,百度seo是不会收录的!所以如果你有国内vps,并且备案了,可以做百度seo,如果没有,百度seo内容都不需要看了。

网域提交方式

  1. 自动提交

    (分三种)

    • 主动推送
    • 自动推送
    • sitemap(站点地图)
  2. 手动提交

    • 即手动地将链接一次性提交给百度

一般自动提交比手动提交效果好一点,自动提交又从效率上来说:

主动推送>自动推送>sitemap

自动提交的三种方式

  1. 主动推送:最为快速的提交方式。将站点当天新产出链接通过此方式推送给百度,以保证新链接可以及时被百度收录。
  2. 自动推送:最为便捷的提交方式。将自动推送的JS代码部署在站点的每一个页面源代码中,当部署代码的页面在每次被浏览时,链接就会被自动推送给百度。可以与主动推送配合使用。
  3. sitemap:您可以定期将网站链接放到sitemap文件中,然后将sitemap文件提交给百度。百度会周期性的抓取检查您提交的sitemap,对其中的链接进行处理,但收录速度慢于主动推送。

使用sitemap方式推送

安装 sitemap 插件生成站点地图文件:

npm install hexo-generator-sitemap --save
npm install hexo-generator-baidu-sitemap --save  #百度专用

安装后直接执行 hexo cl&&hexo g -d 命令,就会在网站根目录生成 sitemap.xmlbaidusitemap.xml 文件。

  • 在博客目录的_config.yml中添加如下代码
# 通用站点地图
sitemap:
  path: sitemap.xml

# 百度站点地图
baidusitemap:
  path: baidusitemap.xml

百度优化

登录百度搜索资源平台, 登录成功之后在 用户中心 –> 站点管理 页面中点击添加网站,按提示操作。

添加网站

添加网站

提示:由于百度的 spider 是爬取不到 GitHub 的内容的,所以在第三步验证网站的时候,建议选择CNAME验证的方式。

经过以上步骤,百度已经知道有我们网站的存在了,但是百度还不知道我们的网站上有什么内容,所以要向百度推送我们的内容。点击 网站支持 –> 数据引入 –> 链接提交菜单,提交站点地图:

提交站点地图

提交站点地图

另外,hexo-theme-matery主题已经内置了 自动推送 的功能, 检查 themes/hexo-theme-matery/_config.yml 文件中如下配置:

# 百度搜索资源平台提交链接
baiduPush: true

自动推送的 JS 代码部署在站点的每一个页面源代码中,当页面在每次被浏览时,链接就会被自动推送给百度。

谷歌优化

登录 Google Search Console,点击添加资源,输入自己的域名,按提示操作。

添加资源

添加资源

提示:需要进行 DNS 验证,进入 DNS 域名解析设置页面,按提示增加 TXT 记录,如下图:

DNS验证内容填写示例

DNS验证内容填写示例

验证成功后,需要提交站点地图。参照下图提交,然后等待收录。

提交站点地图

提交站点地图

注意:hexo 配置文件中的 url 一定要输入正确的域名,插件是根据 url 生成站点地图的。

其它搜索引擎

百度自动推送方式

只要每个需要被百度爬取的HTML页面中加入一段JS代码即可:

<script>
(function(){
    var bp = document.createElement('script');
    var curProtocol = window.location.protocol.split(':')[0];
    if (curProtocol === 'https') {
        bp.src = 'https://zz.bdstatic.com/linksubmit/push.js';
    }
    else {
        bp.src = 'http://push.zhanzhang.baidu.com/push.js';
    }
    var s = document.getElementsByTagName("script")[0];
    s.parentNode.insertBefore(bp, s);
})();
</script>

我所使用的matery主题可以自动给每个页面加上这段代码,只需在主题配置文件中配置:

# 百度搜索资源平台提交链接
baiduPush: true

即可!

其他主题一般都有这个功能的实现,如果没有的话,想办法在每个页面加入以上JS代码即可,原理是一样。

百度主动推送SEO方式

  • 配置文章自动推送到百度蜘蛛

获取百度推送密钥

百度资源 注册你的网址,验证完后可在站点管理->资源提交->链接提交->主动推送(实时) 中找到你的推送密钥,下面说明中的 token= 后的内容即为推送密钥。

推送接口
接口调用地址:http://data.zz.baidu.com/urls?site=https://ifibe.com&token=xxxxxxxxxx

安装主动推送插件:hexo-baidu-url-submit

$ npm install hexo-baidu-url-submit --save

然后打开hexo配置文件,在末尾加入以下配置:

# hexo-baidu-url-submit  百度主动推送
baidu_url_submit:
  count: 80 # 提交最新的一个链接
  host: https://blog.17lai.site # 在百度站长平台中注册的域名
  token: xxxxxxx # 请注意这是您的秘钥, 所以请不要把博客源代码发布在公众仓库里!
  path: baidu_urls.txt # 文本文档的地址, 新链接会保存在此文本文档里

密匙的获取是在百度的自动提交的主动推送那里。

再加入新的deploy

deploy:
- type: baidu_url_submitter

如图:

这样每次执行 hexo d 的时候,新的链接就会被推送了。

$ hexo clean
$ hexo g
$ hexo d

推送成功时,会有如下终端提示!

baidu_url_submitter

各种不同的推送反馈字段说明点我查看,一般来说,推送失败基本都是地址不相符造成的,我们只需对比baidu_url_submitpublic中生成的baidu_urls.txt的地址,与自己填写在host字段中的地址对比看是否一样即可。

Github Action 自动提交SEO方式

安装插件

npm i hexo-seo-autopush --save

配置

在hexo 的config.yml里添加

hexo-seo-autopush配置

# enable: 开启/关闭 推送
# count: 每次提交最新的10篇文章
# https://github.com/lete114/hexo-seo-autopush
hexo_seo_autopush:
  baidu:
    enable: true
    count: 100
  bing:
    enable: true
    count: 10
  google:
    enable: true
    count: 10
    google_file: google_service_account.json # 谷歌服务账户

添加Google Push配置和解决push后没有GitHub Actions .github\workflows\AutoPush.yml文件的问题

# Deployment
## Docs: https://hexo.io/docs/one-command-deployment
deploy:
   - type: git
     repo: https://github.com/lete114/Test.git
     branch: main
     ignore_hidden: false  # 忽略隐藏文件及文件夹(目录)
   - type: GooglePush # 谷歌提交

获取站长平台密钥

Baidu Key

  1. 打开百度站长平台,点击左侧的普通收录https://ziyuan.baidu.com/

Bing Key

  1. 打开Bing站长平台,https://www.bing.com/webmasters/home
  2. 点击右上角头像 旁边的齿轮,跟着下图操作

Google Key

Google Wiki, 使用参考。

  1. 打开Google indexing API官网

  2. 选择创建项目,点击继续

  3. 点击转到凭据页面

  4. 跟着如下图片步骤

    GoogleProof

    GoogleAddProof

    GoogleNone

    GoogleKey

    json文件内的内容

    {
      "type": "service_account",
      "project_id": "elated-guild-298003",
      "private_key_id": "cf58d669c0e8c8e082b2c403ade5e2548078e384",
      "private_key": "-----BEGIN PRIVATE KEY-----\nMIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQDEAJw89yeylRrA\nB+bzOAfQQNgOCABIwEKCy5mMxWSaiXy2RktyCJWjMR2Pgz770NJgClQHPJjsFn0c\nukHufpnuiX3VPlimLANPCRFdU/qp+yiaw4quIhYF1UZJkhmhL30anghUcvi+r9hQ\nw+RwcKrgA4EUzqUJaPdvjtzSoo315PPGfR91ASD5S8gE02yVI8igtYMX7v2x1JYR\n7PwHJwOVemiM9lot8ilvoUbV4BU0vSlwFoxKMJAbEXTmJjEKQi9992rcMW0GzXO8\ncHldUUtURXkt3VFjYTH27KhHiTkTXw+uZRBu1rkubDJkS8lGIWN7Fc/r4HMMCVTu\nXPS6HbJ/AgMBAAECggEANSS7OBaFd3jRL3cVCiZLjA5A5pEJzq/+eKtOn2oYDISx\nwVRO+YTVWdGj47kg1zM4D11NikbGaeDxHFxuKwW9o/04lpyYebneTcw2Hpl6EiOs\nz0WssOlCEmPQ8nrAI0GWiKSHuqoPwtg37TIoGsqZsjKRCby759DDokZYnm3/0sc+\niEllT0ZyBZhGDzyguVLEdCIR2P02q/hQzLyd6ejWGGwZebImbGoILhmuOjVrco0p\nV0JbrrNskjM5Epe7w+CpGftEASJ7Dxa8oj0qIT6cyAipra2AZAGnG9jrLcWpJuhu\nvNeDIFnTfpNEac+khXZZE2++MIQfTX9wGJc8tox2vQKBgQD6yiNvAL7sxExiy6ER\ntLtFQ3bvmMpKRFGvFOyPOtMbmjZ3D1GEtNNKGH4v1TI+tncEy7Q5Dm7nWwpi8yvL\nbh8xKghelAc/CU1nw0xDEDCkMbAwpFg5A5ZDImy3LZsQh0kNXniIMy1vMSt5yLKS\n80gXQKGCxG8t3rP8Qd/2a55g1QKBgQDIExP1nG9sHJaigmitEUwr0Ow6Shqr56Me\nd7995gaV1oLWWCQzrXt/viWkb1W5ZGIxzcWNWz99m4CbvqfewRr598Eenald0csN\nVcIEk+0C+6KqA+jU9Tfs2zow/C7JuKULP2N++o0EoSz/ngokP7f1yLOYbr507v/R\n0cLElQBQAwKBgAbxDWYHKUG4dTzO0hiBXiWepm4fVooTtgcYlyunvywmapeFDwaT\nUr3cS7HbPtbJiiXR1Z02rw8sT+9JN88brzVXKoAjrMer5D6ZA0Vf71i8H1pZUi/R\nz5jwHP48/uvIMtdx4/gxInLPc5qdWYQDw90Q5ueNtF4aqfSzhhV2CR45AoGBAJN9\nPOF6iMjx6jmyWOf8MGK8iOgPaMoA4Ea9j/SHdaNPlvPb1hQid0AcNDObv14Dmj+M\nqW0jLxKxZ4VobufPAsvyz/J51zjKRx11cqldQwNH7QnYB/O1MZzxn1wtC3C5JTG9\ncONSYFJhXoKxRliigEI3ye089jnNVdifAS1ZiflxAoGBANTX1fEMEeNuYU0v3rtd\n5CkPZg4TNZ+y2MGl5xR1LdIgrJ8c9xKoW4rpp7SsOIvHpWX494f90D7o9uFEGSQ4\nyQK53jVzJ0ekGV5BdPF3n3/2j2VEqFLHi7LL4CJSxr6ci7OfBoHOGE8odhevQCCK\njnFzEin0QsBEgIC73fBh6XcH\n-----END PRIVATE KEY-----\n",
      "client_email": "[email protected]",
      "client_id": "103034240916368863393",
      "auth_uri": "https://accounts.google.com/o/oauth2/auth",
      "token_uri": "https://oauth2.googleapis.com/token",
      "auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs",
      "client_x509_cert_url": "https://www.googleapis.com/robot/v1/metadata/x509/googleindexing%40elated-guild-298003.iam.gserviceaccount.com"
    }
  5. 打开谷歌站长平台
    GoogleAddUser
    GoogleAddEmail

配置博客仓库

  1. Name必须是baidu_tokenbing_apikey(不区分大小写)

  2. 添加完成后
    Secrets-token

谷歌的一些问题

触发谷歌提交的命令是hexo d

由于谷歌需要配合Google indexing API平台提供的json进行提交,而这个json格式不能泄露
为防止json泄露只能本地提交,将json放到hexo根目录可自定义重命名(必须对应插件的配置)
如果你的使用Github Actions自动部署的话请把仓库设置为私有
GoogleConfig

提交成功返回状态码

以上步骤完成后即可hexo d部署了

  1. 看看Github仓库是否上传成功

  2. 点击Actions查看是否执行

  3. 点击 Auto Push—->build—–>点击第2步 自动提交

    如图43行

    // baidu返回的结果
    {
    	"remain": 2060,  // 表示当天剩余的可推送url条数
    	"success": 47    // 成功推送的url条数
    } 
    // bing返回结果(错误)
    {
    	"ErrorCode": 2,  // 错误 
    	"Message": "ERROR!!! Quota remaining for today: 2, Submitted: 47"
        // Message:表示 你目前只剩2个url推送,而你现在推送的是47条url
        // bing新用户开始每日只有10个推送额,据我了解连续推送10天(这我也不确定)
        // 如果出现这个错误的话,你就只能先手动添加等系统给你分配额了(分配9999)
    }
    // bing返回结果(成功)
    {"d":null}
  4. Google 返回状态码

    成功返回

    Google response:  {
      urlNotificationMetadata: {
        url: 'https://blog.lete114.top/article/hexo-seo-autopush.html',
        latestUpdate: {
          url: 'https://blog.lete114.top/article/hexo-seo-autopush.html',
          type: 'URL_UPDATED',
          notifyTime: '2020-12-08T02:31:32.871417693Z'
        }
      }
    }

    出现此错误需要: 翻墙

    FetchError: request to https://www.googleapis.com/oauth2/v4/token failed, reason: connect ETIMEDOUT 172.217.27.138:443
        at ClientRequest.<anonymous> (D:\Lete\GitHub\Hexo-Butterfly\node_modules\node-fetch\lib\index.js:1461:11)
        at ClientRequest.emit (events.js:321:20)
        at TLSSocket.socketErrorListener (_http_client.js:426:9)
        at TLSSocket.emit (events.js:321:20)
        at emitErrorNT (internal/streams/destroy.js:92:8)
        at emitErrorAndCloseNT (internal/streams/destroy.js:60:3)
        at processTicksAndRejections (internal/process/task_queues.js:84:21) {
      message: 'request to https://www.googleapis.com/oauth2/v4/token failed, reason: connect ETIMEDOUT 172.217.27.138:443',
      type: 'system',
      errno: 'ETIMEDOUT',
      code: 'ETIMEDOUT',
      config: {
        method: 'POST',
        url: 'https://www.googleapis.com/oauth2/v4/token',
        data: {
          grant_type: 'urn:ietf:params:oauth:grant-type:jwt-bearer',
          assertion: 'eyJhbGciOiJSUzI1NiJ9.eyJpc3MiOiJnb29nbGVpbmRleGluZ0BzdGF0ZWx5LXRyYW5zaXQtMjk3NzE1LmlhbS5nc2VydmljZWFjY291bnQuY29tIiwic2NvcGUiOiJodHRwczovL3d3d

本地主动提交SEO

hexo-url-submission

Wiki

安装方法

  1. 在终端中输入:
npm i hexo-url-submission
  1. blog/_config.yml 文件中添加配置:
url_submission:
   enable: true
   type: 'latest' # latest or all( latest: modified pages; all: posts & pages)
   channel: ['baidu', 'bing', 'google', 'shenma'] # Included channels are `baidu`, `google`, `bing`, `shenma`
   prefix: ['/post', '/wiki'] # URL prefix
   count: 10 # Submit limit
   proxy: '' # Set the proxy used to submit urls to Google
   urls_path: 'submit_url.txt' # URL list file path
   baidu_token: '' # Baidu private key
   bing_token: '' # Bing private key
   google_key: '' # Google key path (e.g. `google_key.json` or `data/google_key.json`)
   shenma_token: '' # ShenMa private key
   shenma_user: '' # Username used when registering
   sitemap: '' # Sitemap path(e.g. the url is like this https://abnerwei.com/baidusitemap.xml, you can fill in `baidusitemap.xml`)

更新方法

在站点根目录执行:

npm update hexo-url-submission

deploy

deploy:
  - type: us_baidu_deployer
  - type: us_bing_deployer
  - type: us_google_deployer
  - type: us_shenma_deployer

good job

Run:

hexo clean && hexo g && hexo d

enjoy it!

提交 robots.txt

robots.txt是干嘛的?

robots.txt 是一种存放于网站根目录下的 ASCII 编码的文本文件,它的作用是告诉搜索引擎此网站中哪些内容是可以被爬取的,哪些是禁止爬取的。
robots.txt 要放在 Hexo根目录 下的 source 文件夹中。

每个人站点目录可能不太一样,可以参考下我的 robots.txt 文件,内容如下:

User-agent: *
Allow: /
Allow: /posts/
Disallow: /about/
Disallow: /archives/
Disallow: /js/
Disallow: /css/
Disallow: /contact/
Disallow: /fonts/
Disallow: /friends/
Disallow: /libs/
Disallow: /medias/
Disallow: /page/
Disallow: /tags/
Disallow: /categories/

更多关于 robots.txt 的写法参见 https://blog.csdn.net/fanghua_vip/article/details/79535639

编写完以上内容再重新部署一下,然后到百度资源平台的数据监控->Robots点击检测并更新 看能不能检测到。

配置 Nofollow

  • nofollow 是HTML页面中 a标签 的 属性值。
  • 这个属性的作用是:告诉搜索引擎的爬虫不要追踪该链接,为了对抗博客垃圾留言信息

URL优化

一般来说,SEO搜索引擎优化认为,网站的最佳结构是 用户从首页点击三次就可以到达任何一个页面,但是我们使用Hexo编译的站点结构的URL是:域名/年/月/日/文章标题四层的结构,这样的URL结构很不利于SEO,爬虫就会经常爬不到我们的文章,于是,我们需要优化一下网站文章的URL

方案一

直接改成域名/文章标题的形式,在Hexo配置文件中修改permalink如下:

# URL
## If your site is put in a subdirectory, set url as 'http://yoursite.com/child' and root as '/child/'
url: https://blog.sky03.cn
root: /
permalink: :title.html
permalink_defaults:

这个方式有个不好的地方:

直接以文章的标题作为URL,而我们所写的文章的标题一般都是中文,但是URL只能用字母数字和标点符号表示,所以中文的URL只能被转义成一堆符号,而且还特别长。

方案二

安装固定链接插件:hexo-abbrlink

插件作用:自动为每篇文章生成一串数字作每篇文章的URI地址。每篇文章的Front-matter中会自动增加一个配置项:abbrlink: xxxxx,该项的值就是当前文章的URI地址。

  1. Hexo根目录执行:

    npm install hexo-abbrlink --save
  2. Hexo配置文件末尾加入以下配置:

    # hexo-abbrlink config 、固定文章地址插件
    abbrlink:
      alg: crc16  #算法选项:crc16、crc32,区别见之前的文章,这里默认为crc16丨crc32比crc16复杂一点,长一点
      rep: dec    #输出进制:十进制和十六进制,默认为10进制。丨dec为十进制,hex为十六进制
  3. Hexo配置文件中修改permalink如下:

    # URL
    ## If your site is put in a subdirectory, set url as 'http://yoursite.com/child' and root as '/child/'
    url: https://blog.17lai.site
    root: /
    permalink: posts/:abbrlink.html
    permalink_defaults:

这样站点结构就变成了:域名/posts/xxx.html

异步加载JS

方法:将JS文件的引入,放到HTML的body结束标签的上方

<html>
    <head>
        <title>Hello World!</title>
    </head>
    <body>
        xxxxx....
        <script src="xx/xx.js"></script>
    </body>
</html>

原理:首先要明白,HTML的加载是从上往下一行一行解释执行的,把js文件的引入放到下面,这样就会先把HTML页面展示出来,然后再加载js。这样看起来的效果就是,大体的页面先出来,而js让它慢慢加载执行,如果你把js放到网页的上方,效果就是必须要加载完js才能继续展示网页,体验极差。

注意:原主题的js文件尽量不要动,我们只需将自己增加的一些js按照异步加载的方式做即可,比如一些音乐js插件、实时在线聊天js插件等放到最后即可!因为这些文件要加载的东西很多。

字蛛压缩字体

在上面我们介绍了如何在网站上引用自己喜欢的字体,但是这样会出现一个问题:字体文件太大!(尤其是中文,有时候为了几个字引入一个数十兆的字体文件,得不偿失),所有需要字体压缩!

官网 GitHub

使用场景

你的网站中需要自定义字体(额外添加一些普通电脑中没有的字体),但是一般字体是包含很多字符的,这就导致字体文件的体积很大

字蛛作用

字蛛就是自动检测网站的 CSS 与 HTML 文件中的自定义字体(额外加的字体),并将网站中用到的文字重新打包成一个新的字体文件,并自动引入;

没用到的文字就会删除,从而达到压缩字体文件体积的作用。

安装

npm install font-spider -g

在 CSS 中使用 WebFont:

/*声明 WebFont*/
@font-face {
  font-family: 'pinghei';
  src: url('../font/pinghei.eot');
  src:
    url('../font/pinghei.eot?#font-spider') format('embedded-opentype'),
    url('../font/pinghei.woff') format('woff'),
    url('../font/pinghei.ttf') format('truetype'),
    url('../font/pinghei.svg') format('svg');
  font-weight: normal;
  font-style: normal;
}

/*使用选择器指定字体*/
.home h1, .demo > .test {
    font-family: 'pinghei';
}
  1. @font-face 中的 src 定义的 .ttf 文件必须存在,其余的格式将由工具自动生成
  2. 开发阶段请使用相对路径的 CSS 与 WebFont

运行 font-spider 命令:

font-spider ./demo/*.html

页面依赖的字体将会自动压缩好,原 .ttf 字体会备份

webp图像大小优化

把所有图像都转换为webp格式,可以极大减小图片体积,加快加载速度。

gulp 体积压缩

  • 减小体积,加快加载速度
  • 因为 hexo 生成的 html、css、js 等都有很多的空格或者换行,而空格和换行也是占用字节的,所以需要将空格换行去掉也就是我要进行的 “压缩”。
npm install gulp -g
# 安装各种小功能模块  执行这步的时候,可能会提示权限的问题,最好以管理员模式执行
npm install gulp gulp-htmlclean gulp-htmlmin gulp-minify-css gulp-uglify gulp-imagemin --save
# 额外的功能模块
npm install gulp-debug gulp-clean-css gulp-changed gulp-if gulp-plumber gulp-babel babel-preset-es2015 del @babel/core --save
 
或者使用yarn 
 
yarn global add gulp
yarn add gulp gulp-htmlclean gulp-htmlmin gulp-minify-css gulp-uglify gulp-imagemin
yarn add gulp-debug gulp-clean-css gulp-changed gulp-if gulp-plumber gulp-babel babel-preset-es2015 del @babel/core
  • npm下载太慢怎么办? 修改国内淘宝源加速,

然后,在根目录新增 gulpfile.js :

var gulp = require("gulp");
var debug = require("gulp-debug");
var cleancss = require("gulp-clean-css"); //css压缩组件
var uglify = require("gulp-uglify"); //js压缩组件
var htmlmin = require("gulp-htmlmin"); //html压缩组件
var htmlclean = require("gulp-htmlclean"); //html清理组件
var imagemin = require("gulp-imagemin"); //图片压缩组件
var changed = require("gulp-changed"); //文件更改校验组件
var gulpif = require("gulp-if"); //任务 帮助调用组件
var plumber = require("gulp-plumber"); //容错组件(发生错误不跳出任务,并报出错误内容)
var isScriptAll = true; //是否处理所有文件,(true|处理所有文件)(false|只处理有更改的文件)
var isDebug = true; //是否调试显示 编译通过的文件
var gulpBabel = require("gulp-babel");
var es2015Preset = require("babel-preset-es2015");
var del = require("del");
var Hexo = require("hexo");
var hexo = new Hexo(process.cwd(), {}); // 初始化一个hexo对象

// 清除public文件夹
gulp.task("clean", function () {
    return del(["public/**/*"]);
});

// 下面几个跟hexo有关的操作,主要通过hexo.call()去执行,注意return
// 创建静态页面 (等同 hexo generate)
gulp.task("generate", function () {
    return hexo.init().then(function () {
        return hexo
            .call("generate", {
                watch: false
            })
            .then(function () {
                return hexo.exit();
            })
            .catch(function (err) {
                return hexo.exit(err);
            });
    });
});

// 启动Hexo服务器
gulp.task("server", function () {
    return hexo
        .init()
        .then(function () {
            return hexo.call("server", {});
        })
        .catch(function (err) {
            console.log(err);
        });
});

// 部署到服务器
gulp.task("deploy", function () {
    return hexo.init().then(function () {
        return hexo
            .call("deploy", {
                watch: false
            })
            .then(function () {
                return hexo.exit();
            })
            .catch(function (err) {
                return hexo.exit(err);
            });
    });
});

// 压缩public目录下的js文件
gulp.task("compressJs", function () {
    return gulp
        .src(["./public/**/*.js", "!./public/libs/**"]) //排除的js
        .pipe(gulpif(!isScriptAll, changed("./public")))
        .pipe(gulpif(isDebug, debug({ title: "Compress JS:" })))
        .pipe(plumber())
        .pipe(
            gulpBabel({
                presets: [es2015Preset] // es5检查机制
            })
        )
        .pipe(uglify()) //调用压缩组件方法uglify(),对合并的文件进行压缩
        .pipe(gulp.dest("./public")); //输出到目标目录
});

// 压缩public目录下的css文件
gulp.task("compressCss", function () {
    var option = {
        rebase: false,
        //advanced: true, //类型:Boolean 默认:true [是否开启高级优化(合并选择器等)]
        compatibility: "ie7" //保留ie7及以下兼容写法 类型:String 默认:''or'*' [启用兼容模式; 'ie7':IE7兼容模式,'ie8':IE8兼容模式,'*':IE9+兼容模式]
        //keepBreaks: true, //类型:Boolean 默认:false [是否保留换行]
        //keepSpecialComments: '*' //保留所有特殊前缀 当你用autoprefixer生成的浏览器前缀,如果不加这个参数,有可能将会删除你的部分前缀
    };
    return gulp
        .src(["./public/**/*.css", "!./public/**/*.min.css"]) //排除的css
        .pipe(gulpif(!isScriptAll, changed("./public")))
        .pipe(gulpif(isDebug, debug({ title: "Compress CSS:" })))
        .pipe(plumber())
        .pipe(cleancss(option))
        .pipe(gulp.dest("./public"));
});

// 压缩public目录下的html文件
gulp.task("compressHtml", function () {
    var cleanOptions = {
        protect: /<\!--%fooTemplate\b.*?%-->/g, //忽略处理
        unprotect: /<script [^>]*\btype="text\/x-handlebars-template"[\s\S]+?<\/script>/gi //特殊处理
    };
    var minOption = {
        collapseWhitespace: true, //压缩HTML
        collapseBooleanAttributes: true, //省略布尔属性的值 <input checked="true"/> ==> <input />
        removeEmptyAttributes: true, //删除所有空格作属性值 <input id="" /> ==> <input />
        removeScriptTypeAttributes: true, //删除<script>的type="text/javascript"
        removeStyleLinkTypeAttributes: true, //删除<style>和<link>的type="text/css"
        removeComments: true, //清除HTML注释
        minifyJS: true, //压缩页面JS
        minifyCSS: true, //压缩页面CSS
        minifyURLs: true //替换页面URL
    };
    return gulp
        .src("./public/**/*.html")
        .pipe(gulpif(isDebug, debug({ title: "Compress HTML:" })))
        .pipe(plumber())
        .pipe(htmlclean(cleanOptions))
        .pipe(htmlmin(minOption))
        .pipe(gulp.dest("./public"));
});

// 压缩 public/medias 目录内图片
gulp.task("compressImage", function () {
    var option = {
        optimizationLevel: 5, //类型:Number 默认:3 取值范围:0-7(优化等级)
        progressive: true, //类型:Boolean 默认:false 无损压缩jpg图片
        interlaced: false, //类型:Boolean 默认:false 隔行扫描gif进行渲染
        multipass: false //类型:Boolean 默认:false 多次优化svg直到完全优化
    };
    return gulp
        .src("./public/medias/**/*.*")
        .pipe(gulpif(!isScriptAll, changed("./public/medias")))
        .pipe(gulpif(isDebug, debug({ title: "Compress Images:" })))
        .pipe(plumber())
        .pipe(imagemin(option))
        .pipe(gulp.dest("./public"));
});
// 执行顺序: 清除public目录 -> 产生原始博客内容 -> 执行压缩混淆 -> 部署到服务器
gulp.task(
    "cicd",
    gulp.series(
        "clean",
        "generate",
        "compressHtml",
        "compressCss",
        "compressJs",
        "compressImage",
        gulp.parallel("deploy")
    )
);
gulp.task(
    "ci",
    gulp.series(
        "clean",
        "generate",
        gulp.parallel("compressHtml", "compressCss", "compressJs","compressImage")
    )
);
// 默认任务
gulp.task(
    "default",
    gulp.series(
        gulp.parallel("compressHtml", "compressCss", "compressJs","compressImage")
    )
);
//Gulp4最大的一个改变就是gulp.task函数现在只支持两个参数,分别是任务名和运行任务的函数

运行:

hexo clean && hexo g && gulp &&  hexo g

直接在 Hexo 根目录执行 gulp ci,这个命令相当于 hexo cl&&hexo g 并且再把代码和图片压缩。 在 Hexo 根目录执行 gulp cicd ,这个命令与 gulp ci相比是:在最后又加了个 hexo d ,等于说生成、压缩文件后又帮你自动部署了

如果不想用图片压缩可以把"compressImage" 去掉即可

DockerImagin

使用Docker版本的imagemin来压缩图片!一行命令搞定!

gulp-imagemin相关的依赖,以及配置太TMD复杂了,博主新的Docker里面配置很久没搞定,虽然以前搞定过,囧rz! 如是去找了一下Docker镜像,立马搞定!

docker run -v `pwd`:/work mitakeck/imagemin

源代码 mitakeck/docker-imagemin

Python图片无损压缩

[email protected]:xinlin-z/smally.git

说明去项目主页看。有中文说明。

有些小bug,压缩jpeg时遇到webp文件会退出。个人解决方法是硬链接到另一个目录,然后删除所有其它格式的图片,再进行压缩,嗯,完美!

本地搜索优化

html、css和js都压缩了,很开心。但是,还有一个大文件没有压缩,就是本地搜索的DB文件search.xml。这个search.xml文件的大小为7.5M,很大。
打开search.xml文件,发现里面不止包含文章内容,还包含html标签。参考hexo-generator-searchdb,发现可以设置不生成标签。

  • 修改hexo/_config.yml的localsearch配置为:
# local search
search:
  path: search.xml
  field: post
  format: striptags
  limit: 10000
  • 重新生成search.xml文件
  • 还可以给search.xml添加上jsdelivr cdn 加速!

系列教程

全部文章RSS订阅

Hexo系列 HexoRSS分类订阅

[三万字教程]基于Hexo的matery主题搭建博客并深度优化完全一站式教程

  • markdown 各种其它语法插件
  • latex公式支持
  • mermaid图表
  • plant uml图表
  • URL卡片
  • bilibili卡片
  • github卡片
  • 豆瓣卡片
  • 插入音乐和视频
  • 插入脑图

笔记系列 Note分类RSS订阅

经历了很长时间,使用了各种各样的方案,最终选择了一种相对完美的方式。docker私有部署运行的joplin,使用markdown语法,github作为图床,picgo作为图像自动上传后端,pypora作为MD编辑器,Snipaste作为截图工具。后备gitlab ee selfhost备份,自建图床VPS多线负载均衡。cloudflare partner cdn加速,jsdelivr加速。

  • pigo图床搭建与配置
  • Joplin教程
  • Snipaste截图工具
  • Typora 作为Markdown编辑器最强
  • Joplin和使用
  • Joplin同步与备份
  • Joplin导入与导出
  • Joplin安装使用,调用外部编辑器,网盘同步等等
  • Joplin简明教程
  • markdown语法简明教程
  • 教你用各种插件打造一个强大的笔记工具。
  • 如何部署自己私有的为知笔记。
  • 其实博主更推荐私有部署joplin

Gitbook使用系列 Gitbook分类RSS订阅

Gitlab 使用系列 Gitlab RSS 分类订阅


文章作者: 夜法之书
版权声明: 本博客所有文章除特別声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来源 夜法之书 !
评论
 上一篇

阅读全文

基于Hexo的matery主题搭建博客增强部署篇4
基于Hexo的matery主题搭建博客增强部署篇4 基于Hexo的matery主题搭建博客增强部署篇4
如果你想自动化部署怎么办?同时部署到多个空间怎么办?如何多种方法同时使用,多线路负载均衡访问了?本篇文章帮助你一一实现!
2022-03-27
下一篇 

阅读全文

基于Hexo的matery主题搭建博客自定义修改篇2
基于Hexo的matery主题搭建博客自定义修改篇2 基于Hexo的matery主题搭建博客自定义修改篇2
通过第一篇你已经有一个基本完整的博客了,现在可以进行各种各样自定义修改,添加音视频支持,字体修改,图形美化等等,让你的博客功能更加强大,界面更美观。
2022-03-27
  目录