【问题标题】:How to use sed command to replace word in file如何使用 sed 命令替换文件中的单词
【发布时间】:2021-12-14 08:10:27
【问题描述】:

我有一个文本文件:

org.jitsi.videobridge.xmpp.user.shard-1.HOSTNAME=localhost
org.jitsi.videobridge.xmpp.user.shard-1.DOMAIN=auth.jc.name.com
org.jitsi.videobridge.xmpp.user.shard-1.USERNAME=name
org.jitsi.videobridge.xmpp.user.shard-1.PASSWORD=Hfr*7462
org.jitsi.videobridge.xmpp.user.shard-1.MUC_JIDS=JvbBredjoy@internal.auth.jc.name.com
org.jitsi.videobridge.xmpp.user.shard-1.MUC_NICKNAME=7896aee5-fgre-4b02-4569-0bcc75ed1d0d

我创建了一个 bash 脚本:

#!/bin/bash
DPATH="/etc/jitsi/videobridge/sip-communicator.properties"
k=$(grep -o 'shard-1' $DPATH) # shard ends by a number#
i=$(grep -o 'shard-1' $DPATH | cut -c7)
m=$((i+1))
n="shard-$m"
sed -i "s|${k}|${n}|g" $DPATH

但我得到错误:

/home/scripts# ./shard_number
./shard_number: line 5: 1
1
1
1
1
1: syntax error in expression (error token is "1
1
1
1
1")
sed: -e expression #1, char 9: unterminated `s' command

您能帮忙解决这个问题吗?谢谢。

【问题讨论】:

  • 你的预期输出是什么?
  • 我的预期输出是这样的... +1 org.jitsi.videobridge.xmpp.user.shard-2.HOSTNAME=localhost org.jitsi.videobridge.xmpp.user.shard-2.DOMAIN=auth.jc.name.com org.jitsi.videobridge.xmpp.user.shard-2.USERNAME=name org.jitsi.videobridge.xmpp.user.shard-.PASSWORD=Hfr*7462 org.jitsi.videobridge.xmpp.user.shard-2.MUC_JIDS=JvbBredjoy@internal.auth.jc.name.com org.jitsi.videobridge.xmpp.user.shard-2.MUC_NICKNAME=7896aee5-fgre-4b02-4569-0bcc75ed1d0d

标签: bash sed


【解决方案1】:

如果您使用bash -x /path/to/your/script 调用您的脚本或在脚本开头的某处添加set -x(在#!shebang 之后,但在您要调试的命令之前),您将看到您的grep 命令每行不返回一个“shard-1”,而是返回一个“shard-1”:

++ grep -o shard-1 /etc/jitsi/videobridge/sip-communicator.properties
+ k='shard-1
shard-1
shard-1
shard-1
shard-1
shard-1'

一旦cut,它会将错误输出中提到的1\n1\n1\n1\n1\n 字符串作为$(( ... )) 表达式的无效标记,这也会破坏sed 替换的语法:

++ cut -c7
++ grep -o shard-1 /etc/jitsi/videobridge/sip-communicator.properties
+ i='1
1
1
1
1
1'

将该字符串设为单个数字(例如,将您的 grep 传递到 sort -u 以统一所有找到的分片),您的脚本就可以正常工作了:

#!/bin/bash
DPATH="/etc/jitsi/videobridge/sip-communicator.properties"
k=$(grep -o 'shard-1' $DPATH | sort -u) # shard ends by a number#
i=$(grep -o 'shard-1' $DPATH | sort -u | cut -c7)
m=$((i+1))
n="shard-$m"
sed -i "s|${k}|${n}|g" $DPATH

您可以try it here。如果您想查看调试的初始脚本,还请查看this test

【讨论】:

  • @Oleg 我不是天才,我只是一个在他的生活中经历过很多 shell 脚本的人:你最终会学到一些技巧来减轻痛苦;)
  • 抱歉,还有一个问题 :) 如果我需要再增加一个 1 怎么办?从org.jitsi.videobridge.xmpp.user.shard-2.HOSTNAME=localhostorg.jitsi.videobridge.xmpp.user.shard-3.HOSTNAME=localhost 因为我们将拥有超过1 台服务器。我想我没有考虑过。 :)
  • 当前您正在文件中搜索“shard-1”,这不是很有用:您要么找到它并检索“shard-1”,要么您没有去找到它,你的脚本就会失败。也许您想搜索 shard-[0-9]+,它会找到 shard-2、shard-3 等,这使您可以使用脚本对先前执行的结果将 shard-2 转换为 shard-3、@ 987654341@ 转为shard-n+1 ?
  • 或者如果你想从初始的shard-1文件同时产生多个shard-n,你可能需要使用某种for循环。 bash 中简单的现代 for 循环语法是 c 风格的 for 循环,for ((i=0; i<9; i++)) { ... }
  • 啊,关于 shard-[0-9]+ :您需要将 -E 标志添加到 grep 以使其工作,或者如果您想使用 anticated Basic,请将其写为 shard-[0-9]\+正则表达式语法
猜你喜欢
  • 2013-09-25
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2022-01-10
  • 2017-06-06
  • 2014-12-28
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多