Repository navigation
feat(builder): hand a 2.x install over to the Hookshot Launcher - #2722
hckrman101 wants to merge 2 commits into
Conversation
docs/launcher-upgrade.md is the contract between a 2.2/2.3 Builder that hands an install over to the Hookshot Launcher (3.0) and the launcher that takes it: how a launcher release is told from a Builder release (hookshot-launcher.txt, never the version name), where the launcher is installed and how it is swapped in whole, the import file dropped for the game folder, what changes in the folder's stamp, and the bridge that brings Builders older than 2.2 to the same screen in one update. tests/fixtures/launcher/ holds sample files that both sides test against, so the upgrader and the launcher read and write the same thing.
The 2.x Builder, on Windows and Linux, now asks whether the release it would update to ships the launcher (hookshot-launcher.txt, docs/launcher-upgrade.md). When it does, Update becomes Upgrade: a screen says what will happen, and Upgrade downloads the launcher, checks its size and SHA-256, installs it whole into the launcher home, drops the import file, points the folder's stamp at it, starts it with --launch and closes. Without this, a 2.x player has no way from the Builder to 3.0. - An installed launcher gets --launch and --update from the Builder (not from a portable Windows Builder). - Windows swaps the unpacked app in by renames, so a failure or a running launcher never leaves half of one; it asks to close a running launcher first. - The bridge (section 5): a Builder without its build tools opens on the hand-over screen (AppRun on Linux, Tools.Find() on Windows). - host/hos_update.c on Linux starts an installed launcher before the 2.x Builder. - Tests: tests/test_linux_upgrade.py, tests/test_builder_upgrade.py (+ .cs fixture), both against tests/fixtures/launcher/; no network, no game.
|
Thanks for writing this as a contract with shared sample files. It made it easy to build the other side against. I've integrated it with the standalone launcher I've been working on for 3.0 (Avalonia, Windows and Linux), and ran both sides together. Branch: https://github.com/madebyjordan/Longshot/tree/launcher/avalonia The launcher side now meets
One difference to discuss: the launcher keeps its builds in the Builder's home ( Tested end to end
Two things I found in this PR
Overlap with #2373: this PR conflicts with #2373 in |
Hookshot 3 replaces the Builder with a new launcher, and a player on 2.x has no way to get there from the Builder they already have. With this PR, the 2.2/2.3 Builder offers the move when a release ships the launcher: one click installs it and hands the game folder over, with the player's build settings.
This is the second of three PRs: #2733 (nightly naming), then this one, then the launcher itself (#2739). It doesn't depend on the launcher's code. The two sides agree through a written contract (
docs/launcher-upgrade.md) and sample files that both test against.What changed
The contract (
docs/launcher-upgrade.md,tests/fixtures/launcher/):hookshot-launcher.txt, with the launcher's SHA-256, size and https link for each platform. A 404 means a Builder release, which updates as it does today. The version name is never used to decide, so the nightly renaming tonightly-<count>-<sha8>doesn't affect it. A tag is only used to find its release (release_of, the same rule the updater uses).%LOCALAPPDATA%\HookshotLauncher,~/.local/share/hookshot/launcher), and how it is installed whole.hookshot_version.txt: onlybuilder=.builder_args=goes, and a portable folder (builder_local=1) is left alone.The upgrader (
builder/HookshotBuilder/Upgrader.cs,builder/linux/linux_upgrade.py, and the two Builder windows):app.partand swaps it in by renames. Zip entries that would land outsideapp.partare refused. The oldappis renamed aside rather than deleted, so a file in use can't leave half a launcher behind.Hookshot.AppImage.partand renames it over the old file.--launch <folder>, and closes.--launchand--updateon to it. A portable Windows Builder doesn't. This means the game folder's own launcher and the game's update offer keep working.host/hos_update.cprefers an installed launcher over the installed 2.x Builder.AppRunon Linux,Tools.Find()on Windows).hookshot_builder.py --handover, used internally byAppRun.docs/versioning.mddescribes the upgrade.Failure handling:
.partfile is left behind.How it was tested
tests/test_linux_upgrade.py(30 tests) covers:AppRunbridge, run with a fake AppDirbegin_update,apply_modeandmain, compiled from source with no Tkhos_update.c'sinstalled_launcher, compiled withcctests/test_builder_upgrade.pycompiles the realUpgrader.cs,Updater.cs,BuilderSettings.cs,BuilderHome.csandStrings.cswith a fake window (52 checks). It covers:../entry, a zip withoutHookshotLauncher.exe, a cancelled install, and a replacement that leaves no stale filespython -I -B tests/run_all.pyon Linux: 423 passed, 67 skipped, 3 failed.test_bake_portabilityandtest_builder_log_read_onlyneedzstandardandlibtk, which this PC doesn't have.test_release_scriptshit a timing failure in its two-runs-at-once nightly case under the parallel run. It passes on its own, and this PR doesn't touch the release scripts.What was not tested
MainWindow.xaml.cs's mode logic, the running-launcher check and the rename swap with real file locks are untested.Upgrader.cswas built and checked on Linux with the .NET 10 SDK, not on Windows with .NET 8.libtk. The Linux hand-over screen, its Cancel button and the error screen were only exercised as functions compiled from the source.hookshot-launcher.txtyet, and the launcher is the next PR.Screenshots: none. Neither the WPF nor the Tk hand-over screen could be run on this PC, so there's nothing real to show yet. I'll add them once the screens run on Windows and on a Linux setup with Tk.
Follow-ups
%LOCALAPPDATA%rather than beside it. The folder's stamp is left alone, and the portable Builder no longer forwards to the launcher, so nothing breaks. A portable launcher home would be its own change.hookshot-launcher.txtand the bridge payloads described in section 5 of the contract. That belongs with the launcher's release.