在目录中递归搜索所有 xml 文件中的特定标签并 grep 标签的值

在目录中递归搜索所有 xml 文件中的特定标签并 grep 标签的值

Ubuntu 14.04 值得信赖的塔尔。

假设我有一个名为“testmag”的目录,它可能包含数百个 xml 文件,而目录又包含许多 xml 文件。我不知道任何 xml 文件的名称,但我知道其中之一包含 tag <dbname>....</dbname>

现在如何找到包含上述标签的文件并将标签的值作为终端中的输出

答案1

这是一个解决方案,find它还将输出包含匹配项的文件的文件名:

find . -name "*.xml" -exec grep '<dbname>' {} \;             \
                     -exec echo -e {}"\n" \;                 \
                     | sed 's/<dbname>\(.*\)<\/dbname>/\1/g'

解释

  1. find . -name "*.xml"从当前目录递归查找所有 xml 文件
  2. -exec grep '<dbname>' {} \;在每个文件上搜索模式<dbname>
  3. -exec echo -e {}"\n" \;echo 文件名 + 新行(-e选项使 echo 解释\n
  4. | sed 's/<dbname>\(.*\)<\/dbname>/\1/g'通过管道输出来sed仅打印标签之间包含的字段<dbname></dbname>

注意1:您可以格式化输出,echo -e ...以便清楚地列出每个文件的结果,例如通过添加新行或下划线行,无论什么都适合您的需要。

.注意2:每个文件的路径将相对于(例如)给出./subfolder1/file.xml。如果您想要绝对路径,请选择find $PWD -name ....

答案2

使用适当的 XML 解析器来解析 XML:

shopt -s globstar nullglob
for file in **/*.xml; do 
    dbname=$(xmlstarlet sel -t -v '//dbname' "$file")
    [[ -n "$dbname" ]] && printf "%s\t%s\n" "$file" "$dbname"
done

答案3

find与以下一起使用xq

find testmag -type f -name '*.xml' -exec xq -r '..|(.dbname? // empty)' {} +

*.xml这将找到目录中或目录下名称匹配的所有常规文件testmag。对于这些批次,将调用以提取在这些文档中找到的xq每个节点的值。dbname

xq是一个类似 XML 解析器,随fromjq一起分发yqhttps://kislyuk.github.io/yq/


您是否需要具有此节点的所有 XML 文件的文件名,您可以使用

find testmag -type f -name '*.xml' -exec xq -e '..|(.dbname? // empty)' {} \; -print

...虽然这比仅仅提取节点的值要慢一些,因为我们需要xq为每个文件调用一次。

答案4

假设我们有XMLS包含这些文件的目录:

cat XMLS/file1
foo bar <dbname>target</dbname> baz
foo foo

cat XMLS/file2
<name>notarget</name>

我会使用这个命令:

grep -r '<dbname>' XMLS/ | sed 's/.*<dbname>\(.*\)<\/dbname>.*/\1/'
target

正如您所看到的,它返回标签内的值<dbname>。而不是标签内的值<name>


递归搜索-r的标志 。grep

sed删除字符串中除 value 之外的所有内容target

相关内容