30

My problem:

#!/bin/bash

function testFunc(){
    echo "param #1 is :" $1
    echo "param #2 is :" $2
}

param1="param1"
param2="param2"

testFunc $param1 $param2

This way the output is:

param #1 is : param1
param #2 is : param2

But when I set param1 to empty string:

param1=""

Then the output is the following:

param #1 is : param2
param #2 is :

I guess the problem is that when the first parameter is empty, it's not declared, so it actually doesn't get passed as a function parameter.

If that is the problem, then is there a way to declare a variable "empty string" in bash, or is there any workaround to get the expected behavior?

Note: It works as expected if I call the function like this:

testFunct "" $param2

But I want to keep the code clean.

UPDATE:

I recently discovered the -u flag which raises an error in case an unbound variable is about to be used.

$ bash -u test.sh
param #1 is : param1
test.sh: line 5: $2: unbound variable
Benjamin W.
  • 46,058
  • 19
  • 106
  • 116
kupsef
  • 3,357
  • 1
  • 21
  • 31
  • 2
    Clean should not override correctness. – chepner Oct 15 '13 at 12:28
  • 3
    So you prefer to keep the correct mess, instead of searching for a clean and correct solution? – kupsef Oct 16 '13 at 08:08
  • 1
    If the code is incorrect, who cares if it is clean? Not quoting a parameter expansion because you think it looks cleaner is incorrect. – chepner Oct 16 '13 at 11:07
  • Read my question again:D My problem was that, I had to call my function without the parameter name to make it work. So I searched for a solution where I could keep the parameter name. A clean and correct solution. – kupsef Oct 16 '13 at 11:55
  • See also more broadly https://stackoverflow.com/questions/10067266/when-to-wrap-quotes-around-a-shell-variable – tripleee Oct 04 '18 at 04:10

3 Answers3

50

On the first case you call the script with testFunct param2. Hence, it understands param2 as the first parameter.

It is always recommendable to pass parameters within quotes to avoid this (and to be honest, for me it is cleaner this way). So you can call it

testFunct "$param1" "$param2"

So to pass an empty variable you say:

testFunct "" "$param2"

See an example:

Given this function:

function testFunc(){
    echo "param #1 is -> $1"
    echo "param #2 is -> $2"
}

Let's call it in different ways:

$ testFunc "" "hello"    # first parameter is empty
param #1 is -> 
param #2 is -> hello

$ testFunc "hey" "hello"
param #1 is -> hey
param #2 is -> hello
fedorqui
  • 275,237
  • 103
  • 548
  • 598
1

Another best practice is to check the number of parameters passed using $#.

However, this does not solve the problem of one empty parameter, how would you know if the param1 is empty or param2 is empty. Therefore both checks are good parctices.

Tom Ron
  • 5,906
  • 3
  • 22
  • 38
0

One can add set -o nounset in the body a bash file to achieve the same effect as bash -u does.

#!/bin/bash
set -o nounset

function testFunc(){
    echo "param #1 is :" $1
    echo "param #2 is :" $2
}

param1="param1"
param2="param2"

testFunc $param1 $param2
Pierre.Vriens
  • 2,117
  • 75
  • 29
  • 42