Superando novas linhas com grep -o

1

Sou um pouco novo na regex e preciso de uma pequena ajuda. Eu tenho um arquivo semelhante a esse.

SampleOutput

{

   "1": {

      "state": "RUNNING",

      "stats": {

         "name": "some-file",

         "uris": [

            "some-example.com"

         ],

         "host": "127.0.0.1",

         "port": 8080,

         "uptime": 168,

         "mem_quota": 2147483648,

         "disk_quota": 2147483648,

         "fds_quota": 16384,

         "usage": {

            "time": "2016-09-13 07:39:40 +0000",

            "cpu": 0.30315522606369516,

            "mem": 1069568000,

            "disk": 237203456

         }

      }

   },

   "0": {

      "state": "RUNNING",

      "stats": {

         "name": "some-file2",

         "uris": [

            "some-example-e.com"

         ],

         "host": "127.0.0.2",

         "port": 8081,

         "uptime": 169,

         "mem_quota": 2147483648,

         "disk_quota": 2147483648,

         "fds_quota": 16384,

         "usage": {

            "time": "2016-09-13 07:39:40 +0000",

            "cpu": 0.3086296386531593,

            "mem": 1073180672,

            "disk": 237203456

         }

      }

   },

   "2": {

      "state": "RUNNING",

      "stats": {

         "name": "some-file3",

         "uris": [

            "some-example.com"

         ],

         "host": "127.1.20.3",

         "port": 8190,

         "uptime": 168,

         "mem_quota": 2147483648,

         "disk_quota": 2147483648,

         "fds_quota": 16384,

         "usage": {

            "time": "2016-09-13 07:39:40 +0000",

            "cpu": 0.31213565359044587,

            "mem": 1072861184,

            "disk": 237203456

         }

      }

   }

}

E eu preciso extrair os valores da cpu, mem e disco e colocá-los em um arquivo no formato como

0.30315522606369516,1069568000,237203456,0.3086296386531593,1073180672

Basicamente, deve ser

first_instance_cpu,first_instance_mem,first_instance_disk,second_instance_cpu,second_instance_mem...

Espero que você entenda.

Estou usando a seguinte instrução grep para recuperar esses valores.

grep -Eow '"(cpu|mem|disk)": [0-9.]+' SampleOutput | grep '[0-9.]'

E isso me dá saída como segue

"cpu": 0.30315522606369516
"mem": 1069568000
"disk": 237203456
"cpu": 0.3086296386531593
"mem": 1073180672
"disk": 237203456
"cpu": 0.31213565359044587
"mem": 1072861184
"disk": 237203456

Com os números que quero destacados em vermelho (correspondência). Agora, eu quero apenas os números, mas quando eu uso a opção -o com o meu segundo comando grep, eu recebo os números, com certeza, mas cada um em uma linha diferente, como assim

0
.
3
3
1

.. e assim por diante.

Como obtenho os resultados como pelo menos números inteiros em linhas diferentes? Então eu poderia usar tr ou algo para vírgula separá-los. Por favor sugira. Qualquer outra alternativa ao meu comando grep é bem vinda!

Além disso, se você pudesse recomendar boas leituras quando se trata de aprender regex avançado, seria ótimo também: D

Obrigado antecipadamente!

    
por Izy- 13.09.2016 / 11:51

2 respostas

3
$ grep -Po '"(cpu|mem|disk)": \K[\d.]+' SampleOutput | paste -sd , -
0.30315522606369516,1069568000,237203456,0.3086296386531593,1073180672,237203456,0.31213565359044587,1072861184,237203456

grep implementações que suportam -o geralmente também suportam -P para PCRE, onde \K (no PCRE Versão 7.2 19-Jun-07 ou acima) pode ser usado para redefinir o início do texto correspondente (assim grep -o apenas mostra o que é correspondido à direita dele).

Você não estava longe de sua abordagem, você só precisava substituir grep -o '[0-9.]' por grep -oE '[0-9.]+' , ou seja, encontrar seqüências de um ou mais dígitos ou ponto em vez de apenas um dígito ou ponto.

    
por 13.09.2016 / 13:46
6

Como seu arquivo está no formato JSON, use jq :

jq '
    flatten |
    map(.stats.usage | del(.time)) |
    map([.cpu, .mem, .disk]) |
    flatten |
    .[]' <file.json | \
paste -sd ,

Saída:

0.30315522606369516,1069568000,237203456,0.3086296386531593,1073180672,237203456,0.31213565359044587,1072861184,237203456
    
por 13.09.2016 / 13:09