2013-11-13 2 views
2

Проблема с параметрами -oX в pcregrep. Указание нескольких таких параметров с разными номерами выводит только последнюю указанную группу.pcregrep с несколькими группами захвата

Данные:

docker ps | awk '{print $1}' | tail -n +2 | xargs docker inspect

выходы:

[{ 
"ID": "4e7f430263c33c25970134760ea96f9b57452680a8cfdf062270f5f7fe385135", 
.... #lots of additional lines 
"Ports": { 
     "5000/tcp": [ 
      { 
       "HostIp": "127.0.0.1", 
       "HostPort": "5000" 
      } 
     ], 
     "5984/tcp": [ 
      { 
       "HostIp": "127.0.0.1", 
       "HostPort": "5984" 
      } 
     ] 
    } 
},{ 
#same as above, but with a different ID and HostPort 5000 
}] 

Идея

docker ps | awk '{print $1}' | tail -n +2 | xargs docker inspect | pcregrep -M -o1 'ID":\s"(\w*)(?:\n|.)*?HostPort":\s"(\w)'

выходы

4e7f430263c33c25970134760ea96f9b57452680a8cfdf062270f5f7fe385135 
db35ce4b1fc7580ff43bacda5e961c4741c9447e97dbbdbf38218d068b0132af 

и

docker ps | awk '{print $1}' | tail -n +2 | xargs docker inspect | pcregrep -M -o2 'ID":\s"(\w*)(?:\n|.)*?HostPort":\s"(\w*)'

выходы

8000 
5000 

До сих пор так хорошо. Теперь я хотел бы, чтобы эти выходы были объединены на Sameline. pcregrep -M -o однако выводит все, что находится между ними (кажется, игнорирует, что средняя группа не захватывает), а pcregrep -M -o1 -o2 выводит только вторую группу - второй вариант, по-видимому, перезаписывает первый. Это на Ubuntu 12.04 LTS.

Любая идея, как получить выход

4e7f430263c33c25970134760ea96f9b57452680a8cfdf062270f5f7fe385135 8000 
db35ce4b1fc7580ff43bacda5e961c4741c9447e97dbbdbf38218d068b0132af 5000 

и по-прежнему держать его 'unixy' (предпочтительно не Perl/Python/рубин скрипты)?

Фон: Я хочу автоматически останавливать контейнеры в докерах, которые занимают определенные порты.

ответ

1

Способность указывать -o несколько раз до pcregrep, по-видимому, является очень недавней разработкой (version 8.32, выпущенной 30 ноября 2012 года). Я предполагаю, что у вашего дистрибутива еще нет этого. :-) Итак, используя вместо этого awk. Также, заменив постороннее использование tail в оригинале с эквивалентной функциональностью в первом скрипте awk.

docker ps | awk '(NR >= 2) { print $1 }' | xargs docker inspect | awk '($1~/"ID":/){gsub("\"|,","",$2);id=$2}; (id && $1~/"HostPort":/) {gsub("\"","",$2);print id " " $2;id=""}' 
Смежные вопросы