html實體編碼趕上js代碼

單雙引號

在js代碼中

在js中單、雙引號引發來的是字符串,若是咱們要在字符串中使用單、雙引號,須要反斜槓進行轉義html

let str='user\'s name';
// or
let str=" user's name";
// or
let str="she said:\"...\".";

若是在字符串中輸出反斜槓,仍然是用反斜槓轉義,即2個反斜槓輸出1個反斜槓git

在html代碼中

html標籤中,屬性值一般用雙引號引發來,也可使用單引號或不用引號。github

<input name=user />
<input name="user" />
<input name='user' />

這3種寫法都正確,不過一般咱們是選擇用雙引號引發來。
若是咱們要在屬性值中使用單、雙綽號,咱們不能直接寫成下面這樣dom

<input name=user'name />
<input name="user"name" />
<input name='user'name' />

這些所有是錯誤的。咱們要像在js中對單、雙引號轉義同樣,對屬性中的單、雙引號轉義xss

在html中輸出預留符號,可使用字符實體轉義的形式,這裏有簡單介紹:http://www.w3school.com.cn/html/html_entities.asp。即想輸出一個雙引號可使用&quot;的形式,工具

<input name="user&quot;name" />

除此以外,html還支持十進制與十六進制編碼的形式輸出字符,如咱們知道字符aascii碼的十進制是97 十六進制是61
因此咱們在頁面body中輸出一個字符a,有如下3種形式編碼

<body>
  a<!--直接輸出-->
  &#97;<!--十進制輸出-->
  &#x61;<!--十六進制輸出-->
</body>

一樣,單雙引號也有十進制(單:39,雙:34)與十六進制(單:27,雙:22),因此咱們在屬性中輸出一個單引號有2種選擇,十進制與十六進制code

<input name='user&#39;name' /><!--十進制-->
<input name='user&#x27;name' /><!--十六進制-->

而輸出一個雙引號則有3種選擇htm

<input name="user&quot;name" /><!--實體-->
<input name="user&#34;name" /><!--十進制-->
<input name="user&#x22;name" /><!--十六進制-->

當js代碼趕上實體編碼

咱們能夠經過dom節點提供的事件寫上調用js的代碼,如點擊body彈出hello這個字符串,咱們能夠寫成事件

<body onclick="alert('hello')">
click here
</body>

若是咱們的需求是就彈出一個雙引號呢?
根據前述規則,咱們要寫成:

<body onclick="alert('&quot;')"><!--這裏用十進制或十六進制均可以-->
click here
</body>

固然,alert裏的單引號也可使用十進制或十六進制編碼

<body onclick="alert(&#34;&#39;&#34;)"><!--&#34;單引號  &#39;雙引號-->
click here
</body>

這樣也是能夠的。
是否是有點xss的感受?

若是咱們把彈雙引號的需求改爲單引號呢?

<body onclick="alert(''')"><!--這樣html中是合法的,但js中並不合法,由於在js中,中間的單引號並無轉義-->
click here
</body>

若是咱們用十進制或十六進制編碼呢?

<body onclick="alert('&#34;')"><!--這樣能夠嗎-->
click here
</body>

這樣仍然是不能夠的

咱們要對js字符串中的單引號進行轉義,如

<body onclick="alert('\'')"><!--轉義後可正確彈出-->
click here
</body>

<body onclick="alert('\&#34;')"><!--轉義後可正確彈出-->
click here
</body>

前面的onclick="alert('\'')"看起來還正常,後面的這個onclick="alert('\&#34;')"就有點不直觀了。由於後面這個看上去反斜槓像在轉義&這1個字符,而&在js的字符串中並不須要轉義的。

動態輸出

如前述的alert彈出的消息,若是是一個變量控制,動態輸出呢?

<body onclick="alert('${msg}')">
click here
</body>

那咱們這個msg字符串就得注意了,從這個示例來看,這個動態的msg即出如今屬性onclick中,也出如今alert的單引號開始的字符串中。

咱們要對msg中的雙引號轉成&quot;&#34;&#x22;,並對msg中單引號的前面加上一個反斜槓\ ?

題外話:對msg中的反斜槓須要作double處理,由於反斜槓在html屬性中並非特殊的,但在js的字符串中是特殊的。所以正確的作法是對反斜槓及單引號前面各加上一個反斜槓

然而,你並不能保證屬性是用雙引號,alert中的字符串用的是單引號,由於能夠寫成下面這樣

<body onclick='alert("${msg}")'>
click here
</body>

?

這種狀況咱們要對msg中的單引號轉成&#39&#x27,並對msg中雙引號前面加上一個反斜槓\

題外話:同上

看上去要根據不一樣的狀況作不一樣的處理,其實也不須要
咱們只須要對單、雙引號前面加上一個反斜槓\而後再對單、雙引號實體編碼便可。

在js中若是反斜槓後面跟的不須要反斜槓轉義的字符,那麼這個反斜槓是被丟棄的,所以像

var str="user\'s name";

單引號前面多加一個反斜槓也沒關係的。

自動化處理與識別提醒

在magix項目中,因爲magix-combine的支持,可識別出屬性中js代碼的部分,並自動化處理,如

<button mx-click="showName({name:'<%=name%>'})">click here</button>

name這個變量可包含任意的單、雙引號及反斜槓。工具自動識別並處理,開發者不須要作任何事情。

而對於這樣的寫法:

<button mx-click="showName({name:'&#34;'})">click here</button>
<!-- or-->
<button mx-click="showName({name:'\&#34;'})">click here</button>

第一種寫法其實並不正確,但第二種狀況看上去又怪怪的。magix-combine工具能識別出來是否須要添加反斜槓,並自動添加處理。
第一種須要添加反斜槓,工具會自動加上,並提醒開發者這裏的寫法是不正確的。
第二種說明開發者意識到了問題所在,本身處理了,工具就再也不處理也再也不提醒開發者。

相關連接:

https://github.com/thx/magix
https://github.com/thx/magix-combine

相關文章
相關標籤/搜索