0

Problem with exit when using function command

I have find this subject about the exit and I will reuse his example to show the problem i enconter : Difference between return and exit in Bash functions

There is a case where the exit does'nt work correctly: the Function Command. Can someone explain that?

#!/bin/sh

retfunc()
{
    echo "this is retfunc()"
    return 1
}

exitfunc()
{
    echo "this is exitfunc()"
    exit 1
}

retfunc
RETFUNC_RETURN_CODE=$?
echo "We are still here"
echo "return code : $RETFUNC_RETURN_CODE"
TEXT=$(exitfunc)
echo $TEXT
echo "We will see this however the exit !!!!! => you need to use global variable to return Strings"
exitfunc
echo "We will never see this"

In my real case I use a function to call an sqlplus command and i would like to exit if there is an error but i would like to return the result string from the function (I can't do it by using return statement because it's a string not a numéric)

My solution is to use a global variable but it multiplies the number of line. Does someone have an other solution for me?

#!/bin/sh

#****************ORACLE CALL FUNCTION****************
function run_oracle {
## need two arguments connextion string as first argument and sql_stmt as second
local CONNEXION=$1
local STMT=$2
##
RETSTRING=$(sqlplus -s ${CONNEXION} as sysdba <<EOF!
set serveroutput off heading off feedback off verify off define off linesize 2000
${STMT};
exit
EOF!
)
check_ora_error "$RETSTRING" $CONNEXION
}
#***********ORACLE CALL FUNCTION ENDS****************

#************Check ORA ERROR FUNCTION****************
function check_ora_error {
if [[ $1 = *"ORA-12514"* ]];then
    echo 
    echo "Sqlplus make an ORA- ERROR"
    echo "$1"
    echo
    echo "Connexion string $2 is wrong"
    echo
    echo "EXIT"
    exit 1
fi
}
#************Check ORA ERROR FUNCTION ENDS***********

SQL_STMT="select USERNAME,default_tablespace,account_status from DBA_USERS where username='${USER_TO_COMPARE}'"

run_oracle ${CONNEXION_STRING_ORIG} "${SQL_STMT}"
USER_ORIG=${RETSTRING}

I would like to reduce the code :

In function :

...
$(sqlplus -s ${CONNEXION} as sysdba <<EOF!
set serveroutput off heading off feedback off verify off define off linesize 2000
${STMT};
exit
EOF!
)
...

in Main :

USER_ORIG=$(run_oracle ${CONNEXION_STRING_ORIG} "${SQL_STMT}")
Michael
  • 1
  • 1

1 Answers1

0

Command substitution executes in a subshell: when you exit within a command substitution, you exit the subshell only.

I don't understand why you want to capture the output of the exitfunc function. You don't have to capture the output of a function and echo it: text echo'ed inside a function will show up on stdout if you don't capture it.

If that's something you need to do, your function can return a "special" status that the main shell can act on:

exitfunc() {
    echo "some text"
    return 234
}

text=$(exitfunc)
status=$?
(( status == 234 )) && exit
glenn jackman
  • 238,783
  • 38
  • 220
  • 352
  • The problem is that my return is a string and then I can't use a return statement. Thank you for the explanation on command substitution. – Michael Sep 12 '19 at 08:55
  • Then it sounds like that function is doing too much. Restructure so that you have a function that generates that string and another that does the cleanup and exits. – glenn jackman Sep 12 '19 at 12:57