关于浏览器对于HTML实体编码,urlencode,Unicode解析
目录
HTML实体编码
URL编码
Unicode编码
解析层次逻辑
为什么<script></script>不可以编码符号
为什么不能编码JavaScript:协议
为什么RCDATA标签中的都会被解析成文本
为什么HTML编码了<>无法执行
HTML实体编码
通过特殊语法(<、>)表示保留字符,防止和HTML标签冲突。
URL编码
URL地址栏编码,表现形式为%开头
Unicode编码
JavaScript本身支持的编解码方式,表现形式为\u000a等。
解析层次逻辑
HTML实体编码-->URLcode-->Unicode编码
注:三者有自己的解析器,是一个传递调用过程。
具体案例分析
<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Document</title>
</head>
<body><a href="%6a%61%76%61%73%63%72%69%70%74:%61%6c%65%72%74%28%31%29">aaa</a>url编码了JavaScript:协议,不可以<br><a href="javascript:%61%6c%65%72%74%28%32%29">222</a>可以,JavaScript:被实体编码,但是HTML解析在url前,所以可以成功执行<br><a href="javascript%3aalert(3)"></a>编码了协议符号,不可以<br><div><img src=x onerror=alert(4)></div>不可以,编码了<>,虽然会解析,但是被当作文本,不回进入标签开始状态<br><textarea><script>alert(5)</script></textarea>不可以,rcdata元素,里的标签会被当作文本<br><textarea><script>alert(6)</script></textarea>不可以,同第5条<br><button onclick="confirm('7');">Button</button>可以执行,HTML实体编码单引号会先解析,传递给JavaScript时就可以执行<br><button onclick="confirm('8\u0027);">Button</button>不可以,Unicode编码单引号,无法解析,JavaScript并不会解析<br><script>alert(9);</script>不可以,script标签内默认是JavaScript代码,HTML不会解析,JavaScript不认识HTML编码后的内容<br><script>\u0061\u006c\u0065\u0072\u0074(10);</script>可以,JavaScript可以解析Unicode编码<br><script>\u0061\u006c\u0065\u0072\u0074\u0028\u0031\u0031\u0029;</script>不可以,JavaScript不可以编码符号<br><script>\u0061\u006c\u0065\u0072\u0074(\u0031\u0032)</script>不可以,因为解析返回是字符串,字符串12需要引号包裹,所以这里是有一个语法错误<br><script>alert(\u002713\u0027)</script>不可以,编码符号JavaScript不认识<br><script>alert('14')\u000a</script>不可以,可以换行,但是被Unicode编码了就不可以了<br><a href="javascript:%5c%75%30%30%36%31%5c%75%30%30%36%63%5c%75%30%30%36%35%5c%75%30%30%37%32%5c%75%30%30%37%34(15)">15</a>可以,遵守了解码顺序,可以执行</body>
</html>
为什么<script></script>不可以编码符号
<script></script>属于“原始文本”元素,在块内的字符引用并不会被解析和解码,这是为什么呢?
字符串中:当Unicode转义序列存在于字符串中时,它只会被解释为正规字符,而不是单引号,双引号或者换行符这些能够打破字符串上下文的字符。这项内容清楚地写在ECMAScript中。因此,Unicode转义序列将永远不会破环字符串上下文,因为它们只能被解释成字符串常量。
为什么不能编码JavaScript:协议
URL解析器只认识ascii类型,一旦编码URL解析器不认识就是一个无协议状态,不会让JavaScript解析器来解析,自然就执行不了。2为什么能执行,因为HTML解析器的优先级在URL解析器之前,先解析成了JavaScript:协议,URL解析器自然就认识了,交给JavaScript解析器处理执行。
为什么RCDATA标签中的都会被解析成文本
RCDATA中有<textarea>,<title>标签,在HTML解析器解析RCDATA 标签时,进入RCDATA状态,在这个状态能被识别为标签的只有</textarea>,</title>。这就解释了为什么RCDATA中的任意代码无法执行。
为什么HTML编码了<>无法执行
当HTML解析器遇到<时后面没有/,就认为是标签的开始,进入标签开始状态。那为什么不行呢?因为当HTML解析了<>的编码后,进入不了标签开始状态,不是标签,自然无法执行。