Resolves https://github.com/ppy/osu/discussions/36107.
The replay linked in the aforementioned discussion happens to contain
the magic sequence for ZIP headers in the binary stream (50 4b 05 06)
which led to it getting classified as a ZIP with no entries and
completely bogus everything in the header at
https://github.com/ppy/osu/blob/c8b18acd4dd1d98170a069240b6666cea3d5da07/osu.Game/Database/ImportTask.cs#L51-L56
and then finally dying of
2025-12-23 07:26:45 [error]: [?????] Model creation of replay-osu_2040232_4828629841.osr failed.
2025-12-23 07:26:45 [error]: System.InvalidOperationException: Sequence contains no matching element
2025-12-23 07:26:45 [error]: at System.Linq.ThrowHelper.ThrowNoMatchException()
2025-12-23 07:26:45 [error]: at System.Linq.Enumerable.First[TSource](IEnumerable`1 source, Func`2 predicate)
2025-12-23 07:26:45 [error]: at osu.Game.Scoring.ScoreImporter.CreateModel(ArchiveReader archive, ImportParameters parameters)
2025-12-23 07:26:45 [error]: at osu.Game.Database.RealmArchiveModelImporter`1.importFromArchive(ArchiveReader archive, ImportParameters parameters, CancellationToken cancellationToken)
at
https://github.com/ppy/osu/blob/554961036e23615b35eb6b66b341b10924664c4d/osu.Game/Scoring/ScoreImporter.cs#L46
A few facts of life:
- Guest difficulties are at this point a staple of mapping.
- People are very much used to flinging `.osu`s around (because there's
no better alternative).
- Currently there are two ways to get an `.osu` out of lazer. You can:
- Export the beatmap as "compatibility" to an `.osz`, then
transmogrify the `.osz` to a `.zip`, then extract the `.zip`, then
pluck out the `.osu`. This is the "correct" way to make sure stable
works, but is also stupidly arcane.
- Use "edit externally" to mount the beatmap files to disk, then
copy-paste out the `.osu`. This is the *wrong* way to make sure
stable works, because the mounting process exposes the raw "for
editing" format with features stable doesn't support, but it the
actual easy one.
- Reports about guest difficulties exported from lazer "working wrong on
stable" are prevalent. Probably mostly because of the preceding point.
What this PR does is introduce a *third* method to export an `.osu`,
which is designed to be both the easiest one yet *and* correct. I am
hoping this will curb the complaints until support for direct submission
of guest difficulties is added - which I still hope to see, but it will
be a significant effort *client-side* (the server side has been ready
for years now).
And yes, you will notice that much of the code added in
`LegacyBeatmapExporter` related to manipulation of the path is
copy-pasted from `LegacyExporter`. I don't care enough to invent
protected / abstract / whatever else OOP faff for something that may not
survive review and is mostly a weird semi-temporary wart.
In order of severity:
- You could actually click on the textbox portion of a disabled textbox,
focus it, select text, input stuff, and commit, which would die
on the spot.
- The slider part had no visual indication that it's not interactable
anymore.
Some are not immediately relevant to the stacking issue because they
fail both before and after it, just less so after the stacking issue
(half-)fix, and as such have been commented out for the time being.