Merge pull request #399 from its-nikhil/FEAT-auth-ctx-streamable-http

[FEAT] added support for AuthInfo in extra for StreamableHTTPServerTransport
This commit is contained in:
ihrpr 2025-05-14 14:30:28 +01:00 • committed by GitHub
commit bac916e804
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -4,6 +4,7 @@ import { isInitializeRequest, isJSONRPCError, isJSONRPCRequest, isJSONRPCRespons
import getRawBody from "raw-body";
import contentType from "content-type";
import { randomUUID } from "node:crypto";
import { AuthInfo } from "./auth/types.js";
const MAXIMUM_MESSAGE_SIZE = "4mb";
@ -112,7 +113,7 @@ export class StreamableHTTPServerTransport implements Transport {
sessionId?: string | undefined;
onclose?: () => void;
onerror?: (error: Error) => void;
onmessage?: (message: JSONRPCMessage) => void;
onmessage?: (message: JSONRPCMessage, extra?: { authInfo?: AuthInfo }) => void;
constructor(options: StreamableHTTPServerTransportOptions) {
this.sessionIdGenerator = options.sessionIdGenerator;
@ -135,7 +136,7 @@ export class StreamableHTTPServerTransport implements Transport {
/**
* Handles an incoming HTTP request, whether GET or POST
*/
async handleRequest(req: IncomingMessage, res: ServerResponse, parsedBody?: unknown): Promise<void> {
async handleRequest(req: IncomingMessage & { auth?: AuthInfo }, res: ServerResponse, parsedBody?: unknown): Promise<void> {
if (req.method === "POST") {
await this.handlePostRequest(req, res, parsedBody);
} else if (req.method === "GET") {
@ -286,7 +287,7 @@ export class StreamableHTTPServerTransport implements Transport {
/**
* Handles POST requests containing JSON-RPC messages
*/
private async handlePostRequest(req: IncomingMessage, res: ServerResponse, parsedBody?: unknown): Promise<void> {
private async handlePostRequest(req: IncomingMessage & { auth?: AuthInfo }, res: ServerResponse, parsedBody?: unknown): Promise<void> {
try {
// Validate the Accept header
const acceptHeader = req.headers.accept;
@ -316,6 +317,8 @@ export class StreamableHTTPServerTransport implements Transport {
return;
}
const authInfo: AuthInfo | undefined = req.auth;
let rawMessage;
if (parsedBody !== undefined) {
rawMessage = parsedBody;
@ -392,7 +395,7 @@ export class StreamableHTTPServerTransport implements Transport {
// handle each message
for (const message of messages) {
this.onmessage?.(message);
this.onmessage?.(message, { authInfo });
}
} else if (hasRequests) {
// The default behavior is to use SSE streaming
@ -427,7 +430,7 @@ export class StreamableHTTPServerTransport implements Transport {
// handle each message
for (const message of messages) {
this.onmessage?.(message);
this.onmessage?.(message, { authInfo });
}
// The server SHOULD NOT close the SSE stream before sending all JSON-RPC responses
// This will be handled by the send() method when responses are ready