提取部分代码并在bash中解析HTML
Extract part of the code and parse HTML in bash
我有外部 HTML 站点,我需要从该站点上的 table 提取数据。但是 HTML 网站的源代码除了 table 之外格式错误,所以我不能使用
xmllint --html --xpath <xpath> <file>
因为它不能正常工作,当 HTML 网站上的格式被破坏时。
我的想法是使用 curl 并删除 table 上方和下方的代码。当 table 被提取时,代码是干净的并且适合 xmllint 工具(然后我可以使用 xpath)。然而,删除匹配项上方的所有内容对 shell 来说具有挑战性,如您在此处所见:Sed doesn't backtrack: once it's processed a line, it's done.
有没有办法从 bash 中的 HTML 站点仅提取 table 的代码?假设,代码有这样的结构。
<html>
<head>
</head>
<body>
<p>Lorem ipsum ....</p>
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
<p>... dolor.</p>
</body>
</html>
我需要这样的输出来正确解析数据:
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
请不要因为尝试使用bash而给我减号。
我将分解我尝试使用 xmllint
的答案,它支持用于解析 html
文件的 --html
标志
首先,您可以通过如下解析来检查 HTML 文件的完整性,确认文件是否符合标准,或者如果发现错误则抛出错误:-
$ xmllint --html YourHTML.html
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
<html>
<head>
</head>
<body>
<p>Lorem ipsum ....</p>
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
<p>... dolor.</p>
</body>
</html>
我的原始 YourHTML.html
文件只是您问题中的输入 HTML 文件。
现在是值提取部分:-
开始从根节点解析文件到 table
节点 (//html/body/table
) 和 运行 xmllint
在 HTML 解析器和交互 shell 模式 (xmllint --html --shell
)
运行命令明明会产生一个结果,
$ echo "cat //html/body/table" | xmllint --html --shell YourHTML.html
/ > -------
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
/ >
现在使用 sed
删除特殊字符,即 sed '/^\/ >/d'
生成
$ echo "cat //html/body/table" | xmllint --html --shell YourHTML.html | sed '/^\/ >/d'
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
这是您预期的输出结构。在 xmllint: using libxml version 20900
上测试
我再往前一步,如果你想获取table
标签内的值,你可以应用sed
命令将它们提取为
$ echo "cat //html/body/table" | xmllint --html --shell YourHTML.html | sed '/^\/ >/d' | sed 's/<[^>]*.//g' | xargs
Company Contact
为了您的目的,一个快速的解决方案是 1-liner:
sed -n '/<table class="my-table">/,/<\/table>/p' <file>
说明:
打印两个指定标签之间的所有内容,在本例中为 <table>
您还可以轻松地为 <body>
或 <p>
创建一个标签变量,并即时更改输出。但是上面的解决方案在没有外部工具的情况下给出了你所要求的。
我有外部 HTML 站点,我需要从该站点上的 table 提取数据。但是 HTML 网站的源代码除了 table 之外格式错误,所以我不能使用
xmllint --html --xpath <xpath> <file>
因为它不能正常工作,当 HTML 网站上的格式被破坏时。
我的想法是使用 curl 并删除 table 上方和下方的代码。当 table 被提取时,代码是干净的并且适合 xmllint 工具(然后我可以使用 xpath)。然而,删除匹配项上方的所有内容对 shell 来说具有挑战性,如您在此处所见:Sed doesn't backtrack: once it's processed a line, it's done. 有没有办法从 bash 中的 HTML 站点仅提取 table 的代码?假设,代码有这样的结构。
<html>
<head>
</head>
<body>
<p>Lorem ipsum ....</p>
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
<p>... dolor.</p>
</body>
</html>
我需要这样的输出来正确解析数据:
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
请不要因为尝试使用bash而给我减号。
我将分解我尝试使用 xmllint
的答案,它支持用于解析 html
文件的 --html
标志
首先,您可以通过如下解析来检查 HTML 文件的完整性,确认文件是否符合标准,或者如果发现错误则抛出错误:-
$ xmllint --html YourHTML.html
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN" "http://www.w3.org/TR/REC-html40/loose.dtd">
<html>
<head>
</head>
<body>
<p>Lorem ipsum ....</p>
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
<p>... dolor.</p>
</body>
</html>
我的原始 YourHTML.html
文件只是您问题中的输入 HTML 文件。
现在是值提取部分:-
开始从根节点解析文件到 table
节点 (//html/body/table
) 和 运行 xmllint
在 HTML 解析器和交互 shell 模式 (xmllint --html --shell
)
运行命令明明会产生一个结果,
$ echo "cat //html/body/table" | xmllint --html --shell YourHTML.html
/ > -------
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
/ >
现在使用 sed
删除特殊字符,即 sed '/^\/ >/d'
生成
$ echo "cat //html/body/table" | xmllint --html --shell YourHTML.html | sed '/^\/ >/d'
<table class="my-table">
<tr>
<th>Company</th>
<th>Contact</th>
</tr>
</table>
这是您预期的输出结构。在 xmllint: using libxml version 20900
我再往前一步,如果你想获取table
标签内的值,你可以应用sed
命令将它们提取为
$ echo "cat //html/body/table" | xmllint --html --shell YourHTML.html | sed '/^\/ >/d' | sed 's/<[^>]*.//g' | xargs
Company Contact
为了您的目的,一个快速的解决方案是 1-liner:
sed -n '/<table class="my-table">/,/<\/table>/p' <file>
说明:
打印两个指定标签之间的所有内容,在本例中为 <table>
您还可以轻松地为 <body>
或 <p>
创建一个标签变量,并即时更改输出。但是上面的解决方案在没有外部工具的情况下给出了你所要求的。