branquito
branquito

Reputation: 4044

traverse array sent from bash, in external awk script

In my bash script I have:

patterns=( "somee? +pattern" "Another +here" )

awk -v l="$line" -f horsepower <(printf '%s\n' "${patterns[@]}") <<<"$stdout"

, so sending to awk script two files, first being process substitution output of printf on ${patterns[@]} array, and second being HERESTRING feed from $stdout variable.

, then in that external awk script, named here horsepower I have the following:

BEGIN {
    ...some initialization, not of importance for this question
}


# while reading first file, populate `patterns` array in awk
FNR==NR { patterns[$0]=""; next }

for (pat in patterns)
    # match lines from `$stdout` on patterns sent from bash, and save them in `a_rem`
    # array, for later output in END block.
    $0 ~ pat { a_rem[NR]=$0 }

# then follows END block
END {
    ...also non important
}

, but I am given notice about syntax error on for from above for (pat in patterns).

What am I doing wrong? Also, is awk getting correct first, second files from my bash script, using that method of <(), and <<<"$stdout"?

I have to mention, all of this was working when I was using literal regexes in awk script, but the moment I introduced that for (pat in patterns), and adding that <() in bash(<<<"$stdout" was ok!), I am getting this syntax error.

Upvotes: 0

Views: 159

Answers (1)

Jonathan Leffler
Jonathan Leffler

Reputation: 753970

There are at least two problems, one at shell level, one at the awk level.

Shell

A program like awk won't read standard input if you give it another file to read. The process substitution <(...) gives it one file to read. To get it to read standard input too, you need:

awk -f program <(...) - <<<"$stdout"

Awk

The pattern/action language applies at the source level. You're trying to apply it dynamically to the list of patterns you read. You'll need to modify the code that reads:

for (pat in patterns)
    # match lines  on patterns sent from bash, and save them in `a_rem`
    # array, for later output in END block.
    $0 ~ pat { a_rem[NR]=$0 }

so that it is more like:

{
    for (pat in patterns)
        if ($0 ~ pat) { a_rem[NR]=$0; break }
}

The added break is an optimization so that you don't add a single line multiple times to the same element of the array.

Upvotes: 3

Related Questions