Skip to content

Add 'devproxy plugin list' command. Closes #2056 - #2110

Open
waldekmastykarz wants to merge 4 commits into
dotnet:mainfrom
waldekmastykarz:list-plugins-command
Open

waldekmastykarz wants to merge 4 commits into
dotnet:mainfrom
waldekmastykarz:list-plugins-command

Conversation

@waldekmastykarz

Copy link
Copy Markdown
Collaborator

Closes #2056

Adds a devproxy plugin list command that lists the plugins available in a plugin assembly, so users and agents don't have to resort to reflection or scanning DLL bytes to discover plugin names.

devproxy plugin list                                # built-in plugins
devproxy plugin list --output json                  # machine-readable
devproxy plugin list --plugin-path ./MyPlugins.dll  # custom plugin assembly

Sample output:

Plugins in /…/plugins/DevProxy.Plugins.dll:

  ApiCenterMinimalPermissionsPlugin (configurable)
  ...
  RetryAfterPlugin
  ...

To use a plugin, add it to the plugins array in your config with "name": "<plugin name>" and "pluginPath": "~appFolder/plugins/DevProxy.Plugins.dll".

JSON output returns name, pluginPath (ready to paste into config) and isConfigurable for each plugin.

Notes

  • The command runs standalone (handled early in Program.cs, like config validate), so it works without a valid config file and doesn't load configured plugins. Without this, any command fails when the config has issues, which is exactly when you'd want to look up plugin names.
  • It's still registered on the root command so it shows up in devproxy --help.
  • Plugin discovery matches the runtime loader: public, non-abstract types implementing IPlugin, loaded via PluginLoadContext. IsConfigurablePlugin was made internal to reuse it.
  • Updated the plugin catalog skill reference to mention the command.

Lists the plugins available in a plugin assembly (defaults to the
built-in DevProxy.Plugins.dll) so that users and agents no longer need
to resort to reflection to discover plugin names. Supports
--output json and --plugin-path, and runs without a config file.

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
@waldekmastykarz
waldekmastykarz requested a review from a team as a code owner November 13, 2026 11:54
Copilot AI balanced review requested due to automatic review settings November 13, 2026 11:54

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

Plugin listing has unresolved path-resolution and JSON-escaping bugs, while global-option handling can trigger unwanted configuration-dependent startup or reject supported invocations.

4 open issues
What changed in this PR

Adds devproxy plugin list to discover built-in and custom plugins without reflection scripts, addressing #2056. The command uses the existing plugin-loading infrastructure and runs independently of configuration loading.

Changes:

  • Adds text and JSON output with plugin names, paths, and configurability.
  • Registers the command in root help and adds standalone startup handling.
  • Adds discovery and output tests, and documents the command.
File Description
skills/​dev-proxy/​references/​plugin-catalog.md Documents plugin discovery commands.
DevProxy/​Program.cs Routes plugin commands through standalone handling.
DevProxy/​Plugins/​PluginServiceExtensions.cs Exposes configurability detection for reuse.
DevProxy/​Commands/​PluginCommand.cs Implements discovery, output formatting, and standalone parsing.
DevProxy/​Commands/​DevProxyCommand.cs Registers and detects the plugin command.
DevProxy.Tests/​PluginCommandTests.cs Tests filtering, configurability, missing assemblies, and output.

Review effort: Balanced

Comment thread DevProxy/Commands/DevProxyCommand.cs Resolved
Comment thread DevProxy/Commands/PluginCommand.cs Resolved
Comment thread DevProxy/Commands/PluginCommand.cs Resolved
Comment thread DevProxy/Commands/PluginCommand.cs Resolved
- Detect plugin command when --output/--no-color precede it
- Support --no-color on the standalone plugin command
- Report relative plugin paths as absolute paths
- JSON-escape the plugin path in the usage hint

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🔵 Needs a closer look

Custom-assembly discovery can report success with unloadable partial results and advertise open generic plugins that the runtime cannot instantiate.

No open issues 🎉

2 previously missed issues

In code that hasn't changed since last review

Medium severity Fail plugin listing when assembly type loading is incomplete

DevProxy/​Commands/​PluginCommand.cs:164

When a custom assembly has a missing type dependency, this silently returns a partial list (or an empty list) with exit code 0. However, the runtime loader calls assembly.GetTypes() without this fallback in PluginServiceExtensions.cs:156, so even the plugins listed here cannot be registered from that assembly. Report the loader exceptions and return a failure instead of presenting the partial result as usable plugins.

Medium severity Exclude open generic types from plugin discovery

DevProxy/​Commands/​PluginCommand.cs:168

This filter also includes open generic plugin classes, such as a public, non-abstract CustomPlugin<T> : BasePlugin. Their names appear as CustomPlugin followed by a backtick and generic arity, but the runtime's ActivatorUtilities.CreateInstance cannot instantiate a type containing generic parameters. Exclude these types so custom-assembly output only advertises plugins that can be instantiated.

4 resolved since last review

Review effort: Balanced

- Fail when assembly types can't be loaded instead of listing partial results
- Exclude open generic plugin types

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
@waldekmastykarz

Copy link
Copy Markdown
Collaborator Author

Addressed the two previously missed issues from the last review:

  • Plugin listing now fails (exit 1, loader messages on stderr) on ReflectionTypeLoadException instead of returning partial results, matching the runtime loader.
  • Open generic types are excluded from discovery (with a test).

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🟡 Changes recommended

Plugin discovery can silently succeed with incomplete or runtime-unloadable results when dependencies are missing, and it rejects valid backslash-separated plugin paths on Linux/macOS.

2 open issues

Review effort: Balanced

Comment thread DevProxy/Commands/PluginCommand.cs Resolved
Comment thread DevProxy/Commands/PluginCommand.cs Resolved
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🔵 Needs a closer look

Human assessment is needed because regression tests do not exercise standalone command execution or on-disk plugin loading, leaving configuration independence and plugin discovery unverified.

No open issues 🎉

2 resolved since last review

Review effort: Balanced

This branch has not been deployed

No deployments
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.

Consider adding a command to list available plugins

2 participants