Skip to content

Add scoped API key permissions - #273

Open
benthecarman wants to merge 1 commit into
lightningdevkit:mainfrom
benthecarman:pr-144-issue-140
Open

Add scoped API key permissions#273
benthecarman wants to merge 1 commit into
lightningdevkit:mainfrom
benthecarman:pr-144-issue-140

Conversation

@benthecarman

Copy link
Copy Markdown
Collaborator

Closes #140

The shared API key gave every client full access and required all clients to rotate credentials when one client's access was revoked. Add separate keys with scoped permissions so each client gets only its required access and can be revoked independently.

Manage keys through gRPC and the CLI, and bind signatures to key IDs and RPC methods.

@ldk-reviews-bot

ldk-reviews-bot commented Sep 7, 2026

Copy link
Copy Markdown

👋 Thanks for assigning @tankyleo as a reviewer!
I'll wait for their review and will help manage the review process.
Once they submit their review, I'll check if a second reviewer would be helpful.

@tankyleo tankyleo 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.

Quick first pass with codex, haven't validated all of them, particularly not sure about the filesystem sync and the shared encoder points. This last point I have thought about: do we want to have some library that contains common logic across ldk-server and ldk-server-cli for example ?

  - [P2] Add the four API-key endpoints to MCP _ ldk-server-mcp/src/tools/mod.rs:70, ldk-server-mcp/tests/integration.rs:14
    CreateApiKey, ListApiKeys, RevokeApiKey, and GetPermissions still lack schemas, handlers, registry entries, and expected-tool coverage. This contradicts both the documented MCP workflow and the README_s claim that MCP
    exposes the unary RPC surface.

  - [P2] Preserve PERMISSION_DENIED in the public client error model _ ldk-server-client/src/client.rs:625
    Status 7 and status 16 are both converted to AuthError. Callers therefore cannot programmatically distinguish bad/revoked credentials from a valid but under-scoped key, despite the server and API guide distinguishing
    them. Add a client-side authorization/permission error variant and update CLI, MCP, and e2e matches.

  - [P2] Avoid filesystem synchronization while holding the authentication write lock _ ldk-server/src/api_keys.rs:198, ldk-server/src/api_keys.rs:236
    Create and revoke hold std::sync::RwLock across file writes and sync_all. During a slow fsync, every authentication attempt blocks a Tokio worker on the read lock, potentially stalling the server and preventing gRPC
    deadlines from being observed promptly. Serialize management separately, perform disk work through spawn_blocking, and keep the key-map write lock limited to the in-memory commit.

  ## Smaller cleanup opportunities

  - authenticate clones the key ID, name, and complete permission BTreeSet on every RPC. Returning an Arc-backed immutable authenticated record would reduce hot-path allocations.
  - The authentication preimage construction is duplicated in client and server. A shared encoder or cross-crate golden test would reduce protocol-drift risk.
  - Add the MCP integration steps to the root CONTRIBUTING.md, not only the nested MCP instructions; that omission likely enabled the missed surface.

The shared API key gave every client full access and required all
clients to rotate credentials when one client's access was revoked.
Add separate keys with scoped permissions so each client gets only
its required access and can be revoked independently.

Manage keys through gRPC and the CLI, and bind signatures to key IDs
and RPC methods.

AI assistance: OpenAI Codex and Claude Fable 5.1 review.
@benthecarman

Copy link
Copy Markdown
Collaborator Author

rebased and addressed those comments

https://github.com/benthecarman/ldk-server/compare/c10be2f..3c2d441

@tnull tnull left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

At this point, are we still positive we want to roll our own scheme rather than reimplementing/using macaroons or biscuit? Given this adds quite a bit of complexity and 2k LoC, we could at least consider reusing a proven scheme?

@benthecarman

Copy link
Copy Markdown
Collaborator Author

At this point, are we still positive we want to roll our own scheme rather than reimplementing/using macaroons or biscuit? Given this adds quite a bit of complexity and 2k LoC, we could at least consider reusing a proven scheme?

Yeah could do macaroons instead, i could have sworn I opened a pr and we decided against it, but can't find it. I can create that too

@benthecarman

Copy link
Copy Markdown
Collaborator Author

opened #276 as an alternative

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.

Explore more granular auth schemes

4 participants