欧美一区二区三区,国内熟女精品熟女A片视频小说,日本av网,小鲜肉男男GAY做受XXX网站

如何在沒有JavaScript的情況下安全地將不受信任的輸入分配給CSS自定義屬性?

假設(shè)我有一個(gè)字符串鍵和字符串值的對(duì)象,我想把它們作為CSS自定義屬性寫到服務(wù)器生成的HTML中。我怎么能這么安全地做呢?

我說的安全是指

如果可能的話,自定義屬性聲明不應(yīng)該導(dǎo)致CSS語(yǔ)法錯(cuò)誤,從而阻止瀏覽器正確解析其他樣式聲明或HTML文檔的一部分。如果由于某種原因這是不可能的,那么鍵值對(duì)應(yīng)該被省略。 更強(qiáng)烈的是,不應(yīng)該有跨站點(diǎn)腳本的可能性。 為了簡(jiǎn)單起見,我將把鍵限制為只允許類[a-zA-Z0-9_-]中的字符。

通過閱讀CSS規(guī)范和一些個(gè)人測(cè)試,我認(rèn)為我可以通過以下步驟獲取值:

尋找字符串 確保每個(gè)引號(hào)后面都跟有另一個(gè)相同類型的(非轉(zhuǎn)義)引號(hào)(& quot或者’)。如果不是這樣,就放棄這個(gè)鍵/值對(duì)。 確保字符串外部的每個(gè)左大括號(hào){([都有一個(gè)匹配的右大括號(hào)。如果不是,就丟棄這個(gè)鍵值對(duì)。 轉(zhuǎn)義& lt與\3C和所有& gt和3E一起。 轉(zhuǎn)義的所有實(shí)例;與\3B。 我想出了基于CSS語(yǔ)法規(guī)范的上述步驟

對(duì)于上下文,這些屬性可能被我們?cè)趧e處插入的用戶自定義樣式所使用,但是同一個(gè)對(duì)象也被用作模板中的模板數(shù)據(jù),因此它可能包含作為內(nèi)容的字符串和作為CSS變量的字符串的混合。我覺得上面的算法取得了一個(gè)很好的平衡,既非常簡(jiǎn)單,又不會(huì)冒險(xiǎn)丟棄太多可能在CSS中有用的鍵值對(duì)(即使考慮將來對(duì)CSS的添加,但我想確保我沒有遺漏什么。

下面是一些JS代碼,展示了我想要實(shí)現(xiàn)的目標(biāo)。obj是正在討論的對(duì)象,preprocessPairs是一個(gè)函數(shù),它接受對(duì)象并對(duì)其進(jìn)行預(yù)處理,按照上面的步驟刪除/重新格式化值。

function generateThemePropertiesTag(obj) {
  obj = preprocessPairs(obj);
  return `<style>
:root {
${Object.entries(obj).map(([key, value]) => {
  return `--theme-${key}: ${value};`
}).join("\n")}
}
</style>`
}

所以當(dāng)給一個(gè)像這樣的物體時(shí)

{
  "color": "#D3A",
  "title": "The quick brown fox"
}

我希望CSS看起來像這樣:

:root {
--theme-color: #D3A;
--theme-title: The quick brown fox;
}

雖然- theme-title在CSS中是一個(gè)非常無用的自定義變量,但它實(shí)際上并沒有破壞樣式表,因?yàn)镃SS忽略了它不理解的屬性。

我們實(shí)際上可能只使用正則表達(dá)式和一些其他算法,而不必依賴于一種特定的語(yǔ)言,希望這是你在這里需要的。

通過聲明對(duì)象鍵在[a-zA-Z0-9_-]內(nèi),我們需要以某種方式解析值。

價(jià)值模式 因此,我們可以將其分為幾類,看看我們會(huì)遇到什么(為了清楚起見,可能會(huì)稍微簡(jiǎn)化):

。* '(用撇號(hào)括起來的字符串;貪婪) "。* & quot(雙引號(hào)括起來的字符串;貪婪) [+-]?\d+(\。\d+)?(%|[A-z]+)?(整數(shù)和小數(shù),可選百分比或單位) #[0-9A-f]{3,6}(顏色) [A-z0-9_-]+(關(guān)鍵字、命名顏色、類似& quot放松& quot) ([\w-]+)\([^)]+\](像url()、calc()等函數(shù)。) 首次過濾 我可以想象,在試圖識(shí)別這些模式之前,你可以做一些過濾。也許我們首先修剪值串。正如你提到的,& lt并且& gt可以在preprocessPairs()函數(shù)的開頭進(jìn)行轉(zhuǎn)義,因?yàn)樗粫?huì)出現(xiàn)在上面的任何模式中。如果您不希望在任何地方出現(xiàn)未轉(zhuǎn)義的分號(hào),您也可以對(duì)它們進(jìn)行轉(zhuǎn)義。

識(shí)別模式 然后,我們可以嘗試識(shí)別值中的這些模式,對(duì)于每個(gè)模式,我們可能需要再次運(yùn)行過濾。我們預(yù)計(jì)這些模式將由一些空白字符(或兩個(gè))分隔。

包括對(duì)多行字符串的支持應(yīng)該沒問題,那是轉(zhuǎn)義換行符。

語(yǔ)言環(huán)境 我們需要認(rèn)識(shí)到,我們至少在過濾兩種上下文——HTML和CSS。因?yàn)槲覀冊(cè)? ltstyle & gt元素,輸入必須是安全的,同時(shí)它必須是有效的CSS。幸運(yùn)的是,您沒有在元素的style屬性中包含CSS,所以這稍微容易一些。

基于價(jià)值模式的過濾 被撇號(hào)包圍的字符串——除了撇號(hào)和分號(hào)之外,我們什么都不關(guān)心,所以我們需要在字符串中找到這些字符的非轉(zhuǎn)義實(shí)例,并對(duì)它們進(jìn)行轉(zhuǎn)義 同上,只是用了雙引號(hào) 應(yīng)該沒問題 應(yīng)該沒問題 非常好 這是有趣的部分 因此,第1-5點(diǎn)將非常容易,通過前面的簡(jiǎn)單過濾和修整將覆蓋大多數(shù)值。通過一些添加(不知道對(duì)性能有什么影響),它甚至可以對(duì)正確的單位、關(guān)鍵字等進(jìn)行額外的檢查。

但我認(rèn)為,與其他要點(diǎn)相比,第六點(diǎn)是一個(gè)相對(duì)更大的挑戰(zhàn)。您可能決定在這種自定義樣式中簡(jiǎn)單地禁止url(),讓您檢查函數(shù)的輸入,因此,例如,您可能想要轉(zhuǎn)義分號(hào),甚至可能再次檢查函數(shù)內(nèi)部的模式,并進(jìn)行微小的調(diào)整,例如calc()。

結(jié)論 大體上這是我的觀點(diǎn)。通過對(duì)這些正則表達(dá)式進(jìn)行一些調(diào)整,它應(yīng)該能夠補(bǔ)充您已經(jīng)做的工作,并為輸入CSS提供盡可能多的靈活性,同時(shí)使您不必在每次調(diào)整CSS功能時(shí)都調(diào)整代碼。

例子

function preprocessPairs(obj) {
  // Catch-all regular expression
  // Explanation:
  // (                                   Start of alternatives
  //   \w+\(.+?\)|                       1st alternative - function
  //   ".+?(?<!\\)"|                     2nd alternative - string with double quotes
  //   '.+?(?<!\\)'|                     3rd alternative - string with apostrophes
  //   [+-]?\d+(?:\.\d+)?(?:%|[A-z]+)?|  4th alternative - integer/decimal number, optionally per cent or with a unit
  //   #[0-9A-f]{3,6}|                   5th alternative - colour
  //   [A-z0-9_-]+|                      6th alternative - keyword
  //   ''|                               7th alternative - empty string
  //   ""                                8th alternative - empty string
  // )
  // [\s,]*
  const regexA = /(\w+\(.+?\)|".+?(?<!\\)"|'.+?(?<!\\)'|[+-]?\d+(?:\.\d+)?(?:%|[A-z]+)?|#[0-9A-f]{3,6}|[A-z0-9_-]+|''|"")[\s,]*/g;

  // newObj contains filtered testObject
  const newObj = {};

  // Loop through all object properties
  Object.entries(obj).forEach(([key, value]) => {
    // Replace <>;
    value = value.trim().replace('<', '\\00003C').replace('>', '\\00003E').replace(';', '\\00003B');

    // Use catch-all regex to split value into specific elements
    const matches = [...value.matchAll(regexA)];

    // Now try to build back the original value string from regex matches.
    // If these strings are equal, the value is what we expected.
    // Otherwise it contained some unexpected markup or elements and should
    // be therefore discarded.
    // We specifically set to ignore all occurences of url() and @import
    let buildBack = '';
    matches.forEach((match) => {
      if (Array.isArray(match) && match.length >= 2 && match[0].match(/url\(.+?\)/gi) === null && match[0].match(/@import/gi) === null) {
        buildBack += match[0];
      }
    });

    console.log('Compare\n');
    console.log(value);
    console.log(buildBack);
    console.log(value === buildBack);

    if (value === buildBack) {
      newObj[key] = value;
    }
  });

  return newObj;
}

如果我忘記觸及你特別感興趣的話題,請(qǐng)?jiān)u論、討論、批評(píng),并讓我知道。

來源 免責(zé)聲明:我不是下面提到的來源的作者、所有者、投資者或貢獻(xiàn)者。我只是碰巧用它們來獲取一些信息。

https://www.w3.org/TR/css-values-3 https://owasp . org/www-project-we b-Security-Testing-guide/v 41/4-Web _ Application _ Security _ Testing/11-Client _ Side _ Testing/05-Testing _ for _ CSS _ Injection https://cheatsheetseries . owasp . org/Cheat Sheets/Securing _ Cascading _ Style _ Sheets _ Cheat _ sheet . html