Skip to content

Feature: run each plugin in its own subprocess with skip/abort on Ctrl+C - #1019

Open
Abu-Huraira21 wants to merge 3 commits into
abrignoni:mainfrom
Abu-Huraira21:feature/mp-per-plugin
Open

Feature: run each plugin in its own subprocess with skip/abort on Ctrl+C#1019
Abu-Huraira21 wants to merge 3 commits into
abrignoni:mainfrom
Abu-Huraira21:feature/mp-per-plugin

Conversation

@Abu-Huraira21

Copy link
Copy Markdown

Summary

Adds a --mp_per_plugin / --mp flag that runs each plugin in an isolated subprocess instead of
in-process. Solves a common pain point during triage: a single slow/hung plugin currently forces you to
kill the whole run (losing all progress) since there's no way to skip past it.

Behavior

  • First Ctrl+C during a plugin: terminates that plugin's subprocess only, run continues to the next
    plugin.
  • Second Ctrl+C within 5s: aborts the run after the current plugin.
  • SIGUSR1/SIGUSR2 work as alternate skip triggers (useful when SIGINT is awkward to send, e.g. under
    sudo).
  • Debounces duplicate SIGINT delivery from sudo, which sends SIGINT to the whole process group and can
    otherwise double-fire the handler.
  • Default behavior (no flag) is unchanged — same in-process execution as today.

How it works

  • Each subprocess reconstructs a minimal PluginLoader, a lightweight SeekerProxy (parent has already
    resolved files_found, so no re-searching needed), and re-opens the existing LAVA sqlite DB.
  • Only picklable deltas cross the multiprocessing.Queue back to the parent: icons_delta,
    lava_artifacts_delta, and meta_modules_delta (per-module metadata for _lava_data.lava). No plugin state
    itself is shared.
  • Parent merges these deltas after each subprocess returns.

Testing

Verified against a full local extraction run (625 plugins, --mp_per_plugin) — output (_lava_data.lava,
HTML/TSV reports, LAVA sqlite) matches an in-process run byte-for-byte aside from ordering-independent
fields. Also exercised the skip/abort paths manually via Ctrl+C mid-run.

Abu-Huraira21 and others added 3 commits August 3, 2026 13:06
Adds --mp_per_plugin/--mp flag. Each plugin runs in a spawned
subprocess; first Ctrl+C terminates just that plugin and continues,
a second within 5s aborts the run. SIGUSR1/SIGUSR2 act as alternate
skip triggers. Parent merges icons/LAVA-artifact deltas back after
each subprocess completes.

Rebased onto upstream's _HTML/_Script_Logs output layout and
lava_db_name-based db path.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Upstream renamed report_folder_base -> output_folder_base; the
mp_per_plugin subprocess payload still referenced the old attribute,
crashing on the first plugin.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Two mp_per_plugin-only bugs found via log diff between an --mp run
and a plain run:

- lava_open_existing() built lava_data without the 'meta' key, so
  lava_process_artifact()'s lava_data['meta']['modules'] access
  raised KeyError: 'meta' for every plugin.

- Context.set_output_params() only ran once in the parent at startup;
  a spawned subprocess is a fresh interpreter, so any plugin calling
  Context.get_output_params() (mister_skinnylegs plugins, media
  linking helpers) raised "Context not set. OutputParameters not
  available." Now set per-subprocess from the known output folder
  layout.

Also wire meta_modules_delta through the result queue and merge it
in the parent, mirroring the existing icons/lava_artifacts delta
pattern — otherwise the final _lava_data.lava's meta.modules would
end up empty under --mp, since every plugin runs in an isolated
subprocess.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
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