@flarcos/kiota-authentication-gnap
v0.1.1
Published
GNAP (RFC 9635) authentication provider for Kiota-generated API clients with RFC 9421 HTTP Message Signatures
Maintainers
Readme
@flarcos/kiota-authentication-gnap
GNAP (RFC 9635) authentication provider for Microsoft Kiota-generated API clients.
Enables Kiota-generated SDKs to authenticate with APIs that use the Grant Negotiation and Authorization Protocol (GNAP), such as Open Payments.
Features
- ✅ Kiota
AuthenticationProviderinterface — drop-in integration - ✅ RFC 9635 GNAP — full grant lifecycle (request, continue, rotate, revoke)
- ✅ RFC 9421 HTTP Message Signatures — Ed25519 request signing
- ✅ RFC 9530 Content-Digest — SHA-256 body integrity
- ✅ RFC 7638 JWK Thumbprint — automatic key ID derivation
- ✅ Token caching — in-memory store with TTL expiration
- ✅ Interactive grants — pluggable
InteractionHandlerfor redirect flows
Installation
npm install @flarcos/kiota-authentication-gnap @microsoft/kiota-abstractionsQuick Start
import { GnapAuthenticationProvider } from "@flarcos/kiota-authentication-gnap";
import { FetchRequestAdapter } from "@microsoft/kiota-http-fetchlibrary";
import fs from "node:fs";
// Create the GNAP auth provider
const authProvider = new GnapAuthenticationProvider({
authServerUrl: "https://auth.wallet.example/.gnap",
privateKey: fs.readFileSync("private-key.pem", "utf-8"),
clientIdentifier: "https://wallet.example/alice",
accessRights: [
{ type: "incoming-payment", actions: ["create", "read"] },
{ type: "outgoing-payment", actions: ["create", "read"] },
{ type: "quote", actions: ["create", "read"] },
],
});
// Use with a Kiota-generated client
const adapter = new FetchRequestAdapter(authProvider);
// const client = new OpenPaymentsClient(adapter);Usage with Open Payments
Open Payments uses GNAP for authorization. Here's how to create a payment:
import { GnapAuthenticationProvider } from "@flarcos/kiota-authentication-gnap";
const authProvider = new GnapAuthenticationProvider({
// The receiving wallet's auth server
authServerUrl: "https://auth.interledger-test.dev/",
// Your Ed25519 private key (PEM format)
privateKey: process.env.PRIVATE_KEY!,
// Your wallet address URL
clientIdentifier: "https://ilp.interledger-test.dev/alice",
// Request access to create incoming payments
accessRights: [
{
type: "incoming-payment",
actions: ["create", "read", "complete"],
identifier: "https://ilp.interledger-test.dev/bob",
},
],
});Interactive Grants (with user consent)
For operations that require user interaction (e.g., outgoing payments), provide an InteractionHandler:
import type { InteractionHandler, InteractionResult } from "@flarcos/kiota-authentication-gnap";
class MyInteractionHandler implements InteractionHandler {
async handleRedirect(redirectUrl: string, nonce: string): Promise<InteractionResult> {
// Open browser for user to approve
console.log(`Please visit: ${redirectUrl}`);
// Wait for callback and return the interact_ref
return {
interactRef: "received-interact-ref",
hash: "received-hash",
};
}
}
const authProvider = new GnapAuthenticationProvider({
authServerUrl: "https://auth.interledger-test.dev/",
privateKey: process.env.PRIVATE_KEY!,
clientIdentifier: "https://ilp.interledger-test.dev/alice",
accessRights: [
{
type: "outgoing-payment",
actions: ["create", "read"],
identifier: "https://ilp.interledger-test.dev/alice",
},
],
interact: {
start: ["redirect"],
finish: {
method: "redirect",
uri: "http://localhost:3000/callback",
nonce: crypto.randomUUID(),
},
},
interactionHandler: new MyInteractionHandler(),
});API Reference
GnapAuthenticationProvider
Main class implementing Kiota's AuthenticationProvider.
Constructor Options
| Option | Type | Required | Description |
|--------|------|----------|-------------|
| authServerUrl | string | ✅ | Authorization Server grant endpoint |
| privateKey | string | ✅ | Ed25519 private key (PEM format) |
| clientIdentifier | string | ✅ | Client identifier (wallet address URL) |
| accessRights | GnapAccessRight[] | ✅ | Access rights to request |
| interact | object | ❌ | Interaction mode configuration |
| interactionHandler | InteractionHandler | ❌ | Handler for interactive grants |
| tokenStore | GnapTokenStore | ❌ | Token cache (defaults to in-memory) |
| allowedHosts | string[] | ❌ | Restrict auth to specific hosts |
Methods
authenticateRequest(request)— Authenticate a Kiota request (called automatically)rotateToken()— Manually rotate the current access tokenrevokeToken()— Revoke the current access token
Standalone Utilities
import {
createHttpSignature, // RFC 9421 signing
computeContentDigest, // RFC 9530 body hash
computeJwkThumbprint, // RFC 7638 key ID
loadPrivateKey, // PEM → KeyObject
} from "@flarcos/kiota-authentication-gnap";How It Works
When authenticateRequest is called, the provider:
- Checks the token cache for a valid, non-expired GNAP access token
- Negotiates a new grant if no cached token exists (POST to AS)
- Handles interaction if the AS requires user consent (via
InteractionHandler) - Sets the
Authorization: GNAP <token>header on the request - Computes
Content-Digest(SHA-256) for requests with a body - Signs the request with RFC 9421 HTTP Message Signatures (Ed25519)
Standards Compliance
| Standard | Description | Coverage | |----------|-------------|----------| | RFC 9635 | GNAP Core Protocol | §2 Grant Request, §3 Response, §5 Continuation, §6 Token Management | | RFC 9421 | HTTP Message Signatures | §2 Signature Base, §3 Creating Signatures (Ed25519) | | RFC 9530 | Content-Digest | SHA-256 digest | | RFC 7638 | JWK Thumbprint | SHA-256 thumbprint for key identification |
Project Structure
src/
├── index.ts # Public exports
├── gnapAuthenticationProvider.ts # Kiota AuthenticationProvider implementation
├── gnapAccessTokenProvider.ts # GNAP grant lifecycle
├── gnapTokenStore.ts # In-memory token cache
├── httpMessageSigner.ts # RFC 9421 HTTP Message Signatures
├── contentDigest.ts # RFC 9530 Content-Digest
├── keyManagement.ts # Ed25519 key utilities
├── types.ts # Type definitions
└── errors.ts # Error classesLicense
Apache-2.0
Acknowledgements
This package was created as part of the Interledger Foundation Open Payments SDK Grant Program.
