簡體   English   中英

用於查找未封閉 HTML 標簽的 JavaScript 庫/函數

[英]JavaScript Library/Function to find Unclosed HTML Tags

我目前正在尋找一種解決方案來從原始 HTML 的任意切片中查找和列出任何未關閉的 HTML 標簽。 我不覺得這應該是一個可怕的問題,但我似乎無法在 JS 中找到可以做到這一點的東西。 不幸的是,這需要在客戶端進行,因為它用於將注釋渲染到 HTML 頁面。 顯然,注釋有點討厭,因為它們選擇或應用的格式可能僅適用於 HTML 元素的一部分(即,標記覆蓋在現有的 HTML 標記上)。

一個簡單的用例是您可能只想呈現 HTML 頁面的一部分,然后再注入其余部分。 例如,想象一個假設段:

<p>This is my text <StartDelayedInject/> with a comment I added. </p>
<p> But it doesn't exist until now. </p> <StopDelayedInject/>

我將進行一些預處理以重建 HTML,以便將部分元素包裝到應用適當格式的跨度類型元素中。 最初這將以以下形式解析:

<p><span>This is my text</span></p>

在一些用戶操作之后,它將被修改為一個形式,例如:

<p><span>This is my text</span><span>with a comment I added.</span></p>
<p>But it doesn't exist until now.</p>

這是一個非常簡化的示例案例(顯然像 ul 元素和表格之類的東西變得更加復雜),但給出了一般原則。 但是,要有效地執行此操作,我需要能夠檢查一段 HTML 並找出已打開(但未關閉)的標簽。 如果我知道該信息,我可以將最后一個未終止的文本數據包裝到一個跨度中,關閉未關閉的標簽,並知道在需要時返回該點以注入剩余的內容。 但是,我需要知道仍處於打開狀態的標簽,以便在我注入或修改另一段內容時,可以確保將其放在正確的位置(例如,在第一段)。

從我對上下文無關語法的理解來看,這應該是一項相對微不足道的任務。 每次打開/進入或關閉/退出標簽時,您可以保持一堆標簽打開但尚未關閉。 話雖如此,我寧願使用一個更成熟的解決方案的庫,而不是為此目的制作天真的解析器。 我假設周圍有一些 JS HTML 解析器可以做到這一點,對吧? 他們中的很多人都知道如何關閉標簽,所以他們在某些時候很清楚地計算了這一點。

問題是 JavaScript 只能通過兩種方式訪問​​ html:

  1. 從某種意義上說,每個元素都是一個具有瀏覽器在頁面加載時創建的屬性和方法的對象。
  2. 從某種意義上說,它是一串文本。

使用與 html 交互的第一種方法,無法檢測未關閉的標簽,因為您只能訪問瀏覽器在解析 html 后為您創建的對象。

使用第二種方法,您必須通過 html 解析器運行整個 html 字符串。 有些人可能會認為您可以簡單地使用 regexp 來完成,但是,這是不可行的。 我向您推薦這個奇妙的stackoverflow 問題

即使您找到了一個非常強大的 html 解析器來使用,您仍然會遇到這樣一個事實,即在您的 JavaScript 甚至觸及它之前,瀏覽器將嘗試解析可能損壞的 html,並且可能到處都有錯誤。

編輯:

如果您喜歡解析器的想法,John Resig 創建了這個您可能想要參考的示例

不完美,但這是我檢查打開/關閉標簽之間不匹配的快速方法:

function find_unclosed_tags(str) {
    str = str.toLowerCase();
    var tags = ["a", "span", "div", "ul", "li", "h1", "h2", "h3", "h4", "h5", "h6", "p", "table", "tr", "td", "b", "i", "u"];
    var mismatches = [];
    tags.forEach(function(tag) { 
        var pattern_open = '<'+tag+'( |>)'; 
        var pattern_close = '</'+tag+'>'; 

        var diff_count = (str.match(new RegExp(pattern_open,'g')) || []).length - (str.match(new RegExp(pattern_close,'g')) || []).length;

        if(diff_count != 0) {
            mismatches.push("Open/close mismatch for tag " + tag + ".");
        }
    });

    return mismatches;
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM