Skip to content

【建议】:使用 onerror 事件来改善外部引用 cdn 资源失败时切回内部本地文件 #902

@Tikas

Description

@Tikas

检查清单

  • 已经搜索过,没有发现类似 issue。
  • 已经阅读 hexo 官方文档,未发现原生支持。

需求描述

想法来源

昨天在开发主题时,给局域网的设备访问,由于局域网并没有开启 "正确" 上网方式,导致使用 cdnjs 引用的 js 和 css 文件无法正常加载,为此想到了为何不在加载失败后切回本地文件呢?

实现原理

好吧,其实我根本没学 js,全程是和 chatGPT 对话以达到最终实现。

实现代码例子

2023 年 8 月 28 日修改了判断语句,之前的判断语法不正确,非常抱歉,首次开发,很多还不是很了解,修改内容具体示例如下:

if theme.swiper_cdnjs.js.src !== ''

//- 改正:

if theme.swiper_cdnjs.js.src

JS 部分我是这样写的,在 cdn 文件加载失败后能正常切换回本地文件,并执行 Swiper 成功

(修改:在此处增加提示,此为 PUG 格式)

if homePage && theme.slide.enable
  script.
    function loadSwiperJS() {
      const script = document.createElement('script')
      script.src = '/js/swiper-bundle.min.js'
      script.onload = () => {
        initSwiperConfig()
      }
      document.body.appendChild(script)
    }
    function initSwiperConfig() {
      let homeSwiper = new Swiper('.home-swiper', {
        spaceBetween: 30,
        centeredSlides: true,
        effect: 'fade',
        loop: true,
        autoplay: {
          delay: 8000,
          disableOnInteraction: false
        }
      })
    }

  //- import swiper js
  if theme.swiper_cdnjs.enable && theme.swiper_cdnjs.js.src
    if theme.swiper_cdnjs.js.integrity
      script(src=url_for(theme.swiper_cdnjs.js.src) integrity=theme.swiper_cdnjs.js.integrity crossorigin='anonymous' referrerpolicy='no-referrer' onerror='loadSwiperJS()' onload='initSwiperConfig()')
    else
      script(src=url_for(theme.swiper_cdnjs.js.src) crossorigin='anonymous' referrerpolicy='no-referrer' onerror='loadSwiperJS()' onload='initSwiperConfig()')
  else
    script(src=url_for(theme.slide.js) onload='initSwiperConfig()')

CSS 部分的代码:(修改:在此处增加提示,此为 PUG 格式)

if theme.slide.enable && homePage
  script.
    function loadSwiperCSS() {
      const link = document.createElement('link')
      link.rel = 'stylesheet'
      link.href = '/css/swiper-bundle.min.css'
      document.head.appendChild(link)
    }
  if theme.swiper_cdnjs.enable && theme.swiper_cdnjs.css.href
    if theme.swiper_cdnjs.css.integrity
      link(rel='stylesheet' href=url_for(theme.swiper_cdnjs.css.href) integrity=theme.swiper_cdnjs.css.integrity crossorigin='anonymous' referrerpolicy='no-referrer' onerror='loadSwiperCSS()')
    else
      link(rel='stylesheet' href=url_for(theme.swiper_cdnjs.css.href) crossorigin='anonymous' referrerpolicy='no-referrer' onerror='loadSwiperCSS()')
  else
    link(rel='stylesheet' href=url_for(theme.slide.css))

主题配置文件参考:

# 启用后,本地的 slide js 和 css 将会在 cdn 加载出错时调用,请确保 slide 里的 js 和 css 有设置
swiper_cdnjs:
  enable: true
  js:
    src: https://cdnjs.cloudflare.com/ajax/libs/Swiper/10.2.0/swiper-bundle.min.js
    integrity: sha512-QwpsxtdZRih55GaU/Ce2Baqoy2tEv9GltjAG8yuTy2k9lHqK7VHHp3wWWe+yITYKZlsT3AaCj49ZxMYPp46iJQ==
  css:
    href: https://cdnjs.cloudflare.com/ajax/libs/Swiper/10.2.0/swiper-bundle.min.css
    integrity: sha512-s6khMl5GDS1HbQ5/SwL1wzMayPwHXPjKoBN5kHUTDqKEPkkGyEZWKyH2lQ3YO2q3dxueG3rE0NHjRawMHd2b6g==

slide:
  enable: true
  js: /js/swiper-bundle.min.js # 当 swiper_cdnjs 开启时,只有出错时才会加载本地 swiper js
  css: /css/swiper-bundle.min.css # 当 swiper_cdnjs 开启时,只有出错时才会加载本地 swiper css

额外求助

2023年9月8号修改了此部分,求助的内容是想把引入的 script 代码里 js 文件使用变量去取代,具体可以看上面的代码。

现在已经找到了实现的办法,使用 pug 的插值去实现,具体代码如下:

if homePage && theme.slide.enable
  script.
    function loadSwiperJS() {
      const script = document.createElement('script')
      script.src = '/js/swiper-bundle.min.js'
      script.onload = () => {
        initSwiperConfig()
      }
      document.body.appendChild(script)
    }

//- 改正:

if homePage && theme.slide.enable
  script.
    function loadSwiperJS() {
      const script = document.createElement('script')
      script.src = '#{theme.slide.js}'
      script.onload = () => {
        initSwiperConfig()
      }
      document.body.appendChild(script)
    }

参考链接

暂无

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions