1

I need to check 2 assetions:

  1. The file content format
  2. Iterate over that content:

So, the content file must be:

key1=value
key2=value2
...

So, each line must have the format key=value. Spaces are not allowed before or after the =. This file content has to be an env format file.

By other hand, I need to split out each line into a key and a value inside a loop.

Any ideas?

  • 1
    What are the restrictions on the key and value? Single words? Are quoted strings ok? Are multi-line value ok? Are values containing = ok? – Kusalananda Jun 26 '18 at 14:26
  • Only has to match <word>=<word> – Jordi Jun 26 '18 at 14:42
  • Right, but can a "word" be preference=apple-juice for a valid line reading drink=preference=apple-juice? Are spaces allowed before and/or after the =? – DopeGhoti Jun 26 '18 at 15:26
  • No. This file content has to be an env format file. – Jordi Jun 26 '18 at 15:27
  • Do you mean that key1=value with spaces should be rejected, or that it should be parsed as key=key1 and value=value with spaces? – Gilles Jun 27 '18 at 15:28
3

With bash:

n=0
while IFS="=" read -r key value; do
    ((n++))
    if [[ -z $key ]]; then echo "missing key on line $n"; continue; fi
    if [[ -z $value ]]; then echo "empty value on line $n"; continue; fi
    echo "key:>$key<; value:>$value<"
done <<END
key1=value1
key2=value2
key3=
=value3
foo

key4=value4=value5=value6
END

outputs

key:>key1<; value:>value1<
key:>key2<; value:>value2<
empty value on line 3
missing key on line 4
empty value on line 5
missing key on line 6
key:>key4<; value:>value4=value5=value6<
2

Given this file as input:

key1=value1
key2=value2
key3=
=value3
key4=value4

We can use = as a field separator for awk:

$ awk -F= '!($1 && $2 && NF==2) { print "File failed validation on line " NR; exit 1} { print $1, $2 }' input
key1 value1
key2 value2
File failed validation on line 3

To throw validation error messages to standard error, the print statement can be modified, and to continue processing after an error is seen, change the exit statement to a next statement:

$ awk -F= '!($1 && $2 && NF==2) { print "File failed validation on line " NR | "cat 1>&2"; next } { print $1, $2 }' input
[stdout] key1 value1
[stdout] key2 value2
[stdout] key4 value4
[stderr] File failed validation on line 3
[stderr] File failed validation on line 4

Validation is done in three steps; if any of these criteria are not met the error is thrown and, in the first example, execution is aborted with an error-state exit code:

  • $1 - Ensure that there is (in the parlance of the input specification) a "key"
  • $2 - Ensure that there is (in the parlance of the input specification) a "value"
  • NF==2 - Ensure that there are only two fields; the aforementioned "key" and "value"

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.