在大文件中搜索并添加模式

时间:2012-01-19 12:58:58

标签: linux perl shell unix awk

我有一个很大的apache配置文件,在每个虚拟主机部分中,我想添加自己的日志条目。我想知道我是否可以用脚本来做。

我当前的配置文件是这样的;

ServerName abc.com   
some information.   
…   
……   

我希望有类似的东西;

ServerName abc.com    
CustomLog "/usr/local/logs/abc.com.log"    
some information.    
…   
……       

是否有可能通过某种脚本?我有很多这样的虚拟主机条目,所以手动更新是不可能的..任何想法?

5 个答案:

答案 0 :(得分:5)

Sed会快速完成这项工作:

sed 's=^ServerName \(.*\)=&\nCustomLog "/usr/local/logs/\1.log"='

编辑:我之前发布了其他内容,然后去测试它,我犯了一个错误。所以我测试了choroba的答案,发现它也没有用,所以修复它并简化它。

答案 1 :(得分:1)

试试这个sed脚本:

sed -i~ '/^ServerName /s=^serverName \(.*\)=&\nCustomLog "/usr/local/logs/\1.log"=' config_file*

(未测试的)

答案 2 :(得分:1)

awk可以更简单地使用。

awk 'NR==3{print "my log"}1' INPUT_FILE
  • NR是一个跟踪行号的内置变量。
  • 您还可以使用-vvariable name动态传递值,而不是在脚本中对其进行硬编码。例如。 awk -v line="$var" 'NR==line{print "my log"}1' INPUT_FILE。在这种情况下,line是一个awk变量,$var可以是在awk's范围之外定义的bash变量。

测试:

[jaypal:~/Temp] cat file
ServerName abc.com   
some information.   
…   
……  

[jaypal:~/Temp] awk 'NR==3{print "my log"}1' file # add log after 2 lines
ServerName abc.com   
some information.   
my log
…   
……  

[jaypal:~/Temp] awk 'NR==4{print "my log"}1' file # add log after 3 lines
ServerName abc.com   
some information.   
…   
my log
……  

[jaypal:~/Temp] var=2 # define a variable which holds the line number you want to print on
[jaypal:~/Temp] awk -v line="$var" 'NR==line{print "my log"}1' file
ServerName abc.com   
my log
some information.   
…   
……  

在评论中,我看到了从匹配模式(ServerName,在此示例中)开始的3行之后添加日志的问题。为此你可以试试这样的东西 -

awk '/ServerName/{a=NR;print;next} NR==(a+3){print$0;print "my log";next}1' file

[jaypal:~/Temp] awk '/ServerName/{a=NR;print;next} NR==(a+3){print$0;print "my log";next}1' file
ServerName abc.com   
some information.   
…   
……  
my log

答案 3 :(得分:0)

实际上当我在Mac上尝试这些答案时,没有一个答案对我有用:

  • sed在打开和关闭用于分组的括号
  • 之前需要\
  • \n置于替换模式中只需插入n
  • Bakkreference \1不适用于a操作

这是一个有效的命令:

sed -i.bak 's~^ServerName \(.*\)$~&\
CustomLog "/usr/local/logs/\1.log"~g' *.conf

答案 4 :(得分:0)

这会在正确的ServerName之后的3之后添加所需的行。

perl -i~ -ne'
   print;
   $target = $.+3 if /^\QServerName abc.com\E\s*$/;
   print qq{CustomLog "/usr/local/logs/abc.com.log"\n}
      if $target && $. == $target;
' apache.conf