本文主要内容参考自:

http://toomuchdata.com/2012/06/25/how-to-install-python-2-7-3-on-centos-6-2/#comment-5691

使用Python,一个绕不过去的问题,就是其版本繁多的问题。首先是版本选择问题,这个不在我们讨论的范围之内,官网上在显眼的位置做了一些说明和建议:Python2 or Python3。

这里我们假设知道自己该选哪个或哪几个版本了。这里就会遇到第二个问题,python在linux中属于基础组件,各发行版会默认安装一个python,例如CentOS5.5中的是2.4.3,而CentOS6.2中是2.6.6.

以CentOS6.2为例,在/usr/bin目录下有一个python和一个python2.6.这两者有什么区别呢:

[root@vps1 ~]# ls -l /usr/bin/python
-rwxr-xr-x 2 root root 3592 Dec 7 2011 /usr/bin/python [root@vps1 ~]# ls -l /usr/bin/python2.6 -rwxr-xr-x 2 root root 3592 Dec 7 2011 /usr/bin/python2.6

可以看到两个都不是软链接。通过计算一下md5值,可以发现这两者一模一样:

958a320a8c3f4d352d398bb0ebc46ed8 /usr/bin/python
[root@vps1 ~]# md5sum /usr/bin/python2.6 958a320a8c3f4d352d398bb0ebc46ed8 /usr/bin/python2.6

因此,/usr/bin/python实际上是/usr/bin/python2.6的一个拷贝。如果我们此时想安装一个python3.3,应该怎么做呢?首先绝对不要想着先去卸载已有的python,曾经apt-get remove python或者yum remove python的人肯定会会心一笑。最通常的做法,下载到python3.3的源码来编译。

在CentOS下,通过./configure&&make&&make install安装后,python会被安装到/usr/local/bin目录下,可能同时有python,python3,python3.3。其中python3.3和python是两个一模一样h的可执行文件,而python3则是一个指向/usr/local/bin/python的软链接。这样带来的问题是,在/usr/bin和/usr/local/bin目录下,都有一个名为python的可执行文件。虽然通过环境变量的可以确定在shell中执行python时到底是执行了哪个目录下的python,但总归显的很麻烦,时间长了更容易引起混乱。

这个仅仅是安装一个python时遇到的问题,现实情况下,你可能同时跑着两个版本的django,每个版本的django依赖的python又不同,通过分别指定路径、建立软连接等方式虽然能解决,但还是一个字,乱。不知什么时候,就会互相影响了。

自从有了virtualenv,pythoner的生活就好起来了。

virtualenv的目的就是让每个python应用程序和自己依赖的python解释器及python库,各自隔离开来,互相不影响,更不会破坏系统自带的python环境。

下面就来详细的演示virtualenv的操作过程:

1.系统环境说明:

操作系统:CentOS6.2
# cat /etc/issue
CentOS release 6.2 (Final)
Kernel \r on an \m

系统自带python环境:

# python -V
Python 2.6.6
|# whereis python
python: /usr/bin/python /usr/bin/python2.6 /usr/lib/python2.6 /usr/include/python2.6 /usr/share/man/man1/python.1.gz
# ls -l /usr/bin/python*
-rwxr-xr-x 2 root root 3592 Dec 7 2011 /usr/bin/python
lrwxrwxrwx 1 root root 6 Nov 12 06:29 /usr/bin/python2 -> python
-rwxr-xr-x 2 root root 3592 Dec 7 2011 /usr/bin/python2.6

2.操作预期:

分别安装最新版的python2.7和python3.3,并各自安装一个flask框架,互相隔离。

3.操作过程:

(1)方便起见,首先安装一些其它常用的组件:

yum groupinstall "Development tools"  
yum install zlib-devel bzip2-devel openssl-devel ncurses-devel sqlite-devel readline-devel tk-devel  

(2)下载和安装python2.7.6

# mkdir -p /home/fangpeng/sources  
# cd /home/fangpeng/sources/  
# wget http://www.python.org/ftp/python/2.7.6/Python-2.7.6.tgz  
#tar xvfz Python-2.7.6.tgz  
#cd Python-2.7.6  
# ./configure --prefix=/usr/local  
# make && make altinstall  

注意,是make altinstall,而不是make install。这样可以避免造成系统存在多个名为python,实际版本却各异的文件。

安装完毕后,/usr/bin下系统自带的几个python文件都没有任何影响。在/usr/local/bin目录下,则多了一个python2.7和python2.7-config。

(3)下载和安装Python3.3.2

# cd /home/fangpeng/sources  
# wget http://www.python.org/ftp/python/3.3.2/Python-3.3.2.tgz  
#tar xvfz Python-3.3.2.tgz  
# cd Python-3.3.2  
# ./configure --prefix=/usr/local  
# make && make altinstall  

同样注意,是make altinstall,而非make install。安装完成后,在/usr/local/bin目录下,多出三个文件,分别是python3.3m,python3.3和python3.3-config,其中python3.3和python3.3m是同一个文件的两份拷贝。对系统自带的python2.6.6和上一步安装的python2.7.6无影响。

(4)下载distribute

# cd /home/fangpeng/sources  
# wget --no-check-certificate https://pypi.python.org/packages/source/d/distribute/distribute-0.6.49.tar.gz  

(5)为python2.7.6安装easy_install

# tar xvfz distribute-0.6.49.tar.gz  
# cd distribute-0.6.49  
# python2.7 setup.py  install  

(6)为python3.3.2安装easy_install

# cd /home/fangpeng/sources/  
# rm -rf distribute-0.6.49  
# tar xvfz distribute-0.6.49.tar.gz  
# cd distribute-0.6.49  
# python3.3 setup.py install  

执行完(5)和(6)后,在/usr/local/bin目录下,会多出三个文件,分别是easy_install,easy_install-2.7和easy_install-3.3。其中,easy_install在两次安装时都会生成,因此会存在覆盖。我们直接使用easy_install-2.7和easy_install-3.3即可。

(7)为python2.7安装virtualenv
终于到了virtualenv了,这才是我们今天的主角。

easy_install-2.7 virtualenv  

(8)为python3.3安装virtualenv

# easy_install-3.3  virtualenv  

至此,我们分别为python2.7.6和python3.3.2安装了virtualenv。同样在/usr/local/bin目录下多出了三个文件,分别是virtualenv,virtualenv-2.7和virtualenv-3.3。其中,virtualenv在两次安装时都会生成,因此会存在覆盖。我们直接使用virtualenv-2.7和virtualenv-3.3即可。

下面用web框架flask的安装,来演示virtualenv的使用。创建两个flask的沙盒,其中一个依赖的是python2.7.6,另一个依赖python3.3.2。

(1)创建相应的工程目录

# mkdir -p /home/fangpeng/project/hello_flask  
# cd /home/fangpeng/project/hello_flask/  
# mkdir python2.7 python3.3  

(2)创建基于python2.7的flask工程

# cd /home/fangpeng/project/hello_flask/python2.7/  
# virtualenv-2.7 --distribute env  
Using base prefix '/usr/local'  
New python executable in env/bin/python3.3  
Also creating executable in env/bin/python  
Installing Setuptools..................................................................................................................................done.  
Installing Pip.............................................................................................................................................done.  
# source env/bin/activate  
(env)# 
(env)# python -V  
Python 2.7.6  
# pip install flask  
(env)# vim hello.py  

hello.py内容如下:

from flask import Flask  
app=Flask(__name__)  
  
@app.route('/hello')  
def hello():  
        return "Hello,Flask!"  
if __name__=='__main__':  
        app.run(host='0.0.0.0',debug=True)  

执行hello.py:

(env)# python hello.py 
 * Running on http://0.0.0.0:5000/  
 * Restarting with reloader  

用浏览器或在另一个终端用curl访问该hello接口,如下:

# curl 192.168.1.101:5000/hello  
Hello,Flask!#  

(3)退出python2.7的virtualenv环境

继续上一步,按ctr+c退出hello.py的执行。如下所示,此时还处于python2.7的virtualenv中,执行deactivate退出。

(env)# deactivate  
# 

(4)创建基于python3.3的flask工程

#cd /home/fangpeng/project/hello_flask/python3.3/  
# virtualenv-3.3 --distribute env  
Using base prefix '/usr/local'  
New python executable in env/bin/python3.3  
Also creating executable in env/bin/python  
Installing Setuptools.........................................................................................done.  
Installing Pip....................................................................................................done.  
# source env/bin/activate  
(env)# 
#(env) python -V  
Python 3.3.2  
(env)# pip  install flask  

hello.py的内容和上面完全一致,此处略去。
执行hello.py:

(env)# python hello.py 
 * Running on http://0.0.0.0:5000/  
 * Restarting with reloader  

用浏览器或在另一个终端用curl访问该hello接口,如下:

# curl 192.168.1.101:5000/hello  
Hello,Flask!#  

至此演示完毕。

与上面的例子类似,以后如果要python2.7.6,则在创建应用程序前,先用virtualenv-2.7创建一个沙盘,要用python3.3.2,则用virtualenv-3.3创建一个沙盘。这样,依赖不同版本python的应用程序彼此完全隔离开来。在各自的virtualenv中,执行python命令就不用管版本问题了,更重要的是,系统自带的python环境也完全被隔离开来。