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
AppImage support #8019
Comments
Don't put too much thought into integrating anything with the build system, it's being replaced with CMake soon. |
Maybe the AppImage creation should be revisited once the project has been migrated to the new CMake based build system, just to avoid double work. |
Hello folks! |
The CMake transition was committed a while ago, in commit 56d54cf (and has been fixed-up in various ways since). Thank you for the offer of help! It might be best if you join the IRC channel -- #openttd on irc.oftc.net , most active in EU evenings/weekends -- to discuss it. Or stick with GitHub comments, that works too. :-) |
I was a bit lazy to compile OpenTTD from sources, instead I used the latest binary you publish to build this AppImage. Nevertheless the recipe should work if you build it from sources and install it into an AppDir. If you help me setup a workflow for the build, I could add the AppImage packaging bit 😃 Here is the link to my project: https://github.com/azubieta/openttd-appimage |
Note on the appiamge-builder usage: Patching the deployed files is not supported yet, therefore we must split it's execution and patch it manually. This feature can be tracked at: AppImageCrafters/appimage-builder#50
Note on the appiamge-builder usage: Patching the deployed files is not supported yet, therefore we must split it's execution and patch it manually. This feature can be tracked at: AppImageCrafters/appimage-builder#50
OpenTTD won't supply AppImage for now; but other awesome people in the community are supplying it: https://www.appimagehub.com/p/1425360/ ! See #8329 why we are not supplying it ourselves for now. What we do have these days, is a Both combined should address this issue, I believe :) So going to close it for now, but let me know if there is anything else to this issue! :) |
Version of OpenTTD: 1.9.3
Expected result: Ability to drop a single binary for friends/coworkers in UNIX environment to be able to play together in ad-hoc LAN games without obligatory ceremony of installing/building.
Actual result: Right now you have to use your package manager in OS which pulls plenty of dependencies, or even build the source if your PM provides old or even no version of OpenTTD. This might increase the latency between idea and playback or even create a serious annoyance for Windows/Mac users yelling at UNIX environment or userbase.
Possible Solution
Use AppImage. It's a specification (not a "package manager" or "daemon" or anything) which allows to build standalone, system-independent executables that run on every modern Linux system.
Compared to snap/flatpak it doesn't enforce any 3rd-party tooling on destination machine, and can be considered like Mac DMGs or Windows ("portable") EXEs.
Under the hood it's just a SquashFS loopback filesystem with specified contents wrapped into ELF binary with actual code on top which mounts the FS as unprivileged user and spawn the application in it. It doesn't provide sandboxing (can be done with firejail on demand) in terms of security, just bundles everything what game/application needs in a single binary, thus being quite ideal for OSS games or "larger" self-contained applications like LibreOffice, Krita, and so on. Definitely not a thing for CLI apps, system tools and utiltiies (but no one prevents anyone from building these and they'll work just fine)
Steps to reproduce
At first I wanted to create a Pull Request for that, adding AppImage as a "bundle" (in
Makefile.bundle.in
) but I found the OpenTTD's build system quite complicated (maybe overcomplicated with that infamous GNU Autotools orchestra). So even if I can rip it out and inject my own inventions here and there, it would be a bit rude and unrespectful to do that.Instead, I'd like to share the steps which I manually did to achieve working AppImage add my thoughts on it and how OpenTTD behaves:
1.1. I've done that in Docker (Podman) container, but bare-metal, CI, chroot or VM will do.
1.2. For reference, you can recreate the same environment in Docker using the following:
/openttd
dir, checked out to 1.9.3 tagmake -j8
to build the game.8.1. The release binary is an AppImage itself, so you can
curl
orwget
it in CI pipeline and use it right there8.2. The only thing
linuxdeploy
does in the actualopenttd
binary isRPATH
to make it look for shared libraries in AppDir first, which is the probably the only "trick" making the AppImages work. Dead simple and quite elegant.8.3. I call
linuxdeploy
like this:# "VERSION" is needed to indicate a version of software we build, in other cases it'll use a git/hg/cvs hash and store it in target filename and metadata (optional) VERSION=1.9.3 ./bin/linuxdeploy--appdir appdir/ --output appimage
linuxdeploy
simply callsldd
onopenttd
, copies required*.so
s for it into AppDir (with some exclusions, more on it later), finds*.desktop
file in AppDir to lookup metadata and icon, packs that into SquashFS+payload and… its done!9.1. In CIs without
fuse
, you can runlinuxdeploy
(and other AppImages) via./linuxdeploy --appimage-extract-and-run
TL;DR version
Issues I found
These are mostly cosmetic or formal ones, which can probably be addressed more officialy by someone not being dumb as me right now:
openttd
will fail with error about missing languages.strace
shows it also misses all data in from its basedir.openttd
will look up its data in$PWD
or global directory (/usr/share
) or local user dirs. AppImage does not fake or remap directories in running process andopenttd
can't figure out it has all its data stored in/tmp/.mount_<appimage_name>_<random uuid>/usr/share/games/openttd
.linuxdeploy
symlinkedopenttd
asAppRun
which is the default entrypoint for AppImage. It's nice, but it don't need to be like that, the AppRun can be a script to so we don't need to fake binary paths, just use this asAppRun
:I had to bundle OpenGFX/OpenMSX/OpenSFX inside the AppImage (in
$APPDIR/usr/share/games/openttd
)firejail
, but should be invoked by user explicitly<appimage filename without extension>.home
in your $PWD or AppImage folder, it's being used as a$HOME
environment variable. Simple and elegant solution.<appimage filename>.config
, which is used as$XDG_CONFIG_HOME
and that's why I usedlibxdg-basedir
in build systemI had issues with ICU libraries ABI change:
linuxdeploy
excludes thelibicu*.so
from integration into AppDir by default, explaining that's a "too internal" system library and it's not often directly called--static-icu
option which I tried to use, but Ubuntu LTS doesn't havelibsicu*.a
libs available. It has, however,libicu*.a
static libs in itslibicu-dev
packages, so I assume it's just matter of linker configuration and some Autotools magiclinuxdeploy
to bundle these libs with you, and resulting AppImage has been proven working for us on a small network game this evening. For reference, you can call it like that:# you don't need to address .so.XX.y directly, linuxdeploy is a little smarter about symlinks and ABIs ./linuxdeploy \ --appdir appimage/ \ -output appimage \ --library /usr/lib/x86_64-linux-gnu/libiculx.so \ --library /usr/lib/x86_64-linux-gnu/libicutu.so \ --library /usr/lib/x86_64-linux-gnu/libicuuc.so \ --library /usr/lib/x86_64-linux-gnu/libicuio.so \ --library /usr/lib/x86_64-linux-gnu/libicui18n.so \ --library /usr/lib/x86_64-linux-gnu/libicudata.so \ --library /usr/lib/x86_64-linux-gnu/libicu-le-hb.so
Why I'm doing this here, instead of maintaining it on my own?
AppImages are meant to be done by upstream. Why?
appimaged
, which is optional but handy in a fleet of AppImageslibappimage
library if you're so kind to support that. The library can also determine if you're running in AppImage or not, so you can use other search paths for baseset.A little disclaimer
If you find this like forcing or advertising a new technology, it's not. I'm not affiliated in @probonopd or AppImage project in any way. The whole reasoning is that I wanted to quickly share an OpenTTD build for many different platforms and make it as most easy as possible, without polluting the host system. It worked pretty well and I've been looking forward to integrate such distribution form to other users.
P.S.: Dedicated server build can be done that way too, making them deployable in seconds.
P.P.S: Just stumbled upon the fact that your "cousin project" OpenRCT2, already does this and shares the AppImage build on their downloads page which is cool.
The text was updated successfully, but these errors were encountered: