This is the mail archive of the cygwin mailing list for the Cygwin project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: Bash shell script issue


On 7 September 2016 at 21:27, Eric Blake <eblake@redhat.com> wrote:
>>> project_root=$PWD
>>
>> Still bad.
>
> No, that one's good.  Quotes are only REQUIRED when you want to ensure
> that there is no word splitting or globbing going on, and assignment
> context has neither of those.  However, although the quotes are optional
> in that context, using them out of habit makes it easier to remember to
> use quotes in the contexts where it does matter.

I was going to say that. Consider the following example:

# path1='/mnt/c/Program Files (x86)'
22:12:49 ~
# path2=$path1
22:12:54 ~
# path3=$path2/tools
22:13:00 ~
# echo $path1
/mnt/c/Program Files (x86)
22:13:05 ~
# echo $path2
/mnt/c/Program Files (x86)
22:13:06 ~
# echo $path3
/mnt/c/Program Files (x86)/tools

Assignment requires no extra quoting.
However if you try
# test -d $path2 && echo $path2 is a directory
bash: test: too many arguments

Because $path2 becomes split by space into words, while `test -d`
expects only one argument.
# test -d "$path2" && echo $path2 is a directory
/mnt/c/Program Files (x86) is a directory

This is really bash basics, and you should read Bash Beginner's Guide:
http://tldp.org/LDP/Bash-Beginners-Guide/html/

And just remember that UNIX tools such as bash, sed, awk etc. expect
scripts to use UNIX-style line endings (one LF character ends the
line), as opposed to a pair of CR and LF characters used in Windows.
Whenever you encounter problems or error messages that don't seem to
make any sense, check the file line endings. You can use the `file`
command to check the file's line endings. An example bash session:

22:22:49 ~
# cat >test.sh <<EOF
> #!/bin/sh
>
> echo line ending test script
> EOF
22:23:29 ~
# chmod 755 test.sh
22:23:14 ~
# u2d test.sh
unix2dos: converting file test.sh to DOS format...
22:23:24 ~
# file test.sh
test.sh: POSIX shell script, ASCII text executable, with CRLF line terminators
22:23:36 ~
# ./test.sh
./test.sh: line 2: $'\r': command not found
line ending test script
22:23:37 ~
# d2u test.sh
dos2unix: converting file test.sh to Unix format...
22:23:41 ~
# file test.sh
test.sh: POSIX shell script, ASCII text executable
22:23:43 ~
# ./test.sh
line ending test script

Here I've created a test shell script, and deliberately converted it
to DOS (Windows) line endings. The `file` command explicitly tells you
it has CRLF line terminators.
Next try to run the script and it will not work, because the
supposedly empty line is considered as a single `\r` (CR) character,
which is not a valid command.
After converting the file back to UNIX line endings, the `file`
command doesn't mention anything about line endings, because they are
the standard/default/normal UNIX-style ones (`\n` = LF). The script
runs.

Personally I use Notepad2-mod to edit shell scripts, the `File > Line
Endings` shows you the current line endings, allows to convert between
different line ending styles, and allows to set UNIX style as default.
Link if you're interested: http://xhmikosr.io/notepad2-mod/

> No, that one's okay.  In fact, if you are going for minimalism, you
> could use:
>
> x=$project_root/tools
>
> as the ${} form is only REQUIRED when you are using operators inside {}
> or when the next character after } is ambiguous with a continuation of
> the name of the variable in after the $.

Minimalism is good, but when writing anything more or less
complicated, consistent style and coding conventions become more
important. Quoting a variable in one context, but not the other, using
${var1}_${var2} here, but plain $var1$var2 etc. - it will work, but it
might not be best idea to code/script like this. Same as sometimes
it's better to put an extra set of otherwise unnecessary parenthesis
in a math expression, just to group terms and make the expression more
readable and operator precedence more obvious.
Bash has a lot of different syntax, and beginners would bump into less
problems if they overquote rather than underquote...
This is personal opinion based on my software development experience,
mostly working with high-level languages, involving complicated
architectural frameworks: sometimes you write more than strictly
necessary, to prevent problems in the future, make code more readable,
maintainable etc.

Regards,
--Gene

--
Problem reports:       http://cygwin.com/problems.html
FAQ:                   http://cygwin.com/faq/
Documentation:         http://cygwin.com/docs.html
Unsubscribe info:      http://cygwin.com/ml/#unsubscribe-simple


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]