Skip to content

NPCDW/HtmlDiff

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

17 Commits
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

HtmlDiff

Html文本比对实现,基于google的diff_match_patch

尝试一下:https://npcdw.github.io/HtmlDiff/

HtmlDiff支持比对两个html,然后生成添加标记的两个html,并保证样式不会乱,支持添加到忽略列表的标签不进行对比

还支持对比后生成一个html(非常不推荐,因为格式可能会错乱,例如两个结构不同的表格对比,不推荐为什么还要做?领导要求的)

效果图如下: image 对比两个简单的、没有格式的文本可以直接使用 google 的 diff-match-patch 进行对比。

对比html难点在于

  1. 如何忽略掉不需要进行对比的标签,只对比标签中间的文本
  2. 如果修改了样式我们该怎么对比出来
  3. 对比完文本后,我们该怎样把标签原封不动的分别还原到两段html标签中

我提供的思路只解决了第一条和第三条,关于第二条,没找到解决的方法,所以本文标题才叫做 Html文本对比 下面说一下我的思路和实现:

首先、我们需要保存好两段原始的html文本,以下简称为原始html1和原始html2。

然后、分别创建一个原始html1和原始html2的副本,然后分别将副本的标签去掉,只保留其中的文本,以下简称原始文本1和原始文本2。

第三、使用google的 diff-match-patch 将文本进行对比,对比完成返回的结果样式应该是这样的

[
  {
    "0": 0,
    "1": "Hamlet: Do you see "
  },
  {
    "0": -1,
    "1": "yonder cloud"
  },
  {
    "0": 1,
    "1": "the cloud over there"
  }
]

解释一下:

字符串 "0" 代表对比结果的类型,数字 0 代表相同的文本,-1 代表原始文本1相对于原始文本2删除的文本,1 代表原始文本1相对于原始文本2增加的文本。

字符串 "1" 代表对比结果的文本

这个列表是有顺序的,所有的类型为 0 和类型为 -1 的文本前后拼接起来就是原始文本1,所有的类型为 0 和类型为 1 的文本前后拼接起来就是原始文本2。

我们将所有的类型为 0 和类型为 -1 的列表称为对比列表1,将所有的类型为 0 和类型为 1 的列表称为对比列表2

第四、开始还原原始的 html 文本,并在其中加入插入标签 <ins></ins> 和删除标签 <del></del>,还原的过程大致如下:

因为两个html文本的还原过程一致,我们只拿第一个举例。

1、创建一个用于还原的html文本,我们称之为还原html

2、我们取出原始html1中的最前面一段,选取的规则是取出一段【文本】,如果一开始就是文本,而非标签(开始标签和结束标签都算标签),那么就取这段文本,遇到标签结束,如果一开始就是标签,那么取出这段标签和之后遇到文本,同样是遇到下一段标签结束,例如:

</span><div></div><div><p>这是一块文本

我们将取出的标签和文本称之为选取标签和选取文本

3、将选取标签直接追加到还原文本末尾,将选取文本与对比列表中的第一段文本(以下简称第一段对比文本)进行对比,

  1. 如果选取文本等于第一段对比文本,将选取文本追加到还原文本末尾,删除原始html的选取部分,删除选取列表的第一块
  2. 如果选取文本小于第一段对比文本,将选取文本追加到还原文本末尾,删除原始html的选取部分,删除第一段对比文本中选取文本的部分,再取出原始html文本。。。。。重复此过程
  3. 如果选取文本大于第一段对比文本,将第一段对比文本追加到还原文本末尾,删除选取文本中第一段对比文本的部分,删除选取列表的第一块,再取出选取列表的第一块,再与选取文本对比。。。。重复此过程

直到原始html的长度变成0,或对比列表的长度变成0,直接将剩下的部分都追加到还原文本末尾,那么还原的过程就结束了。