Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Question] Adding wxPython #58

Closed
mantielero opened this issue Nov 19, 2022 · 4 comments
Closed

[Question] Adding wxPython #58

mantielero opened this issue Nov 19, 2022 · 4 comments

Comments

@mantielero
Copy link

I am trying to pack a piece of software using python2.7. I am struggling to get the dependencies properly.

I download python2.7:

wget https://github.com/niess/python-appimage/releases/download/python2.7/python2.7.18-cp27-cp27m-manylinux1_x86_64.AppImage
chmod +x python2.7.18-cp27-cp27m-manylinux1_x86_64.AppImage
./python2.7.18-cp27-cp27m-manylinux1_x86_64.AppImage  --appimage-extract

Then I install the dependencies:

usr/bin/pip2.7 install future zeroconf==0.19.1 numpy==1.16.5 matplotlib==2.0.2 lxml==4.6.2 pyro sslpsk pyserial

But I struggle to get wxPython given than only v4.x is available, while I need v3.0. I found it in Ubuntu. So I downloaded:

apt-get download python-wxgtk3.0
dpkg-deb -xv python-wxgtk3.0_3.0.2.0+dfsg-8build1_amd64.deb ./

Is there a way to get the extracted data from the .deb package integrated with the extracted data from python-appimage?

@niess
Copy link
Owner

niess commented Dec 5, 2022

Hello @mantielero,

sorry, I missed this post.

I understand that you need a wxPython version that is not available as a binary wheel on PyPI. But you found the corresponding binary in a .deb file. Is this correct?

If so, you could try to simply copy the wxPython package from the deb file to the AppImage site-packages directory, hoping that the two builds are binary compatible (?) You would also need to package any external libraries that are used by wxPython (you can check this e.g. with ldd or objdump -p).

Note, that the previous attempt is likely not to work straight out of the box :( Thus, it might actually be easier to rebuild wxPython from source and to bundle it in the AppImage.

@jeanslack
Copy link

Hello @niess

Thank you for developing this very useful project!
I saw this issue a few days.

I pip installed an ubuntu 18.04 specific wxPython wheel into python-appimage, which works in some Linux distributions but in others needs other libraries. I'm wondering how to include the following missing libraries required by wxPython inside a python-appimage:

strings squashfs-root/opt/python3.9/lib/python3.9/site-packages/wx/libwx_gtk3u_core-3.1.so.5 | grep "\.so."
libgtk-3.so.0
libgdk-3.so.0
libpangocairo-1.0.so.0
libpango-1.0.so.0
libcairo.so.2
libgdk_pixbuf-2.0.so.0
libgio-2.0.so.0
libgobject-2.0.so.0
libglib-2.0.so.0
libX11.so.6
libXxf86vm.so.1
libSM.so.6
libnotify.so.4
libXtst.so.6
libpangoft2-1.0.so.0
libfontconfig.so.1
libSDL2-2.0.so.0
libpng16.so.16
libjpeg.so.8
libtiff.so.5
libwx_baseu-3.1.so.5
libm.so.6
libstdc++.so.6
libgcc_s.so.1
libpthread.so.0
libc.so.6
libwx_gtk3u_core-3.1.so.5

Although not all of these libraries should be included inside appimage assuming that all target systems (Linux distributions) ship them by default.

I am also aware that getting a wxPython wheel compiled to run on only a few compatible Linux systems is a tough task, since there is no official wxPython manylinux wheel yet.

@niess
Copy link
Owner

niess commented Mar 29, 2023

Hello @jeanslack ,

in principle, extra system like libraries would be bundled under AppDir/usr/lib, where AppDir is the (extracted) AppImage root directory. Now, it actually depends on the pip installed binaries. I am assuming that your wxPython package ships with shared libraries (A.so), properly loaded by Python, but depending on (missing) system like libraries (B.so). Then, A.so would not be aware that B.so would be under AppDir/usr/lib.

A quick and dirty solution would be to modify the LD_LIBRARY_PATH at runtime by editing the AppImage entry point (AppDir/AppRun). For example you could add $APPDIR/usr/lib to it (assuming that B.so goes there), as

export LD_LIBRARY_PATH=$APPDIR/usr/lib:$LD_LIBRARY_PATH

(in AppDir/AppRun, right before calling Python.)

You could try this first as a quick hack. The inconvenience with this solution is that you are spamming the LD_LIBRARY_PATH env variable, which could have side effects. But, if your AppImage is not intended to be further re-used, then this could be very OK for your use case.

As for which B.so should be bundled or not, your link looks good to me. Clearly libc.so should not. It would not work actually. I would assume that libstdc++.so.6 should be excluded as well.

Concerning the first issue, i.e. locating B.so, I am discussing a more sophisticated solution below, which is used by python-appimage. First, you need to check the RPATH of A.so. For example, using objdump as

objdump -p A.so

(Look for the RUNPATH entry, in the output of objdump. It might be absent, which means that RPATH is empty)

The RPATH tells where to look for dependencies, i.e. B.so (like PATH for executable, etc.). There is a special keyword $ORIGIN which refers to the parent directory of A.so (see e.g. objdump -p AppDir/usr/lib/libcrypt.so.2). If the RPATH is empty (or not consistent with the AppImage layout), then you would need to edit it. This can be done with patchelf. Note that if you installed python-appimage, then you already have patchelf as well (see e.g. python-appimage which patchelf, or python-appimage install patchelf).

The RPATH can be edited as

patchelf --set-rpath '$ORIGIN/relative/path/to/where/B/is/located' A.so

(Note that you need to use relative paths in order that the application is relocatable. Otherwise, the re-built AppImage would not work.)

It might be that simply copying B.so aside of A.so works. You could try this first. I actually do not remember if $ORIGIN is by default in the search path for dependencies.

As a final word, indeed, making this work will likely be a tough task in this particular case :( Even if you properly set all RPATHs (a mandatory requirement, somehow), you might be stuck with conflictual dependencies issues at some point. But, if you are interested in these technicalities, this could be an instructive exercise :)

@jeanslack
Copy link

Your explanation was very helpful and instructive.
I'm already trying to do some testing using your directions and will see what's more convenient at this point.

Thank you very much!

@niess niess closed this as completed Apr 27, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants