MobDev.Plugin.RuntimeManifest (mob_dev v0.6.9)

Copy Markdown View Source

Builds the host's runtime plugin manifest — the device-readable record of the activated plugins' tier-3/4 contributions.

Tiers 3 and 4 are pure-Elixir and runtime-wired: the host needs to know, on device, which screens exist, what lifecycle/settings/notification declarations each plugin made — but MobDev.Plugin.activated/0 is compile-time only. So at build time this module gathers those sections (running any spec-v2 :screens_generator under the host-config audit) and emits a terms file (priv/generated/mob_plugins.exs) that the core Mob.Plugins module reads at boot. It mirrors the driver_tab / MobPluginBootstrap codegen pattern, but for serializable Elixir data instead of native symbols.

Only the behavioral data lives here. Migration files and font/image assets are physically copied into the host at build time (see native_build), not carried in this manifest.

Everything emitted must be serializable terms — atoms, tuples, maps, strings, integers. The manifest validator forbids closures in plugin sections so this always holds.

Summary

Functions

Builds the merged runtime manifest map from {plugin_dir, manifest} pairs.

Renders the manifest map to the contents of priv/generated/mob_plugins.exs — a self-describing .exs that evaluates back to the map.

Validates a :screens_generator's output, raising on malformed specs.

Writes the rendered manifest to <host_root>/priv/generated/mob_plugins.exs and returns the path.

Functions

build(plugins)

@spec build([{Path.t(), map() | nil}]) :: map()

Builds the merged runtime manifest map from {plugin_dir, manifest} pairs.

Static :screens and spec-v2 :screens_generator output are combined (each tagged with its plugin); generators run under MobDev.Plugin.with_host_config_audit/3 so an undeclared host-config read fails the build.

render(manifest)

@spec render(map()) :: String.t()

Renders the manifest map to the contents of priv/generated/mob_plugins.exs — a self-describing .exs that evaluates back to the map.

validate_generated_screens(screens, plugin_name)

@spec validate_generated_screens(term(), atom() | nil) :: [map()]

Validates a :screens_generator's output, raising on malformed specs.

A generator must return a list of %{module: atom, default_route: binary} maps (a bare map is wrapped). This mirrors MobDev.Plugin.Manifest's static :screens validation so generator-produced screens are held to the same shape contract — otherwise a typo'd or wrong-typed spec would be written into mob_plugins.exs and silently dropped at boot (Mob.Plugins.register_screens/0 pattern-matches %{module:, default_route:} and skips non-matching maps), making the plugin's screen vanish with no build-time error.

Returns the validated screen list (without the :plugin tag, which the caller adds). Public for testing.

write(host_root, manifest)

@spec write(Path.t(), map()) :: Path.t()

Writes the rendered manifest to <host_root>/priv/generated/mob_plugins.exs and returns the path.