Kalin Borisov
Kalin Borisov

Reputation: 1120

Output only specific var from text

Output only specific var from text. In that case:

echo "ote -C -pname ap01 -HLS 134 -db 1 -instance 43 -log ap01"

Want to get only this value from "-pname"

Exptected result:

ap01

Upvotes: 0

Views: 103

Answers (7)

Vytenis Bivainis
Vytenis Bivainis

Reputation: 2376

This looks simple

xargs -n1 | sed -n "/-pname/,//p" | tail -n1

Upvotes: 1

terdon
terdon

Reputation: 3380

You can simply use (GNU) grep:

$ echo "ote -C -pname ap01 -HLS 134 -pname foo -db 1 -instance 43 -log ap01" |
     grep -Po -- '-pname \K[^ ]+'
ap01

Explanation

The -P enables Perl Compatible Regular Expressions (PCREs) which gives us \K (meaning "discard anything matched up to this point). The -o means "print only the matched portion of the line. So, we then look for the string -pname followed by a space and then as many consecutive non-space characters as possible ([^ ]+). Because of the \K, everything before that is discarded and because of the -o, only the matched portion is printed.

This will work for an arbitrary number of -pname flags as long as none of their values contain spaces.

Upvotes: 1

fedorqui
fedorqui

Reputation: 290135

grep with look behind?

$ grep -Po '(?<=-pname )[^ ]*' <<< "ote -C -pname ap01 -HLS 134 -db 1 -instance 43 -log ap01"
ap01

As there might be many -pname in the string (see comments below), you can then "play" with head and tail to get the value you want.

Explanation

  • This uses -P for Perl Regex and -o for "print only the matched parts of a machine line".
  • (?<=-pname ) is a look-behind: match strings that are preceeded by -pname (note the space).
  • [^ ]* match any set of characters until a space is found.

Upvotes: 3

mpapec
mpapec

Reputation: 50667

echo "ote -C -pname ap01 -HLS 134 -db 1 -instance 43 -log ap01" | \
  perl -pe '($_)= /-pname\s+([^-]\S*)/'

Upvotes: 3

Axeman
Axeman

Reputation: 29854

This will deal with a doubled -pname.

echo "ote -C -pname ap01 -HLS 134 -db 1 -instance 43 -log ap01" |\
    perl -ne 'print ( /\s+-pname\s+([^-]\S*)/ )'

As ikegami notes below, if you should happen to want to use dashes as the first character of this value, the only way I know that you can be sure you're getting a value and not another switch is more complicated. One way is to do a negative lookahead for all known switches:

echo "ote -C -pname -pname -ap01- -HLS 134 -db 1 -instance 43 -log ap01" |\
    perl -ne 'print ( /\s+-pname\s+(?!-(?:pname|other|known|switches))(\S+)/ )'

Upvotes: 4

ikegami
ikegami

Reputation: 386416

-log takes a string. That string could be -pname. The existing solutions so far fail to handle that and treat the value of the -log parameter as the start of another argument.

You'll have to recreate the argument parsing ote performs if you want a robust solution. The following is well on your way to do that.

echo ... | perl -MGetopt::Long -nle'
   local @ARGV = split;
   GetOptions(\%args, "C", "pname=s", "HLS=i", "db=i", "instant=i", "log=s")
      && defined($args{pname})
         && print($args{pname});
'

Upvotes: 5

Barmar
Barmar

Reputation: 781974

echo "ote -C -pname ap01 -HLS 134 -db 1 -instance 43 -log ap01" | \
    awk '{for (i = 1; i <= NF; i++) {if ($i == "-pname") { print $(i+1); break; } } }'

Upvotes: 4

Related Questions