Nepal12 Nepal12 - 8 months ago 59
Bash Question

Grab return value from python with Shell Script

I am aware that a similar kind of question has already been asked and answered.
However, my question deals with a slightly different type of problem and implementation:

The situation is:

I need to build a shell script which will capture the return value of a python (2.7) script, which will then be used in a jenkins job.
In the python script, I have to read an SVN checkout text file and return the value of the file, update the value of the file, and commit it.

I have implemented the following code:

import posixpath
import os
import sys
import subprocess

SWDL_FILE_NAME = "swdl_number.txt"

# Exit codes
class ExitCode:
""" Exit code Enumeration """

# get SWDL number from the file
def getSWDLNumber():
work_dir = posixpath.join(os.getcwd(),SVN_VERSION_DIR_PATH)
version_number = None
new_version_number = None

# Read the File
with open(SWDL_FILE_NAME, "r") as input_file:
for line in input_file:
version_number = str.strip(line)
if version_number is None:
print "---- SWDL NUmber is empty existing the code ....... "
print "++++ The found SWDL number is : " + version_number
new_version_number = int(version_number) + 1
print "++++ The New SWDL Number is : " + str(new_version_number)

print "++++ Writing the new SWDL Number from " + str(version_number) + " to " + str(new_version_number)
#replace the file with new content
with open(SWDL_FILE_NAME, 'wb') as output:

checkin_message = '"Updated SWDL Number to : ' + str(new_version_number) + '"'
try:['svn', 'commit', '-m ' + checkin_message, SWDL_FILE_NAME, '--non-interactive'])

return new_version_number

if __name__ == "__main__":
print getSWDLNumber()

In my shell script I am doing:

echo $outputString

The swdl_number.txt contains only one line with 5 digits.

My problem:
When I comment out all the "print" lines and the try and catch for the SVN commit, I get only new_version_number as the return value.
In other words, If I uncomment all the lines with print statements and the try and catch block for SVN commit, then on the shell script as $output_string I get every print statements and the commit message as well as the "new_version_number". And If I comment out all the print statement and try and catch block then I am getting the desired "new_version_number".

How should my code be modified in order to get the only required "new_version_number" return, and display all print lines?

Answer Source



construction captures text sent to stdout. If you want your script to print information to the terminal then you can send it to stderr. Here's a simple demo.

import sys

print >>sys.stderr, "this is sent to stderr"
print "this is sent to stdout"

In Bash:

$ outputString=$(python;echo "ok";echo "$outputString"


this is sent to stderr
this is sent to stdout

Here's a version of that works on Python 2 and Python 3:

from __future__ import print_function
import sys

print("this is sent to stderr", file=sys.stderr)
print("this is sent to stdout")

If you also want to capture the output sent to stderr in a variable, one way to do that, without changing "", is to redirect stderr in Bash to a file:

$ outputString=$(python 2>qtemp);echo "ok";stderrString=$(<qtemp);echo "STDOUT: $outputString";echo "STDERR: $stderrString"
STDOUT: this is sent to stdout
STDERR: this is sent to stderr

A better way is to write directly to the file in Python:

from __future__ import print_function

with open("qtemp", "w") as f:
    print("this is sent to qtemp", file=f)
    print("this is sent to stdout")


$ outputString=$(python;echo "ok";qtempString=$(<qtemp);echo "STDOUT: $outputString";echo "qtemp: $qtempString"
STDOUT: this is sent to stdout
qtemp: this is sent to qtemp