cx-freeze, runpy et multiprocessing – plusieurs chemins vers l’échec

C’est un peu complexe et peut prendre un peu de votre temps.

Le problème de base est que, sur Linux (Ubuntu dans mon cas de test), une version de mon programme (Omnitool) cx-freeze ne peut pas créer de sous-processus. Cela fonctionne sur Windows 7, cependant. Ou lors de l’exécution directe à partir du code source. Malheureusement, ce n’est pas aussi simple que d’oublier freeze_support .

Le problème

Le comportement par défaut du démarrage d’un sous-processus est que le serveur X se bloque. Spécifiquement comme ceci:

 XIO: fatal IO error 11 (Resource temporarily unavailable) on X server ":0" after 23 requests (23 known processed) with 0 events remaining. [xcb]Unknown sequence number while processing queue [xcb] Most likely this is a multi-threaded client and XInitThreads has not been called [xcb] Aborting, sorry about that. Omnitool: ../../src/xcb_io.c:274: poll_for_event: Assertion `!xcb_xlib_threads_sequence_lost' failed. Aborted (core dumped) 

Il n’y a pas de trace de python. J’ai essayé d’appeler manuellement XInitThreads avec ctypes, il retourne 0 pour réussir à définir, mais se bloque malgré tout. Bref, avant le crash, l’interface utilisateur de pygame est défectueuse, donc je m’attends à quelque chose qui ne fonctionne pas.

Maintenant, configurer multiprocessing.set_start_method() change les problèmes: “forkserver” me donne cette belle traceback, qui ne dit rien:

Exemple de collage

Le placer au lieu de le faire fait simplement qu’il ne fait rien. Le processus démarre et passe par __main__ , comme je peux le prouver avec les impressions, mais n’entre jamais dans la fonction cible du sous-processus.

Vous essayer

Assurez-vous d’avoir Ubuntu ou un Linux comparable avec python 3.4. Ensuite, pour obtenir toutes les dépendances:

Téléchargez omnitool comme zip ou clone à partir de git: https://github.com/Berserker66/omnitool requirements.txt dans le code suivant provient de Omnitool.

 sudo apt-get update -qq sudo apt-get install --fix-missing mercurial subversion python3-dev python3-numpy libav-tools libsdl-image1.2-dev libsdl-mixer1.2-dev libsdl-ttf2.0-dev libsmpeg-dev libsdl1.2-dev libportmidi-dev libswscale-dev libavformat-dev libavcodec-dev python3-pip pip3 install -r requirements.txt pip3 install cx_Freeze 

Pour geler, exécutez omnisetup.py avec l’argument build .

J’ai aussi essayé de geler avec pyinstallers python 3 fork, qui échoue très similaire. Le fichier de spécification n’est cependant pas suivi.

J’ai utilisé cx_freeze pour un projet au travail. Je ne suis pas sûr que ce soit votre problème … mais j’utilisais la dissortingbution Anaconda et cx_freeze ne collectait pas correctement les fichiers .dll dont j’avais besoin pour mon projet.

La solution était de:

  1. Installer une version avion de Python
  2. faire un environnement avec les paquets dont j’avais besoin pour ce projet
  3. Exécutez cx_freeze.

Comme par magie, tous les problèmes ont disparu et tout ce qui a été compilé comme cela était supposé.

Je sais que ce n’est probablement pas ce que vous voulez entendre, mais la réalité est que vous ne pourrez jamais réussir avec cette approche et voici pourquoi:

  • Linux ne dispose pas de fichiers binarys du package Python, ce qui signifie qu’un numéro compilé sur une dissortingbution ne fonctionnera probablement pas sur un autre. Cela peut même arriver avec la même dissortingbution et la même version, simplement parce qu’une bibliothèque système a reçu une mise à jour.
  • manylinux1 est supposé résoudre ce problème, mais il est vraiment difficile de créer des paquets pour cela et seuls quelques-uns ont commencé à l’utiliser.
  • Le projet cx-freeze avait la dernière version en décembre 2014, ce qui, à l’échelle de temps de Python, le place comme un projet abandonné.

Le problème que vous rencontrez peut être dû au manque de dépendances. cx_Freeze a des dépendances. Afin de dissortingbuer votre travail en python, de nombreux paquets légers sont disponibles. Vous pouvez utiliser:-

  1. Pyinstaller: il peut être installé par

    pip install pyinstaller pyinstaller est vraiment bon pour faire des exécutables avec moins de taille

  2. Py2exe