Skip to content

Refuse a plugin route whose permission key nobody declared #362

Description

@BechsteinDigital

Follows #345, which is otherwise done: a plugin declares its permission keys in registry.json (#360), and those keys appear in the inventory an operator grants from (#361). A plugin that declares correctly is fully usable.

What is left is the plugin that does not declare correctly.

The remaining case

A route requiring a key that is neither a host key nor declared by its plugin:

[CalloraRoute("POST", "/dialer/campaigns", Permission = "communication.trunk.updat")]
//                                                                            ^ typo

The manifest is valid, the plugin installs and activates, the route is served — and answers 403 forever. Nothing says why. It is the original defect of #345 in miniature, surviving as a typo.

The information to catch it exists at both ends: PluginApiEndpointDataSource.BuildEndpoints sees route.Permission and owned.PluginId; PluginDeclaredPermissionCatalog knows what that plugin declared.

Why it was not done with the rest

BuildEndpoints is synchronous and has no service scope; the catalog reads manifests asynchronously. Bridging that is a design decision of its own — an eagerly-populated runtime registry (as RuntimeCapabilityRegistry does), or a check moved into activation where the lifecycle already has both — and it does not block anything, which is why it was cut rather than rushed.

Proposal

Refuse the route rather than failing the install. BuildEndpoints already does exactly this for reserved-prefix collisions:

logger.LogWarning(
    "Rejected plugin route {Method} {Path} on {ControllerType}: it collides with a reserved host route namespace.");

Follow that. An install-time failure would take down an otherwise working plugin over one mistyped route, and leave an operator with no move except uninstalling it. A refused route with a named reason is repairable and costs only the broken part.

Done when

  • A plugin route requiring an undeclared, non-host key is not registered, and the log names the route, the key and the plugin
  • A route requiring a declared key is registered; a test pins both directions
  • A route requiring a host key is still registered — plugins legitimately reuse host keys such as plugin.execute
  • The mechanism that makes declarations available to BuildEndpoints is documented where the next person will look for it

Not in scope

Anything about granting. That works — see #361.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    .NETPull requests that update .NET codeenhancementNew feature or request

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions