Skip to content

SP-11: plugins parity — PluginState/Descriptor + per-plugin lifecycle cascade (v26.06.91)#119

Merged
ancongui merged 6 commits into
mainfrom
worktree-parity-sp11-plugins
Jun 9, 2026
Merged

SP-11: plugins parity — PluginState/Descriptor + per-plugin lifecycle cascade (v26.06.91)#119
ancongui merged 6 commits into
mainfrom
worktree-parity-sp11-plugins

Conversation

@ancongui

@ancongui ancongui commented Jun 9, 2026

Copy link
Copy Markdown
Contributor

Summary

Eleventh sub-project of the PyFly↔Spring-Boot parity initiative — the plugin system.

  • State model: PluginState (LOADED/STARTED/STOPPED/FAILED) + per-plugin PluginDescriptor.
  • Per-plugin lifecycle: start_plugin(id) (dependency cascade — deps first), stop_plugin(id) (reverse cascade — dependents first), get_plugin(id); FAILED + typed PluginStartError/PluginStopError on hook failure.
  • Exception hierarchy: PluginException(PyFlyException) + Load/Start/Stop/State errors; add() raises PluginLoadError.
  • ExtensionRegistry.get_extension(point) single-getter; @plugin(name=, author=) (backward-compatible).
  • E2E multi-plugin lifecycle test + auto-config test + docs.

Test Plan

  • ruff / format / mypy --strict clean (667 src files).
  • Fast suite: 4523 passed, 7 skipped, 45 deselected.
  • 34 plugins tests incl. e2e 3-plugin cascade + the review-fix regressions.
  • Review: CHANGES REQUESTED → both Important issues fixed (PluginLoadError, start_all skip).
  • Backward-compatible (existing @plugin(id=...) + tests pass).
  • CI lint/typecheck/test/build pass on this PR.

Andrés Contreras Guillén added 6 commits June 10, 2026 01:43
…PluginError hierarchy

- New models.py: PluginState (StrEnum) with LOADED/STARTED/STOPPED/FAILED;
  PluginDescriptor mutable dataclass tracking per-plugin runtime state
- decorators.py: Plugin dataclass gains optional name/author fields;
  @plugin decorator gains matching kw-args; name defaults to id
- exceptions.py + kernel/__init__: PluginException base + PluginLoadError,
  PluginStartError, PluginStopError, PluginStateError subclasses
- resolver.py: PluginResolutionError now extends PluginException
…/get_plugin with cascade

- registry.py: get_extension() returns single highest-priority extension;
  raises ValueError if point not registered or has no extensions
- manager.py: track _descriptors dict[str, PluginDescriptor]; _transition()
  helper for state changes; start_plugin() cascades transitive deps in topo
  order, skips STARTED; stop_plugin() cascades transitive dependents in
  reverse order, skips STOPPED/LOADED; get_plugin() returns descriptor or None;
  start_all/stop_all wire state transitions; remove() drops descriptor
- plugins/__init__.py: re-export PluginDescriptor, PluginState
- test_plugin_lifecycle.py: 14 tests covering start_plugin cascade (A←B←C),
  skip-already-started, stop_plugin reverse cascade, get_extension happy/error
  paths, FAILED state on hook error, get_plugin none/descriptor, name/author
  in descriptor, start_all/stop_all state marking
- test_plugins_auto_configuration.py: 7 tests verifying PluginsAutoConfiguration
  markers, on_property condition key, bean factory types and registry identity
…de, PluginError, get_extension)

Documents: PluginState/PluginDescriptor fields and transitions; @plugin name/author
optional fields with backward-compat note; per-plugin start_plugin/stop_plugin/
get_plugin with cascade semantics; PluginError hierarchy tree; get_extension
single-getter; PluginsAutoConfiguration conditional activation and bean table
…ptor, per-plugin lifecycle cascade, PluginError, get_extension)
@ancongui ancongui merged commit 1bbdab2 into main Jun 9, 2026
5 checks passed
@ancongui ancongui deleted the worktree-parity-sp11-plugins branch June 9, 2026 23:54
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