====== Backport di Python 2.7 ======
===== Su Debian 6 Squeeze =====
Nel caso sia necessario fare il **backporting** di un Python più recente su una distribuzione molto datata, c'è una alternativa rispetto a scaricare i sorgenti e procedere alla compilazione. Si tratta di **pyenv**, che si definisce in questo modo: //pyenv lets you easily switch between multiple versions of Python. It's simple and unobtrusive//.
Il tool **[[https://github.com/pyenv/pyenv|pyenv]]** è in grado di automatizzare gran parte del processo, che comunque prevede il download e la compilazione dei sorgenti. Quindi è necessario installare a livello di systema i **tool di compilazione** e le gli **header** delle librerie da cui dipende Python. L'installazione del Python 2.7 e delle librerie aggiuntive desiderate invece **può risiedere nella $HOME di un utente**, senza disturbare il resto del sistema.
Queste le installazioni da fare come root:
apt-get install curl git gcc build-essential \
libmysqlclient-dev libadns1-dev \
libreadline-dev libgdbm-dev zlib1g-dev libsqlite3-dev \
libssl-dev libbz2-dev libncurses5-dev libdb-dev
==== Installazione in $HOME utente ====
:!: **ATTENZIONE**: Qui si installa pyenv nella directory utente **$HOME/.pyenv/** che è **sconsigliato** se deve essere usata a livello di sistema (vedi più avanti):
curl -L https://raw.githubusercontent.com/pyenv/pyenv-installer/master/bin/pyenv-installer \
> pyenv-installer
export USE_GIT_URI='yes'
cat pyenv-installer | bash
==== Installazione in /usr/local/lib/ ====
Più opportunamente si può usare una **directory di sistema**, pur eseguendo il tutto da **utente non privilegiato**. L'impostazione **USE_GIT_URI** serve ad utilizzre http invece di https per aggirare il problema di SSL su vecchie distribuzioni: //tlsv1 alert protocol version//.
:!: **ATTENZIONE**: la directory destinazione (nell'esempio ''/usr/local/lib/pyenv'' NON deve esistere, ma la directory parente deve essere scrivibile dall'utente che esegue il comando:
curl -L https://raw.githubusercontent.com/pyenv/pyenv-installer/master/bin/pyenv-installer \
> pyenv-installer
export USE_GIT_URI='yes'
export PYENV_ROOT='/usr/local/lib/pyenv'
cat pyenv-installer | bash
==== Utilizzo di pyenv ====
Dopo aver installato il tool pyenv è necessario inizializzare l'ambiente prima di usarlo (conviene aggiungere i comandi a ''.bashrc'' o simili):
export PYENV_ROOT='/usr/local/lib/pyenv'
export PYTHON_BUILD_CACHE_PATH=/usr/local/lib/pyenv/cache
export PATH="/usr/local/lib/pyenv/bin:$PATH"
eval "$(pyenv init -)"
eval "$(pyenv virtualenv-init -)"
Per evitare il problema di download su https, si è scaricato da altro host il file **[[https://www.python.org/ftp/python/2.7.13/Python-2.7.13.tar.xz|Python-2.7.13.tar.xz]]** e lo si è messo nella directory **PYTHON_BUILD_CACHE_PATH** (che va creata), a questo punto si può eseguire
pyenv install 2.7.13
Per selezionare l'**ambiente Python 2.7.13** appena installato invece di quello di sistema, si deve aggiungere questa variabile d'ambiente (oltre a quelle viste in precedenza):
export PYENV_VERSION=2.7.13
Dopo avere settato queste variabili è possibile installare librerie con il gestore **pip**. Resta il problema del download automatico via https, per aggirarlo è necessario fare il download del pacchetto da un altro host e quindi eseguire **pip install nomefile.tar.gz**.
==== Ricollocazione dell'installazione di pyenv ====
La directory ''$HOME/.pyenv/'' **non può essere spostata altrove**. Molti degli eseguibili creati in **$HOME/.pyenv/versions/2.7.13/** contengono hard-coded il percorso di installazione originale, ad esempio:
* bin/python2.7
* lib/libpython2.7.a
* lib/pkgconfig/python-2.7.pc
==== Problema con pip e ssl ====
Con l'installazione di **pyenv** e di Python 2.7.13 comunque **non si risolve il problema dell'SSL**: Debian 6 fornisce una versione troppo vecchia della libreria, quindi il **wget** da siti **https falisce**. Ad esempio anche la ricerca della **libreria openpyxl** fallisce:
pip search openpyxl
...
SSLError: [SSL: TLSV1_ALERT_PROTOCOL_VERSION] tlsv1 alert protocol version (_ssl.c:661)
Ovviamente viene a mancare anche **la gestione delle eventuali dipendenze** (download e install automatico). La soluzione è scaricare gli archivi necessari e copiarli in una directory locale prima di fare l'installazione. Nel caso della libreria **openpyxl** gli archivi necessari sono prelevabili da **pypi.org**:
* **[[https://pypi.org/project/jdcal/#files|jdcal-1.4.1-py2.py3-none-any.whl]]**
* **[[https://pypi.org/project/et_xmlfile/#files|et_xmlfile-1.0.1.tar.gz]]**
* **[[https://pypi.org/project/openpyxl/#files|openpyxl-2.6.2.tar.gz]]**
Gli archivi di tipo **.tar.gz** vanno scompattati, mentre i **.whl** (Python wheel) possono essere installati direttamente (ricordarsi sempre di settare le **variabili di ambiente Pyenv**):
pip install /usr/local/download/openpyxl/jdcal-1.4.1-py2.py3-none-any.whl
pip install /usr/local/download/openpyxl/et_xmlfile-1.0.1/
pip install /usr/local/download/openpyxl/openpyxl-2.6.2/
===== Su Fedora 12 =====
L'operazione è del tutto analoga, salvo che i pacchetti per la compilazione si chiamano in modo diverso:
yum install gcc git readline-devel zlib-devel bzip2-devel libsq3-devel openssl-devel
Per fare **pip install lxml** servono anche i seguenti pacchetti (probabilmente è necessario solo il **libxml2-devel**):
yum install libxml2-python libxslt-python libxml2-devel libxslt-devel
Su Fedora 12 c'è il grave problema della libreria SSL obsoleta, per cui tutti i download su protocollo https falliscono. È necessario scaricare i file localmente per altra via (scp) e poi usare i trucchi sopra per eseguire le installazioni da file locali.
===== Archivi da installare =====
Un esempio pratico: si deve eseguire uno script Python che utilizza le librerie **bs4**, **lxml** e **suds**.
Avendo installato Python 2.7, si dovrà cercare le librerie marcate con **cp27**, che significa appunto CPython 2.7 (la versione ufficiale di Python distrinuita da python.org).
I suffissi **cp27m** e **cp27mu** si riferiscono ai tag ABI **%%--enable-unicode=ucs2%%** e **%%--enable-unicode=ucs4%%** rispettivamente. Per vedere quale ABI supporta il proprio Python si esegue il comando **print sys.maxunicode**; il valore restituito significa: 65535 = ucs2, 1114111 = ucs4.
I file con estensione **.whl** sono **wheel distribution**. Possono essere installati direttamente con **pip install pacchetto.whl**.
* [[https://www.python.org/ftp/python/2.7.13/Python-2.7.13.tar.xz|Python-2.7.13.tar.xz]]
* [[https://pypi.org/project/beautifulsoup4/#files|beautifulsoup4]]
* [[https://pypi.org/project/lxml/#files|lxml-4.2.5]]
* [[https://pypi.org/project/suds2/|suds2]]
Se si desidera che eseguento genericamente python venga avviata la versione 2.7 invece che quella di sistema, basta creare uno script **/usr/local/bin/python** che contiene:
#!/bin/sh
export PYENV_ROOT="/usr/local/lib/pyenv"
export PATH="/usr/local/lib/pyenv/bin:$PATH"
eval "$(pyenv init - --no-rehash)"
eval "$(pyenv virtualenv-init -)"
export PYENV_VERSION=2.7.13
exec python "$@"
L'opzione **%%--no-rehash%%** serve ad evitare l'errore causato dal tentativo di python di aggiornare la directory degli [[wp>Shim (computing)|shim]] (script che intercettano le chiamate ai vari tool e le dirottano all'eseguibile opportuno):
pyenv: cannot rehash: /usr/local/lib/pyenv/shims isn't writable
Ricordarsi comunque che per eseguire **pip** e simili bisogna impostare le variabili d'ambiente.
===== Installazione con pip =====
Il comando **pip** può essere usato per installare le librerie necessarie nell'ambiente Python in uso. In caso di Python installato in backporting come illustrato sopra (**pyenv**, ecc.) è sufficiente **impostare le variabili d'ambiente** necessarie a pyenv prima di eseguire pip.
Alcuni comandi utili:
^ pip list | Elenca i pacchetti installati tramite il sistema pip. |
^ pip freeze | Elenca i pacchetti installati tramite il sistema pip, in formato //requirements//. |
^ pip search package | Cerca un pacchetto disponibile nei repository pip. |
^ pip install package | Scarica un pacchetto dai repository e lo installa. |
^ pip install /src/pkg/dir/ | Installa un pacchetto dalla directory di installazione (deve contenere il file **setup.py**). |
^ pip uninstall package | Rimuove un pacchetto installato. Se si desidera disinstallare una specifica versione, usare la stringa prodotta da //pip freeze// (requirements format), ad esempio:\\ pip uninstall Pillow==5.4.1 |
Per vedere **quali moduli installati da pip sono disponibili in Pyton** (e le rispettive versioni), eseguire in Python:
import pip
pip.get_installed_distributions(local_only=True)
[ setuptools 28.8.0 (/usr/local/lib/pyenv/versions/2.7.13/lib/python2.7/site-packages),
pip 9.0.1 (/usr/local/lib/pyenv/versions/2.7.13/lib/python2.7/site-packages),
openpyxl 2.4.9 (/usr/local/lib/pyenv/versions/2.7.13/lib/python2.7/site-packages),
jdcal 1.3 (/usr/local/lib/pyenv/versions/2.7.13/lib/python2.7/site-packages),
et-xmlfile 1.0.1 (/usr/local/lib/pyenv/versions/2.7.13/lib/python2.7/site-packages)
]
Si ottiene l'elenco delle librerie contenute in **$PYTHONPATH/../lib/python2.7/site-packages/**.
**ATTENZIONE**: L'elenco sopra riportato dovrebbe essere lo stesso riportato da **list** o **freeze**
pip list
et-xmlfile (1.0.1)
jdcal (1.3)
openpyxl (2.6.2, /usr/local/download/openpyxl/openpyxl-2.6.2)
Pillow (5.4.1, /usr/local/download/python-pil/Pillow-5.4.1/src)
pip (9.0.1)
setuptools (28.8.0)
pip freeze
et-xmlfile==1.0.1
jdcal==1.3
openpyxl==2.6.2
Pillow==5.4.1
Se i due elenchi differiscono potrebbe dipendere dal fatto che il pyenv non ha impostato correttamente le variabili d'ambiente (vedi sopra il problema della rilocazione dei file dopo l'installazione).
===== Aggiornamento libreria con pip =====
È possibile installare una versione aggiornata di una libreria tramite pip, disinstallando eventualmente il pacchetto Debian che contiene la vecchia versione. Ad esempio:
dpkg --purge python-openpyxl
pip install openpyxl