picke est un module python qui permet de sérialiser les données d'une classe dans un fichier. Par exemple (dans un shell IPython):

In [1]:a = "abc"

In [2]:import pickle

In [3]:pickle.dump(a, file("out.dump", "w"))
In [4]:!cat out.dump
S'abc'
p0
.
In [5]:b = pickle.load(file("out.dump", "r"))

In [6]:b
Out[6]:'abc'

C'est très pratique pour coder efficacement avec Python mais dans le cas qui m'intéresse, ça ne résoud pas la problématique principale : n'obtenir qu'un seul .exe.

Remarque : Pour utiliser pickle, regardez le module StringIO, ça permet d'avoir des objets de type String se comportant comme des fichiers, pratique !

Une petite optimisation avc la zlib

Le code initial n'utilisait que l'encodage en base64. Pourtant, il n'y a rien de plus simple que d'ajouter un encodage (compression) avec la zlib !

import os
import sys
import getopt

__doc__ = """
convert file into an importable module

data2py.py toto.dat >toto.py

extract from python  :

import toto
f = file("toto.dat", "wb")
f.write(toto.data.decode("base64").decode("zlib"))
"""
def main(args):
    if not args or ("-h" in args):
        print __doc__
        return

    try:
        opts, fileArgs = getopt.getopt(args, "")
    except getopt.GetoptError:
        print __doc__
        return

    f = file(fileArgs[0], "rb")
    buff = f.read()
    print "data = %s%s%s" % ('"""', buff.encode("zlib").encode("base64"), '"""')

if __name__ == "__main__":
    main(sys.argv[1:])

Et avec PyInstaller ?

Avec PyInstaller, il est possible d'inclure des fichiers directement depuis le fichier .spec PyInstaller, il suffit de regarder la documentation associée (le logiciel est repris depuis peu, il vaut largement py2exe !).