What\'s the best way to download a python package and it\'s dependencies from pypi for offline installation on another machine? Is there any easy way to do this with pip or
Download the tarball, transfer it to your FreeBSD machine and extract it, afterwards run python setup.py install
and you're done!
EDIT: Just to add on that, you can also install the tarballs with pip now.
The pip download
command lets you download packages without installing them:
pip download -r requirements.txt
(In previous versions of pip, this was spelled pip install --download -r requirements.txt
.)
Then you can use pip install --no-index --find-links /path/to/download/dir/ -r requirements.txt
to install those downloaded sdists, without accessing the network.
If the package is on PYPI, download it and its dependencies to some local directory. E.g.
$ mkdir /pypi && cd /pypi $ ls -la -rw-r--r-- 1 pavel staff 237954 Apr 19 11:31 Flask-WTF-0.6.tar.gz -rw-r--r-- 1 pavel staff 389741 Feb 22 17:10 Jinja2-2.6.tar.gz -rw-r--r-- 1 pavel staff 70305 Apr 11 00:28 MySQL-python-1.2.3.tar.gz -rw-r--r-- 1 pavel staff 2597214 Apr 10 18:26 SQLAlchemy-0.7.6.tar.gz -rw-r--r-- 1 pavel staff 1108056 Feb 22 17:10 Werkzeug-0.8.2.tar.gz -rw-r--r-- 1 pavel staff 488207 Apr 10 18:26 boto-2.3.0.tar.gz -rw-r--r-- 1 pavel staff 490192 Apr 16 12:00 flask-0.9-dev-2a6c80a.tar.gz
Some packages may have to be archived into similar looking tarballs by hand. I do it a lot when I want a more recent (less stable) version of something. Some packages aren't on PYPI, so same applies to them.
Suppose you have a properly formed Python application in ~/src/myapp
. ~/src/myapp/setup.py
will have install_requires
list that mentions one or more things that you have in your /pypi
directory. Like so:
install_requires=[
'boto',
'Flask',
'Werkzeug',
# and so on
If you want to be able to run your app with all the necessary dependencies while still hacking on it, you'll do something like this:
$ cd ~/src/myapp $ python setup.py develop --always-unzip --allow-hosts=None --find-links=/pypi
This way your app will be executed straight from your source directory. You can hack on things, and then rerun the app without rebuilding anything.
If you want to install your app and its dependencies into the current python environment, you'll do something like this:
$ cd ~/src/myapp $ easy_install --always-unzip --allow-hosts=None --find-links=/pypi .
In both cases, the build will fail if one or more dependencies aren't present in /pypi
directory. It won't attempt to promiscuously install missing things from Internet.
I highly recommend to invoke setup.py develop ...
and easy_install ...
within an active virtual environment to avoid contaminating your global Python environment. It is (virtualenv that is) pretty much the way to go. Never install anything into global Python environment.
If the machine that you've built your app has same architecture as the machine on which you want to deploy it, you can simply tarball the entire virtual environment directory into which you easy_install
-ed everything. Just before tarballing though, you must make the virtual environment directory relocatable (see --relocatable option). NOTE: the destination machine needs to have the same version of Python installed, and also any C-based dependencies your app may have must be preinstalled there too (e.g. say if you depend on PIL, then libpng, libjpeg, etc must be preinstalled).
Using wheel
compiled packages.
bundle up:
$ tempdir=$(mktemp -d /tmp/wheelhouse-XXXXX)
$ pip wheel -r requirements.txt --wheel-dir=$tempdir
$ cwd=`pwd`
$ (cd "$tempdir"; tar -cjvf "$cwd/bundled.tar.bz2" *)
copy tarball and install:
$ tempdir=$(mktemp -d /tmp/wheelhouse-XXXXX)
$ (cd $tempdir; tar -xvf /path/to/bundled.tar.bz2)
$ pip install --force-reinstall --ignore-installed --upgrade --no-index --no-deps $tempdir/*
Note wheel
binary packages are not across machines.
More ref. here: https://pip.pypa.io/en/stable/user_guide/#installation-bundles
I had a similar problem. And i had to make it install the same way, we do from pypi.
I did the following things:
Make a directory to store all the packages in the machine that have internet access.
mkdir -p /path/to/packages/
Download all the packages to the path
Edit: You can also try:
python3 -m pip wheel --no-cache-dir -r requirements.txt -w /path/to/packages
pip download -r requirements.txt -d /path/to/packages
Eg:- ls /root/wheelhouse/ # **/root/wheelhouse** is my **/path/to/packages/**
total 4524
-rw-r--r--. 1 root root 16667 May 23 2017 incremental-17.5.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 34713 Sep 1 10:21 attrs-18.2.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 3088398 Oct 15 14:41 Twisted-18.9.0.tar.bz2
-rw-r--r--. 1 root root 133356 Jan 28 15:58 chardet-3.0.4-py2.py3-none-any.whl
-rw-r--r--. 1 root root 154154 Jan 28 15:58 certifi-2018.11.29-py2.py3-none-any.whl
-rw-r--r--. 1 root root 57987 Jan 28 15:58 requests-2.21.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 58594 Jan 28 15:58 idna-2.8-py2.py3-none-any.whl
-rw-r--r--. 1 root root 118086 Jan 28 15:59 urllib3-1.24.1-py2.py3-none-any.whl
-rw-r--r--. 1 root root 47229 Jan 28 15:59 tqdm-4.30.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 7922 Jan 28 16:13 constantly-15.1.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 164706 Jan 28 16:14 zope.interface-4.6.0-cp27-cp27mu-manylinux1_x86_64.whl
-rw-r--r--. 1 root root 573841 Jan 28 16:14 setuptools-40.7.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 37638 Jan 28 16:15 Automat-0.7.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 37905 Jan 28 16:15 hyperlink-18.0.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 52311 Jan 28 16:15 PyHamcrest-1.9.0-py2.py3-none-any.whl
-rw-r--r--. 1 root root 10586 Jan 28 16:15 six-1.12.0-py2.py3-none-any.whl
Tar the packages directory and copy it to the Machine that doesn't have internet access. Then do,
cd /path/to/packages/
tar -cvzf packages.tar.gz . # not the . (dot) at the end
Copy the packages.tar.gz into the destination machine that doesn't have internet access.
In the machine that doesn't have internet access, do the following (Assuming you copied the tarred packages to /path/to/package/ in the current machine)
cd /path/to/packages/
tar -xvzf packages.tar.gz
mkdir -p $HOME/.config/pip/
vi $HOME/.config/pip/pip.conf
and paste the following content inside and save it.
[global]
timeout = 10
find-links = file:///path/to/package/
no-cache-dir = true
no-index = true
Finally, i suggest you use, some form of virtualenv
for installing the packages.
virtualenv -p python2 venv # use python3, if you are on python3
source ./venv/bin/activate
pip install <package>
You should be able to download all the modules that are in the directory /path/to/package/.
Note: I only did this, because i couldn't add options or change the way we install the modules. Otherwise i'd have done
pip install --no-index --find-links /path/to/download/dir/ -r requirements.txt
For Pip 8.1.2 you can use pip download -r requ.txt
to download packages to your local machine.