Installing the latest Python from source

Here is a shell script to install the lastest version of Python under Debian / Raspbian (3.7.4 and Stretch/Buster at the time of writing):

#!/bin/sh
RELEASE=3.7.4

# install dependencies
sudo apt-get install libbz2-dev liblzma-dev libsqlite3-dev libncurses5-dev libgdbm-dev zlib1g-dev libreadline-dev libssl-dev tk-dev uuid-dev libffi-dev

# The following line is required for Buster but will fail harmlessly under Stretch
sudo apt-get install libgdbm-compat-dev

# download and build Python
mkdir ~/python3
cd ~/python3
wget https://www.python.org/ftp/python/$RELEASE/Python-$RELEASE.tar.xz
tar xvf Python-$RELEASE.tar.xz
cd Python-$RELEASE
./configure --enable-optimizations --enable-shared
make
sudo make altinstall
sudo ldconfig
sudo rm -rf ~/python3/Python-$RELEASE
cd ~

Changelog

  • Updated to work with both Stretch and Buster
  • Updated version of Python and updated dependencies
  • ‘make altinstall’ instead of ‘make install’ – note that doing this no longer sets the default python3 to the copy you are building – you have to use python3.x instead.  I tend to use virtual environments these days to have better control over the versions in use.
  • Added –enable-optimizations to the configure step.  This makes builds much slower but you can remove this if you are impatient.
  • Added —enable-shared to the configure step.  This was needed for mod_wsgi builds and is a default option in Debian package builds anyway.

22 thoughts on “Installing the latest Python from source”

  1. Thank you, this is very helpful. What are your thought with regards to installing the next version if/when it becomes available. What will be the likely upgrade path moving forward, another in-place build over the top?

    1. To get the latest version (currently 3.5.2), it is as simple as visiting python.org to check what the latest version is then altering the version number in the shell script to match. If the dependencies are different with Python 3.6 then I will make a note on this blog post.

  2. gosh the dependencies took forever!! I seen something about screen savers also? I run jessie lite I hope a bunch of junk did not just get dropped on my sd card

  3. Can I also suggest that when the new Python is installed, links to the likes of RPi.GPIO are broken and you need to do a pip3 install RPi.GPIO to re-register the broken library link.

  4. Hello,
    All seems to work, except that when i input “python” on command line, python 2.7.3 stays the active release. How to replace with the new release (3.x), without deleting the 2.7 release ?
    Best regards.

  5. Thanks for sharing these instructions. I do have a rather newbie question though. What directory should I place the shell script in if I already have Python3.4 installed? Or does it not matter? Based on how you’ve written the script it doesn’t appear to matter, but wanted to check before running. I appreciate the help.

    1. It doesn’t matter where you store the shell script but I would suggest that anywhere in your home directory in suitable. It will install alongside Python 3.4 and become the default python3. You can still use python 3.4 if you need to by referring to it as python3.4 instead of python3.

        1. You don’t need to overwrite Python 3.4 – Python 3.6 will become the default version of python3. If you really need to then you can remove Python 3.4 with the command:
          $ sudo apt-get remove python3.4

          Bear in mind that this might break things that still depend on python 3.4.

  6. After all this (4 tries so far, with various prescriptions, all vaguely related but each subtly different, a full day’s work), still got this message:
    Failed to build these modules:
    _hashlib _ssl
    This is on a vanilla install of Debian/Raspian Jessie. Should it really be this hard?

  7. After running the script above python3.7 doesn’t work.
    I did not see any build errors.

    steps:
    reimage RPi3B+ with 2018-11-13-raspbian-stretch-lite.img
    “Linux raspberrypi 4.14.79-v7+ #1159 SMP Sun Nov 4 17:50:20 GMT 2018 armv7l GNU/Linux”

    create a script “nano pytest.py” to see OEM behavior
    #!/usr/bin/python3
    print (“allGood”)

    result:
    pi@raspberrypi:~ $ nano pytest.py
    pi@raspberrypi:~ $ chmod +x pytest.py
    pi@raspberrypi:~ $ ./pytest.py
    allGood
    pi@raspberrypi:~ $ python3 pytest.py
    allGood

    Ran the install as above. Results afterwards:
    pi@raspberrypi:~ $ python3 pytest.py
    allGood
    pi@raspberrypi:~ $ ./pytest.py
    allGood
    pi@raspberrypi:~ $ python3 –version
    Python 3.5.3
    pi@raspberrypi:~ $ python3.7 pytest.py
    python3.7: error while loading shared libraries: libpython3.7m.so.1.0: cannot open shared object file: No such file or directory

    1. Oops – I forgot a command at the end of the script:
      sudo ldconfig

      You don’t need to rerun the whole script, just type that single command at the shell prompt.

  8. Ah, thank you. My minimalist test now complete successfully.
    (hopefully it still is functional with a real task)

    pi@raspberrypi:~ $ python pytest.py
    allGood
    pi@raspberrypi:~ $ python3 pytest.py
    allGood
    pi@raspberrypi:~ $ python3.7 pytest.py
    allGood
    pi@raspberrypi:~ $ python -V
    Python 2.7.13
    pi@raspberrypi:~ $ python3 -V
    Python 3.5.3
    pi@raspberrypi:~ $ python3.7 -V
    Python 3.7.2
    pi@raspberrypi:~ $ which python3.7
    /usr/local/bin/python3.7

    And, once I used this path in the she-bang line of my script:
    pi@raspberrypi:~ $ ./pytest.py
    allGood

    1. My favoured shebang line would be:
      #!/usr/bin/env python3.7
      This would let your script work in more cases if you or someone else tried to run it on a different computer.

      I do however tend to use virtual environments these days though. In which case it would be:
      #!env/bin/python

  9. Any idea why pip is not found?
    I see this at the end of the install:
    Collecting pip
    Installing collected packages: setuptools, pip
    Successfully installed pip-18.1 setuptools-40.6.2

    But this when I run it:
    pi@raspberrypi:~ $ pip –version
    -bash: pip: command not found
    pi@raspberrypi:~ $ pip3 –version
    -bash: pip3: command not found
    pi@raspberrypi:~ $ sudo pip –version
    sudo: pip: command not found

    (I’ll reinstall pip – just curious what happened)

Leave a Reply

Your email address will not be published. Required fields are marked *