kward / shunit2

shUnit2 is a xUnit based unit test framework for Bourne based shell scripts.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

oneTimeTearDown()/tearDown() is being called an additional time at the end of execution

vtereso opened this issue · comments

I have been pulling master and had functions that were executing within these hooks and saw what seems to be some unintended behavior. Example file as show below:

testSomething() {
    assertTrue "true" "true"
}

setUp() {
  echo "setup"
}
tearDown() {
  echo "Tear down"
}
oneTimeTearDown() {
  echo "One time tear down"
}
. shunit2

Output:

setup
testSomething
Tear down
One time tear down

Ran 1 test.

OK
Tear down
One time tear down

Looking into it, I only see warnings being raised if these functions do not exit successfully, but do not see why they would be called at the end of execution. PR for consideration: #113

These are being called as part of the EXIT trap. Related to #108.

Right, I wasn't familiarized with the entire topology. Looked things over and there is still a fundamental flaw since the exit code at the end of the script gets caught by the trap on successful runs so the 0 signal triggers _shunit_cleanup and the following block

if command [ ${__shunit_clean} -eq ${SHUNIT_FALSE} ]; then
    # Ensure tear downs are only called once.
    __shunit_clean=${SHUNIT_TRUE}

    tearDown
    command [ $? -eq ${SHUNIT_TRUE} ] \
        || _shunit_warn "tearDown() returned non-zero return code."
    oneTimeTearDown
    command [ $? -eq ${SHUNIT_TRUE} ] \
        || _shunit_warn "oneTimeTearDown() returned non-zero return code."

    command rm -fr "${__shunit_tmpDir}"
  fi

will trigger the tear downs again. I don't know what @kward's perspective is and whether the idea was to have termination always happen from within _shunit_cleanup (migrate in _shunit_generateReport and relative code here for 0 signal) or to remove the trap '_shunit_cleanup EXIT' 0

This can be used as sort of a hacky workaround:

tearDown() {
    #need this to suppress tearDown on script EXIT
    [[ "${_shunit_name_}" = 'EXIT' ]] && return 0

I tried adding the above code inside tearDown() but get the following error - is there something else that needs to be enabled or set?

in oneTimeSetUp
in setUp
testOne
validateTestOrdinals_test.sh[34]: shunit_name: parameter not set

the test script:

#! /bin/sh
#assume this test script is in a subdirectory under the shunit directory; a sibling of examples

#Load test helpers.
. ../shunit2_test_helpers

testOne() {
assertTrue 0
}

testTwo() {
assertTrue 0
}

setUp() {
echo "in setUp"
}

tearDown() {
#need this to suppress tearDown on script EXIT
[[ "${shunit_name}" = 'EXIT' ]] && return 0
echo "in tearDown"
}

oneTimeSetUp() {
echo "in oneTimeSetUp"
}

oneTimeTearDown() {
echo "in oneTimeTearDown"
}

#Load and run shUnit2.
. ../shunit2

My workaround is to create a directory in oneTimeSetUp and wrap the tear down code inside a check for that directory inside oneTimeTearDown - second time around, directory is not there, so code is skipped

Is this still a problem in the HEAD release?

Yes, tested on release 2.1.8. My output looks like this:

Calling teardown...

Ran 4 tests.

OK
Calling teardown...
PharoLauncherCommonFunctions.sh: line 45: ./pharo-launcher.sh: No such file or directory

I had the same problem. The following modification resolved my issue.

diff --git a/shunit2 b/shunit2
index 57a45da..ead9de6 100755
--- a/shunit2
+++ b/shunit2
@@ -1367,6 +1367,7 @@ _shunit_execSuite
 if ! oneTimeTearDown; then
   _shunit_fatal "oneTimeTearDown() returned non-zero return code."
 fi
+__shunit_clean=${SHUNIT_TRUE}
 
 # Generate a report summary.
 _shunit_generateReport