【问题标题】:Comparing two HTML files using Python difflib package使用 Python difflib 包比较两个 HTML 文件
【发布时间】:2020-07-13 06:48:22
【问题描述】:

我在使用 Pythob difflib 比较两个 HTML 文件时遇到问题。虽然我能够生成一个突出显示所有更改的比较文件,但当我打开比较文件时,它显示的是原始 HTML 和 CSS 脚本/标签,而不是纯文本。

例如

<Html><Body><div class="a"> Text Here</div></Body></html>

而不是

Text Here

我的 Python 脚本如下:

import difflib

file1 = open('file1.html', 'r').readlines()
file2 = open('file2.html', 'r').readlines()
diffHTML = difflib.HtmlDiff()
htmldiffs = diffHTML.make_file(file1,file2)

with open('Comparison.html', 'w') as outFile:
     outFile.write(htmldiffs)

我的输入文件看起来像这样

                    <!DOCTYPE html>
            <html>
                    <head>
                        <title>Text here</title>        
                    <style type="text/css">
            @media all {
                h1 {
                    margin: 0px;
                    color: #222222;
                }
                #page-title {
                    color: #222222;
                    font-size: 1.4em;
                    font-weight: bold;
                }
                body {
                    font: 0.875em/1.231 tahoma, geneva, verdana, sans-serif;
                    padding: 30px;
                    min-width: 800px;
                }
                .divider {
                    margin: 0.5em 15% 0.5em 10%;
                    border-bottom: 1px solid #000;
                }
                
                }
                .section.header {
                    background-color: #303030;
                    color: #ffffff;
                    font-weight: bold;
                    margin: 0 0 5px 0;
                    padding: 5px 0 5px 5px;
                }
                .section.subheader {
                    background-color: #CFCFCF;
                    color: #000;
                    font-weight: bold;
                    padding: 1px 5px;
                    margin: 0px auto 5px 0px;
                }
                
            
        
                .response_rule_prefix {
                    font-style: italic;
                }

                .exception-scope
                {
                    color: #666666;
                    padding-bottom: 5px;
                }

                .where-clause-header
                {
                    color:#AAAA99;
                }

                .section {
                    padding: 0em 0em 1.2em 0em;
                }

                #generated-Time {
                    padding-top:5px;
                    float:right;
                }
                #page-title, #generated-Time {
                    display: inline-block;
                }
            

        
            </style></head>

                    <body>
            <div id="title-section" class="section ">
                            <div id="page-branding">
                                <h1>Title</h1>
                            </div>
                            <div id="page-title">
                                Sub title
                            </div>
                            <div id="generated-Time">
                                Date & Time : Jul 2, 2020 2:42:48 PM
                            </div>
            </div>

                <div class="section header">General</div>
                <div id="general-section" class="section">
                <div  class="general-detail-label-container">
                    <label id="policy-name-label">Text here</label>
                </div>
                <div class="general-detail-content-container">
                        <span id="policy-name-content" >Text here</span>
                </div>
                <div  class="general-detail-label-container">
                    <label id="policy-description-label">Description A :</label>
                </div>
                <div class="general-detail-content-container">
                        <span id="policy-description-content""></span>Text here</span>
                </div>
                <div  class="general-detail-label-container">
                    <label id="policy-label-label" class="general-detail-label">Description b:</label>
                </div>
                <div class="general-detail-content-container">
                        <span id="policy-label-content" class="wrapping-text"></span>
                </div>
                <div  class="general-detail-label-container">
                    <label id="policy-group-label" class="general-detail-label">Group:</label>
                </div>
                <div class="general-detail-content-container">
                        <span id="policy-group-content" class="wrapping-text">Text here</span>
                </div>
                <div  class="general-detail-label-container">
                    <label id="policy-status-label" class="general-detail-label">Status:</label>
                </div>
                <div class="general-detail-content-container">
                        <span id="policy-status-content">
                            <label id="policy-status-message">Active</label>
                        </span>
                </div>
                <div  class="general-detail-label-container">
                    <label id="policy-version-label" class="general-detail-label">Version:</label>
                </div>
                <div class="general-detail-content-container">
                        <span id="policy-version-content" class="wrapping-text">7</span>
                </div>
                <div  class="general-detail-label-container">
                    <label id="policy-last-modified-label" class="general-detail-label">Last Modified:</label>
                </div>
                <div class="general-detail-content-container">
                        <span id="policy-last-modified-content" class="wrapping-text">Jun 15, 2020 2:41:48 PM</span>
                </div>
                </div>

                </body>
            </html>

【问题讨论】:

  • 您能否分享您的代码以及带有输入和预期输出的示例 - 一个最小的可重现示例,我们可以为您提供帮助。
  • 我已经包含了我从另一个线程中找到的我的 python 脚本示例和我的两个输入文件的示例
  • 我刚刚检查了 HTML,它不正确。请阅读此stackoverflow.com/help/minimal-reproducible-example,并分别为 file1 和 file2 提供输入。为了让您获得帮助,您应该准备一个示例,该示例对于任何将要承担该任务的人都可以轻松复制。您提供的内容不完整。
  • 我稍微修改了代码并删除了一些不相关的东西。本质上,这两个文件应该非常相似,只有 file1 是 file2 的早期版本,我试图确定 file1(早期版本)和 file2(更高版本)之间发生了什么变化。我的问题与此类似:stackoverflow.com/questions/34983301/…。尽管尝试了不同的浏览器,但我的问题并没有解决。我似乎无法查看与实际 Html 网页的比较文件,而是查看原始代码。

标签: python html difflib


【解决方案1】:

假设您只查找文本更改而不是 HTML 更改,您可以在比较之后去除 HTML 的输出。有多种方法可以实现这一目标。我首先想到的两个是:

  1. RegEx,因为这是 Python 原生的,并且
  2. BeautifulSoup,因为它是为阅读网页而创建的

使用上述任一方法创建一个函数,以去除 HTML 的输出

例如使用 BeautifulSoup

更新

再次阅读文档,在我看来,比较也会产生实际的 HTML,但是,您可以创建一个仅显示文本更改的附加输出。

另外为了避免显示整个文档,我将context 参数设置为True

使用 BeautifulSoup

import re
import difflib
from bs4 import BeautifulSoup

def remove_html_bs(raw_html):
    data = BeautifulSoup(raw_html, 'html.parser')
    data = data.findAll(text=True)
    
    def visible(element):
        if element.parent.name in ['style', 'script', '[document]', 'head', 'title']:
            return False
        elif re.match('<!--.*-->', str(element.encode('utf-8'))):
            return False
        return True
    
    result = list(filter(visible, data))

    return result

def compare_files(file1, file2):
    "Creates two comparison files"
    file1 = file1.readlines()
    file2 = file2.readlines()
    
    # Difference line by line - HTML
    difference_html = difflib.HtmlDiff(tabsize=8).make_file(file1, file2, context=True, numlines=5)
    # Difference line by line - raw
    difference_file = set(file1).difference(file2)
    
    # List of differences by line index
    difference_index = []
    for dt in difference_file:
        for index, t in enumerate(file1):
            if dt in t:
                difference_index.append(f'{index}, {remove_html_bs(dt)[0]}, {remove_html_bs(file2[index])[0]}')

    # Write entire line with changes
    with open('comparison.html', 'w') as outFile:
        outFile.write(difference_html)

    # Write only text changes, by index
    with open('comparison.txt', 'w') as outFile:
        outFile.write('LineNo, File1, File2\n')
        outFile.write('\n'.join(difference_index))

    return difference_html, difference_file


file1 = open('file1.html', 'r')
file2 = open('file2.html', 'r')

difference_html, difference_file = compare_files(file1, file2)

【讨论】:

  • @okijuh123,让我知道它是否适合你 :)
  • 似乎没有删除 CSS 标签,只打印文本。根据我在其他线程上的发现,我根本不应该面临这个问题,比较文件应该只是打印并突出显示两个文件之间的差异。
  • 能否同时包含 file1 和 file2,只包含有问题的部分
  • 现在整个文件都在打印原始的 html 代码和 Css 标签。
  • @okijuh123:我已经更新了答案来帮助你。但是,据我从文档中可以看出; HTML 应该显示在输出文件中。
猜你喜欢
  • 1970-01-01
  • 2022-10-08
  • 2013-03-29
  • 2016-05-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-09-24
  • 2019-06-27
相关资源
最近更新 更多