我有一个文件uca.xml(自定义操作的 Thunar 配置):
<?xml encoding="UTF-8" version="1.0"?>
<actions>
<action>
<!--some code-->
</action>
</actions>
<--blank line here-->
请注意该文件以空行结尾
我想要一个 bash 命令/脚本来插入文件自定义操作.txt包含:
<action>
<!--custom configuration-->
</action>
所以它最终会看起来像:
<?xml encoding="UTF-8" version="1.0"?>
<actions>
<action>
<!--some code-->
</action>
<action>
<!--custom configuration-->
</action>
</actions>
我尝试了给出的方法杰夫加涅:
sed -n -i -e '/<\/actions>/r customAction.txt' -e 1x -e '2,${x;p}' -e '${x;p}' uca.xml
但仅当标签下方至少插入一个字符(不是空行)时才有效。
我的临时解决方法是一个脚本:
echo "someDummyText" >> uca.xml
sed -n -i -e '/<\/actions>/r customaction.txt' -e 1x -e '2,${x;p}' -e '${x;p}' uca.xml
sed -i 's/someDummyText//' uca.xml
sed -i '${/^$/d;}' uca.xml
但我相信 sed 有一种更优雅的单行解决方案。提前致谢。
笔记:这是我在 U&L 和 StackExchange 社区发表的帖子,所以请宽容我,如果我做错了什么,请毫不犹豫地详细纠正我。我阅读了 SE FAQ 并尝试在其他地方寻找答案,但运气不佳。
答案1
我认为你的解决方案是完全足够的。您可以通过仅用一个替换最后 2 个 sed 来对其进行优化:
sed -i '$d' uca.xml
毕竟,您只需将额外的行放在那里,这样您就知道要删除什么。
如果您正在寻找替代解决方案,可以使用 sed 获取模式匹配的行号,然后使用 -1 进行读取:
if lno=$(sed -n -e '/<\/actions>/=' uca.xml)
then let lno=lno-1
sed -i -e "$lno"'r customaction.txt' uca.xml
fi
或者如果你喜欢古老但有用的ed
命令,你可以这样做
ed -s uca.xml <<\!
?</actions>
-1r customaction.txt
w
q
!
答案2
使用sed
read( r
)命令:
$ sed '\#</action>#r customAction.txt' uca.txt
<?xml encoding="UTF-8" version="1.0"?>
<actions>
<action>
<!--some code-->
</action>
<action>
<!--custom configuration-->
</action>
</actions>
输入文件末尾有一个空行,它会保留在输出中。该r
命令将在找到给定模式后插入给定文件的内容。这在示例数据上按预期工作,因为字符串仅出现一次</action>
。如果输入文件中有更多预先存在的操作,则这将无法按预期工作。
以下内容适用于包含多个操作的文件:
gsed -e '\#</actions>#d' -e '$ r customAction.txt' -e '$ a\</actions>' uca.txt
它在找到时删除标签并在末尾</actions>
插入 的内容。customAction.txt
然后它附加</actions>
在那之后。
这种编写命令的方式a
需要 GNU sed
(因此gsed
)。