Skip to content

feat(plugin): linux { flathub { } } and generateFlathubRepository - #900

Merged
kdroidFilter merged 4 commits into
nucleus-3.0from
feat/flathub-dsl
Nov 2, 2026
Merged

kdroidFilter merged 4 commits into
nucleus-3.0from
feat/flathub-dsl

Conversation

@kdroidFilter

Copy link
Copy Markdown
Collaborator

What

A plugin DSL that writes the Flathub repository of any Nucleus app (github.com/flathub/<appId>), for apps that Flathub repackages from their released Linux tar.gz. Flathub builds nothing from source in that setup, which is the path a closed-source app takes. The Lab used a hand-written template and script for this; it now uses the DSL.

linux {
    flathub {
        appId = "com.example.App"
        summary = "Edit example documents"
        projectLicense = "LicenseRef-proprietary"
        archiveUrl = "https://example.com/releases/{version}/app-{version}-linux-{arch}.tar.gz"
        screenshot("https://example.com/shots/main.png", "The main window")
    }
}

./gradlew generateFlathubRepository writes build/flathub/<appId>/:

  • the manifest;
  • the AppStream metainfo;
  • the desktop entry;
  • the icon;
  • the shared-mime-info XML;
  • flathub.json, only when the app targets a subset of architectures.

flathub { } only holds what Flathub alone needs. The other values come from the rest of the DSL:

  • name, description, vendor, homepage and categories;
  • the icon;
  • fileAssociation, which gives the MIME types;
  • protocol, which gives x-scheme-handler;
  • the version, from packageVersion;
  • the executable, from the GraalVM image name (bin/<packageName> for a jpackage build).

This is independent of flatpak { }, which builds a .flatpak bundle that Flathub does not accept.

  • Sources: each archive is downloaded once from archiveUrl ({version}, {arch} → x64 / arm64) to compute its sha256. With -Pnucleus.flathub.localArchive=<tar.gz>, the task uses that file instead, for the local repository loop.
  • Checks before writing: the task reports every issue Flathub would reject in one go: reverse-DNS app id, a summary of at most 35 characters without a trailing period, description, license, developer, categories, at least one screenshot, #rrggbb branding colors, and a square PNG icon of 256 px or more.

Verification

  • The Lab, generated from release v3.0.0-dev-202611011507, gives the same sha256 values as the hand-written script, and its content is identical apart from formatting.
  • The generated repository passes flathub-build, flatpak-builder-lint on both manifest and repo, appstreamcli validate and desktop-file-validate.
  • FlathubRepositoryTest has 10 tests. ktlint passes. detekt reports nothing in the new code; the plugin's existing detekt findings are unchanged.

docs/internals/flathub.md documents the DSL, the local loop and linting.

Writes the Flathub repository of an app (github.com/flathub/<appId>)
from its DSL: a manifest that repackages the released Linux tar.gz, the
AppStream metainfo, the desktop entry, the icon, the shared-mime-info
XML and, for a subset of architectures, flathub.json. flathub { } only
holds what Flathub alone needs; name, description, vendor, homepage,
categories, icon, file associations and URL protocols come from the rest
of the DSL, the executable from the GraalVM image name.

Archives are hashed from archiveUrl ({version}, {arch}), or taken from
-Pnucleus.flathub.localArchive for the local repository loop. The task
fails with everything Flathub would reject before writing anything.

The Lab now uses it instead of its hand-written template and script; its
output matches theirs and passes flathub-build and flatpak-builder-lint.
generateFlathubRepository can now write into a clone of
github.com/flathub/<appId> (flathub { outputDir }, or
-Pnucleus.flathub.outputDir for one run). It no longer wipes its output
directory: it replaces only the files it writes and removes flathub.json
or the MIME file when they no longer apply, so the clone's .git and
files of its own are left alone.
Flathub's stable remote refuses a release version containing alpha,
beta, rc, pre or dev (appstream-latest-release-is-prerelease, never
granted an exception), which the new-submission CI enforces. The store
version can now differ from the package version, which the archive URL
keeps using, and generateFlathubRepository refuses a pre-release one
with the same regex as the linter. The Lab publishes a dev build under
the date of its tag (v3.0.0-dev-202611011507 -> 2026.11.01).
…put directory

With outputDir pointing at a clone of the Flathub repository, Gradle
fingerprinted the whole clone, Flatpak build directories included, whose
var/run links to /run: the task failed on an unreadable
/run/snapd/ns/prompting-client.mnt. The task is now untracked; it only
writes a few small files and always runs.
@kdroidFilter
kdroidFilter merged commit d975bba into nucleus-3.0 Nov 2, 2026
16 of 17 checks passed
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

Successfully merging this pull request may close these issues.

1 participant