11.应用中如何对静态资源加载失败的场景做降级处理?

1. 场景

有哪些资源会加载失败呢?

  • 图片
  • css文件
  • JS文件
  • CDN
  • 字体文件
  • 服务端渲染失败

2. 方案

2.1 图片处理

  1. 图片要设置占位符,并且设置alt属性来描述图片
  2. 对于图片做一个重试的机制,这个图片为什么出错?(404资源不存在、无权限,使用CDN存储无权限)
  3. 上传服务器端解析错误
<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title></title>
	</head>
	<body>
		<img src="image.png" alt="错误图片" onerror="handleImageError(this)">
		<script>
			function handleImageError(image){
				image.onError=null//防止死循环
				image.src='placeholder.png'//占位图
			}
		</script>
	</body>
</html>

2.2 css文件处理

  • 关键性样式、通过内联
  • 备用样式
  • 上报
<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<link rel="stylesheet" href="style.css" onerror="handleCssError()">
		<title></title>
		<style>
			body{
				font-size: 12px;
			}
		</style>
	</head>
	<body>
		<script>
			function handleCssError(){
				const fallbackCss=document.createElement('link')
				fallbackCss.ref='stylesheet'
				fallbackCss.href='fallback-style.css'
				document.head.append(fallbackCss)
			}
		</script>
	</body>
</html>

2.3 js文件处理

  • 内联脚本
  • 备用脚本处理
  • 上报监控平台
<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title></title>
	</head>
	<body>
		<script src="main.js" onerror="handleJsError()"></script>
		
		<script>
			function handleJsError(){
				const fallbackScript=document.createElement('script')
				fallbackScript.src='fallback-main.js'
				document.head.append(fallbackScript)
			}
		</script>
	</body>
</html>

2.4 CDN 错误

  • 本地备份,如果cdn出错了,就是用本地备份
  • 动态切换,切换到另一个有用的CDN服务

和JS处理一致

2.5 字体处理

  • 使用降级字体 apple、微软雅黑
  • 通过webfont处理字体问题
@font-face {
	font-family: 'CustomFont';
	src: url('customfont.woff2') format('woff2');
	font-display: swap;
}
body{
	font-family: 'CustomFont',Arial,sans-serif;
}

2.6 服务器端渲染

一般出错了之后整个页面就已经不能访问了

  • 降级的html渲染使用客户端渲染
  • 切换为客户端渲染