2

I'm building an rpm to install a component on my machines, but I would like to check if certain python libraries are already installed so as not to reinstall them unnecessarily. So, in the %post section of my spec file, I'm doing this:

function check4pythonlib() {
    library=$1
    if [[ $(/usr/local/bin/python2.7 -c "import $library" 2> /dev/null ; echo $?) -eq 0 ]]; then
        echo "$library is installed"
    else
        echo "$library is not installed"
        echo "Installing $library..."
        cd /path/to/lib/$library
        /usr/local/bin/python2.7 setup.py build
        /usr/local/bin/python2.7 setup.py install
    fi
}

check4pythonlib pythonlib1
check4pythonlib pythonlib2

I'm writing all output to a log file, and I see this:

 is not installed
Installing ...
/usr/local/bin/python2.7: can't open file 'setup.py': [Errno 2] No such file or directory
/usr/local/bin/python2.7: can't open file 'setup.py': [Errno 2] No such file or directory
 is not installed
Installing ...
/usr/local/bin/python2.7: can't open file 'setup.py': [Errno 2] No such file or directory
/usr/local/bin/python2.7: can't open file 'setup.py': [Errno 2] No such file or directory

It seems the argument is not being passed to the function. I have also tried enclosing the arguments in double quotes, but it does not work either. What can I do to properly pass the arguments during rpm installation, so that this works?

Tino
  • 304
  • 4
  • 14
  • http://unix.stackexchange.com/q/149034/22257 doesn't really explain the problem, but might be useful as a workaround. (At least, its success or failure might provide a clue to solving this problem.) – chepner Apr 14 '16 at 18:12
  • Not the issue just a comment. To test the return code of a command just run it. Don't use string/numeric comparison. So use `if some_command arg1 arg2; then` if you want to test for success and `if ! some_command arg1 arg2; then` if you want to test for failure. – Etan Reisner Apr 14 '16 at 19:26
  • 1
    Does your spec file have DOS line endings by any chance? If you add `set -vx` to the top of that scriplet what do you see as output when you install the rpm? As a general comment are you correctly `Require`-ing whatever provides `/usr/local/bin/python2.7` or that file itself so that you RPM is properly packaged? Why would those libraries be on the machine but not installed? Are they packaged in some other RPM/this RPM? – Etan Reisner Apr 14 '16 at 19:29
  • @EtanReisner Thanks for the suggestion on the if statement! And yeah, the libraries are actually included in the RPM, so they are only copied / installed if they are missing. – Tino Apr 14 '16 at 19:46
  • Why would they be there if the package isn't installed? Why does the package itself not just contain the built pieces in the correct (installed) location? – Etan Reisner Apr 14 '16 at 19:51
  • I release new versions of the software somewhat constantly, so when I install a new version on a machine with the old rpm already installed, the python libraries are there already (they don't change with every release). I mean, I could do this just by copy pasting the commands * the number of libraries I have to check, but that would be crappy, so I'd like to do it a more intelligent way. – Tino Apr 14 '16 at 20:12

1 Answers1

0

So, I noticed that when running that section of the spec file with set -vx as Etan Reisner suggested, something weird would occur... the output looked like this:

function check4pythonlib() {
    library=pythonlib1
    if [[ $(/usr/local/bin/python2.7 -c "import " 2> /dev/null ; echo $?) ]]; then
        echo " is installed"
    else
        echo " is not installed"
        echo "Installing ..."
        cd /path/to/lib/
        /usr/local/bin/python2.7 setup.py build
        /usr/local/bin/python2.7 setup.py install
    fi
}

So clearly the argument pythonlib1 was making it inside the function, but for some reason I could not see the variable I had assigned it to (in this case $library).

So this is what I ended up doing:

function check4pythonlib() {
    if [[ $(/usr/local/bin/python2.7 -c "import $1" 2> /dev/null ; echo $?) ]]; then
        echo "$1 is installed"
    else
        echo "$1 is not installed"
        echo "Installing $1..."
        cd /path/to/lib/$1
        /usr/local/bin/python2.7 setup.py build
        /usr/local/bin/python2.7 setup.py install
    fi
}

I replaced the variable $library directly with the argument, in this case $1. Dirty, but now it works. Now I just need to figure out why variables seem to disappear when used inside spec files...

Tino
  • 304
  • 4
  • 14