更清洁的方式来编写多个sed命令?

时间:2014-04-29 16:11:19

标签: linux bash shell ubuntu sed

是否有更多的DRY方式来编写以下命令(将它们放在bash shell脚本中):

sudo sed -i 's/^#PermitRootLogin yes/PermitRootLogin no/' /etc/ssh/sshd_config
sudo sed -i 's/PermitRootLogin yes/PermitRootLogin no/' /etc/ssh/sshd_config

sudo sed -i 's/^#PermitEmptyPasswords yes/PermitEmptyPasswords no/' /etc/ssh/sshd_config
sudo sed -i 's/PermitEmptyPasswords yes/PermitEmptyPasswords no/' /etc/ssh/sshd_config

sudo sed -i 's/^#PasswordAuthentication yes/PasswordAuthentication no/' /etc/ssh/sshd_config
sudo sed -i 's/PasswordAuthentication yes/PasswordAuthentication no/' /etc/ssh/sshd_config

sudo sed -i 's/^#X11Forwarding yes/X11Forwarding no/' /etc/ssh/sshd_config
sudo sed -i 's/X11Forwarding yes/X11Forwarding no/' /etc/ssh/sshd_config

8 个答案:

答案 0 :(得分:12)

由于要匹配的模式相似,您可以使用4个字符串的替换并捕获它。使字符串开头的#可选。

以下内容将这些合并为一个:

sed -i -r 's/^#?(PermitRootLogin|PermitEmptyPasswords|PasswordAuthentication|X11Forwarding) yes/\1 no/' /etc/ssh/sshd_config

如果您的sed版本不支持扩展正则表达式,您可以说:

sed -i 's/^#\{0,1\}\(PermitRootLogin\|PermitEmptyPasswords\|PasswordAuthentication\|X11Forwarding\) yes/\1 no/' /etc/ssh/sshd_config

答案 1 :(得分:10)

-e 'sed-command'的单个调用中使用多个sed参数:

sudo sed -i.bak \
         -e 's/^#PermitRootLogin yes/PermitRootLogin no/' \
         -e 's/PermitRootLogin yes/PermitRootLogin no/' \
         -e 's/^#PermitEmptyPasswords yes/PermitEmptyPasswords no/' \
         -e 's/PermitEmptyPasswords yes/PermitEmptyPasswords no/' \
         -e 's/^#PasswordAuthentication yes/PasswordAuthentication no/' \
         -e 's/PasswordAuthentication yes/PasswordAuthentication no/' \
         -e 's/^#X11Forwarding yes/X11Forwarding no/' \
         -e 's/X11Forwarding yes/X11Forwarding no/' \
         /etc/ssh/sshd_config

或者创建一个脚本文件sed.script,其中包含以下命令:

s/^#PermitRootLogin yes/PermitRootLogin no/
s/PermitRootLogin yes/PermitRootLogin no/
s/^#PermitEmptyPasswords yes/PermitEmptyPasswords no/
s/PermitEmptyPasswords yes/PermitEmptyPasswords no/
s/^#PasswordAuthentication yes/PasswordAuthentication no/
s/PasswordAuthentication yes/PasswordAuthentication no/
s/^#X11Forwarding yes/X11Forwarding no/
s/X11Forwarding yes/X11Forwarding no/

然后使用该文件运行sed

sudo sed -i.bak -f sed.script /etc/ssh/sshconfig

我在-i选项中添加了备用扩展程序。如果您编辑主要配置文件而不首先制作备份副本,那么您就比我更勇敢! (如果你在Mac OS X或BSD上工作也是必要的; sed需要-i的扩展名。)

答案 2 :(得分:3)

您可以使用-e

sudo sed -i -e 'first_command' -e 'second command' ... -e 'last command' /etc/ssh/sshd_config

答案 3 :(得分:3)

就像我说过你也可以使用for循环。

#!/bin/bash

FILE='/etc/ssh/sshd_config'
REPLACE_STRINGS=('s/^#PermitRootLogin yes/PermitRootLogin no/' 's/PermitRootLogin yes/PermitRootLogin no/' 's/^#PermitEmptyPasswords yes/PermitEmptyPasswords no/' 's/PermitEmptyPasswords yes/PermitEmptyPasswords no/' 's/^#PasswordAuthentication yes/PasswordAuthentication no/' 's/PasswordAuthentication yes/PasswordAuthentication no/' 's/^#X11Forwarding yes/X11Forwarding no/' 's/X11Forwarding yes/X11Forwarding no/')


for i in "${REPLACE_STRINGS[@]}"
{
    sudo sed -i "$i" $FILE
}

答案 4 :(得分:1)

您可以将sed命令放在外部文件中:

sudo sed -i -f commands.sed /etc/ssh/sshd_config

commands.sed:
s/#*PermitRootLogin yes/PermitRootLogin no/
s/#*PermitEmptyPasswords yes/PermitEmptyPasswords no/
s/#*PasswordAuthentication yes/PasswordAuthentication no/
s/#*X11Forwarding yes/X11Forwarding no/

您还可以在bash脚本中嵌入多行sed脚本:

#!/bin/bash

sudo sed -i '
    s/#*PermitRootLogin yes/PermitRootLogin no/
    s/#*PermitEmptyPasswords yes/PermitEmptyPasswords no/
    s/#*PasswordAuthentication yes/PasswordAuthentication no/
    s/#*X11Forwarding yes/X11Forwarding no/
' /etc/ssh/sshd_config

答案 5 :(得分:0)

在标准的unix上(其次是posix而不是GNU)

sed -e 's/^#PermitRootLogin yes/PermitRootLogin no/;s/PermitRootLogin yes/PermitRootLogin no/;s/^#PermitEmptyPasswords yes/PermitEmptyPasswords no/;s/PermitEmptyPasswords yes/PermitEmptyPasswords no/;s/^#PasswordAuthentication yes/PasswordAuthentication no/;s/PasswordAuthentication yes/PasswordAuthentication no/;s/^#X11Forwarding yes/X11Forwarding no/;s/X11Forwarding yes/X11Forwarding no/' /etc/ssh/sshd_config > /tmp/sshd_config
cat /tmp/sshd_config > /etc/ssh/sshd_config 
rm /etc/ssh/sshd_config 

正常情况下它可以,但有时会定义以#than字开头,有时没有指定地点,因此PermitRootLogin替代品也会更改SpecialPermitRootLogin

答案 6 :(得分:0)

懒惰,但我会这样做:

sed -Ei 's/.*PermitRootLogin yes|#PermitRootLogin no/PermitRootLogin no/g' /etc/ssh/sshd_config
sed -Ei 's/.*PermitEmptyPasswords yes|#PermitEmptyPasswords no/PermitEmptyPasswords no/g' /etc/ssh/sshd_config
sed -Ei 's/.*PasswordAuthentication yes|#PasswordAuthentication no/PasswordAuthentication no/g' /etc/ssh/sshd_config
sed -Ei 's/.*X11Forwarding yes|#X11Forwarding no/X11Forwarding no/g' /etc/ssh/sshd_config

〜SimonTek

答案 7 :(得分:0)

只是一个小评论。

建议使用漂亮的解决方案here (from ask Ubuntu)

我们可以将其修改为

,而不是在一行中两次编写相同的字符
sed -i '/^#PermitRootLogin/s/yes/no/' /etc/ssh/sshd_config

这种方法可以减少基于拼写错误的错误。