2015. január 25., vasárnap

PyV8 még egyszer (Python 3 + pyenv)

Ma rendesen megszopattam magam, ugyanis nem kisebb probléma megoldásának álltam neki mint hogy lefordítom Python 3 alá a PyV8-at (Python 2 alá ez már egyszer sikerül). Az extra csavar a történetben az, hogy az interpreterem pyenv környezetben létezik.

A jövőben mindenképp írok még egy teljes bejegyzést a pyenvről. Egyelőre elég annyit tudni róla, hogy ez egy nagyszerű shell script, amivel pofonegyszerűen lehet menedzselni és váltogatni ugyan azon az operációs rendszeren a különböző verziójú Python interpretereket. Akár minden könyvtárban, minden shellben más verziót lehet futtatni, sőt, a virtualenv-ek kezelését is rá lehet bízni. Innen lehet beszerezni

Térjünk a tárgyra

Ez a mai menet kicsit trükkösebb mint a múltkori, mivel mindent forrásból kell elkészíteni. A PyV8 wikin kívül hatalmas segítség volt a ez a bejegyzés, ez is, meg ez is. Ezúton is köszönet értük.

Előkészületek

Steril gépen szükség lehet ezekre a csomagokra:

$ sudo apt-get install build-essential subversion

Ha ez megvan akkor rakjuk fel a Python 3-as verzióját (3.4.2 volt a legutolsó amikor ezt a bejegyzést írtam). Ha kész a fordítás akkor készítsünk egy virtualenvet.

$ pyenv install 3.4.2
$ pyenv virtualenv 3.4.2 v8
$ pyenv shell v8

Hozzunk létre egy könyvtárat amibe a forrásokat pakolásszuk majd:

$ cd ~
$ mkdir v8
$ cd v8

Jöhetnek a források

$ svn checkout http://v8.googlecode.com/svn/trunk/ v8
$ svn checkout http://pyv8.googlecode.com/svn/trunk/ pyv8

Állítsuk be a V8_HOME környezeti változót, hogy a setup.py megtalálja majd a V8 forrását:

$ export V8_HOME=/home/slapec/v8/v8

A Boostra is szükség lesz, a nélkül nem fordul a PyV8. Jelenleg az 1.57.0-ás verzió a legújabb.

$ wget http://sourceforge.net/projects/boost/files/boost/1.57.0/boost_1_57_0.tar.gz
$ tar -xvzf boost_1_57_0.tar.gz

A boost_1_57_0.tar.gz-t törölhetjük is akár.

Boost fordítás

A Boosttal kezdünk. A 3.4.2-es verzió ellen kell lefordítani. Mivel a pyenv is minden alkalommal forrásból fordítja a feltelepített Python verziót, ezért a header fájlokat megtaláljuk majd a .pyenv könyvtárban.

$ cd boost_1_57_0
$ ./bootstrap.sh --with-python-version=3.4 
                 --with-python-root=/home/slapec/.pyenv/versions/3.4.2/ 
                 --with-python=/home/slapec/.pyenv/versions/3.4.2/bin/python

Az argumentumokat nem kell új sorba írni, csak az olvashatóság miatt írtam így őket. Fontos: a scriptnek abszolút elérési útvonalakat kell adni.

Ha kész a bootstrap akkor pedig:

$ ./b2 include="/home/slapec/.pyenv/versions/3.4.2/include/python3.4m"

És lehet menni ebédelni amíg ezen gondolkozik a számítógép.

A The Boost C++ Libraries were successfully built! üzenet után installáljuk a libraryt, frissítsük a cache-t és állítsuk be a BOOST_HOME környezeti változót hogy a boost könyvtárára mutasson:

$ sudo ./b2 install
$ sudo ldconfig
$ export BOOST_HOME=/home/slapec/v8/boost_1_57_0

V8 fordítás

A V8 fordítása kicsit trükkösebb. Egy patchet kéne alkalmazni a PyV8 setup.py fájljának, ami bekapcsolja a V8 RTTI és Exception támogatását. Ez a setup.py viszont nem Python 3 kompatibilis. Ez még a kisebb probléma.

A nagyobb probléma, hogy a V8 fordításához is szükség van a Pythonra, de ott is csak a 2-es verzió a megfelelő. Lassan 7 éve hogy megjelent az első Python 3 verzió, és még mindig ilyen gyakoriak a problémák.

Jobb ötlet híján úgy döntöttem, hogy a PyV8 setup scriptjét módosítom egy kicsit, hogy elvégezze a patchelést, de a V8 fordítását már nem, de kiírja a parancsot amivel a V8-at fordíthatom, amit aztán kézzel, Python 2 környezetben futtatok is.

Tehát a pyv8/setup.py fájlban két dolgot kell szerkeszteni:

Az 523. sorban ebből:

os.makedirs(build_path, 0755)

Ez lesz:

os.makedirs(build_path, 0o755)

Ugyanis Python 3-ban az octal literal is megváltozott.

Az 513. sorban ebből az egy sorból

exec_cmd(cmdline, "build v8 from SVN")

Ez a három lesz:

#exec_cmd(cmdline, "build v8 from SVN")
print('Now switch to a Python 2 environment and build V8 with the following command')
exit(cmdline)

(Természetesen az első print() elhagyható.)

Ezek után jöhet is a build.

$ python setup.py build

A script a végén kiírja a parancsot amivel a V8-at lefordíthatjuk és kilép.

Ha ez megvan, akkor váltsunk át egy Python 2-es környezetre (pyenv shell system ha az alapértelmezett interpreter ilyen, vagy egyszerűen nyissunk egy új shellt).

$ cd v8
$ make -j 8 disassembler=off vtunejit=off library=shared werror=no strictaliasing=on gdbjit=off debuggersupport=on extrachecks=off visibility=on regexp=native objectprint=off backtrace=on i18nsupport=off liveobjectlist=off snapshot=on verifyheap=off x64.release

(Természetesen mindenki a saját make parancsát használja)

Ameddig ez lefordul, addig megtárgyalhatjuk hogy nem-e gáz hogy a build scriptből félúton kiléptünk.

A buld osztályban a run() metódu a prepare_v8() függvényt hívja meg, itt látszódnak a V8 fordításának lépései. Feljebb a build_v8() függvényt írogattuk át kicsit, ez mellékesen az utolsó előtti lépés. A következő a generate_probes() lenne, ami nálam amúgy is meghal dtrace not found errorral, úgyhogy annak mindegy hogy lefut-e vagy sem (természetesen annyira nem mindegy, de ezzel a hibával egyelőre nem tudtam mit kezdeni).

Mostanra remélhetőleg elkészült a V8. Menjünk vissza a PyV8 könyvtárába, váltsunk vissza Python 3-ra (pyenv shell v8) és jöhet az install:

$ cd pyv8
$ python setup.py install

Ha szerencsénk van akkor Finished processing dependencies for PyV8==1.0-dev üzenet fogad. Már csak ki kell próbálni hogy működik-e a vadiúj librarynk :3

$ cd ~
$ python -m unittest PyV8
...
FAILED (failures=2)

Sajna 2 teszt elhasalt, dehát semmi se tökéletes, nem :) ?

Aftermath

Vannak megoldásra váró problémái a PyV8 projektnek, de én nagyon örülök neki, hogy dolgoznak rajta hogy Javascript kódot lehessen futtatni Python alól. Az a példányom, amit még a régi projektemhez fordítottam a mai napig jól működik, csak én már szeretnék Python 3-ra váltani, ezért voltam kénytelen újra elővenni ezt a problémát.

Mindenkinek kellemes fordítgatást : )

-slp

Nincsenek megjegyzések:

Megjegyzés küldése