Operating System - HP-UX
1752781 Members
6220 Online
108789 Solutions
New Discussion юеВ

how to parse using shell quoting

 
Jdamian
Respected Contributor

how to parse using shell quoting

Hi

Is there any way to take advantage of shell features as quoting and parameter substitution in my own scripts ?

For instance, supose you have to write down a script in order to parse a configuration file (text, not binary). The parameters assigned in it may contain blank chars, so quoting is in mind... You know that Korn shell and Posix shell can parse source lines in order to substitute values and alias before launching commands.

Is it possible to get advantage of these shell features or I have to write down my own parser ?

Thanx in advance
7 REPLIES 7
Ollie R
Respected Contributor

Re: how to parse using shell quoting

Do you have an example of what you're trying to achieve here?
To err is human but to not award points is unforgivable
James R. Ferguson
Acclaimed Contributor

Re: how to parse using shell quoting

Hi:

One way is to leverage the shell's 'read' command with the Inter-Field Separator (IFS). A common use would be reading a colon-delimited file lie '/etc/passwd':

#!/usr/bin/sh
echo "...using COLON as IFS..."
IFS=\:
while read A B C X
do
echo "A=${A} B=${B} C=${C} LEFT=${X}"
done < /etc/passwd
IFS=${OLDIFS}
exit 0

Regards!

...JRF...
James R. Ferguson
Acclaimed Contributor

Re: how to parse using shell quoting

HI (again):

Here's another crude example:

#!/usr/bin/sh
IFS=\,
while read A B C X
do
FIRST=`echo ${A}|sed -e 's/"//g' | cut -d" " -f1`
LAST=`echo ${A}|sed -e 's/"//g' | cut -d" " -f2`
SEX=`echo ${C}|sed -e 's/"//g'`
echo "FIRST=${FIRST} LAST=${LAST} SEX=${SEX}"
done < /tmp/parse.stuff
IFS=${OLDIFS}
exit 0

Run above using an 'infile' of comma-delimited, quoted fields like:

"James Ferguson","husband","male"
"Shirlee Ferguson","wife","female"
"Jessica Ferguson","daughter","female"
"Jamie Ferguson","daughter","female"

Regards!

...JRF...
James R. Ferguson
Acclaimed Contributor

Re: how to parse using shell quoting

Hi (again):

OK, after a bit of coffee, here's another shell feature that can be leveraged -- 'set' and array assignment. Consider this crude script:

#!/usr/bin/sh
IFS=\,
while read LINE
do
set -A ARY ${LINE}
FIRST=`echo ${ARY[0]}|sed -e 's/"//g' | cut -d" " -f1`
LAST=`echo ${ARY[1]}|sed -e 's/"//g' | cut -d" " -f2`
SEX=`echo ${ARY[2]}|sed -e 's/"//g'`
echo "FIRST=${FIRST} LAST=${LAST} SEX=${SEX}"
done < infile
IFS=${OLDIFS}
exit 0

Use the same input file ('infile') I used with my previous post, above, with the format:

"Firstname Lastname","Title","Sex"

...as the fields to dissect.

Regards!

...JRF...

Jdamian
Respected Contributor

Re: how to parse using shell quoting

Supose you have a configuration file as:

FULL_NAME="Brew, John Peter" # full name
INITIALS=B_JP # initials
MAIN_FILE="/direct/people/${INITIALS}.data"
EXT='#1234'

in this example you have characters as '#' used to insert comments as lines 2 and 3 (but see the last line where # is not inerting a comment).

You also have to parse blank chars as a part of an assignment (first line).

You also see one parameter INITIALS used to compound the value of other parameter (MAIN_FILE).

Steve Steel
Honored Contributor

Re: how to parse using shell quoting

Hi

Use your config file as input

#Give file name as parameter and ensure it can be executed.
file=$1
. $file
echo User $FULL_NAME with Initials $INITIALS on extension $EXT uses $MAIN_FILE

Then it is parsed

Steve Steel
If you want truly to understand something, try to change it. (Kurt Lewin)
Gregory Fruth
Esteemed Contributor

Re: how to parse using shell quoting

Steve's suggestion to use the "." operator is right on
the mark. However, note that the "." operator uses
PATH, so you may want to temporarily add the
current directory to the head of PATH or require that
the name of the config file is always specified exactly.
Otherwise, if the name of the config file clashes with
a program somewhere in PATH you'll get unexpected
results.

For example, suppose the config file is called "test".
Then if your script does:

cfg="test"
echo FOO
. $cfg
echo BAR

The output will only be FOO, because the "." searches
through the dirs in PATH and will likely find "/usr/bin/test"
before it finds "./test", and "/usr/bin/test" does an "exit"
which will terminate the program. To fix this, try something
like:

PATH=.:$PATH
cfg="test"
echo FOO
. $cfg
echo BAR

or:

cfg="./test"
echo FOO
. $cfg
echo BAR