# Directory Structure
```
├── .vscode
│ └── settings.json
├── commands.js
├── IMPLEMENTATION.md
├── index.js
├── loader.js
├── logs
│ ├── mcp-debug-2025-05-03T14-37-53.568Z.log
│ ├── mcp-debug-2025-05-03T16-03-19.748Z.log
│ ├── mcp-debug-2025-05-03T16-05-27.648Z.log
│ ├── mcp-debug-2025-05-03T16-08-20.395Z.log
│ ├── mcp-debug-2025-05-03T16-12-30.756Z.log
│ ├── mcp-debug-2025-05-03T16-15-36.466Z.log
│ └── mcp-debug-2025-05-03T16-31-37.961Z.log
├── node_modules
│ ├── .bin
│ │ ├── node-which
│ │ ├── tsc
│ │ └── tsserver
│ ├── .package-lock.json
│ ├── @modelcontextprotocol
│ │ └── sdk
│ │ ├── dist
│ │ │ ├── cjs
│ │ │ │ ├── cli.d.ts
│ │ │ │ ├── cli.d.ts.map
│ │ │ │ ├── cli.js
│ │ │ │ ├── cli.js.map
│ │ │ │ ├── client
│ │ │ │ │ ├── auth.d.ts
│ │ │ │ │ ├── auth.d.ts.map
│ │ │ │ │ ├── auth.js
│ │ │ │ │ ├── auth.js.map
│ │ │ │ │ ├── index.d.ts
│ │ │ │ │ ├── index.d.ts.map
│ │ │ │ │ ├── index.js
│ │ │ │ │ ├── index.js.map
│ │ │ │ │ ├── sse.d.ts
│ │ │ │ │ ├── sse.d.ts.map
│ │ │ │ │ ├── sse.js
│ │ │ │ │ ├── sse.js.map
│ │ │ │ │ ├── stdio.d.ts
│ │ │ │ │ ├── stdio.d.ts.map
│ │ │ │ │ ├── stdio.js
│ │ │ │ │ ├── stdio.js.map
│ │ │ │ │ ├── streamableHttp.d.ts
│ │ │ │ │ ├── streamableHttp.d.ts.map
│ │ │ │ │ ├── streamableHttp.js
│ │ │ │ │ ├── streamableHttp.js.map
│ │ │ │ │ ├── websocket.d.ts
│ │ │ │ │ ├── websocket.d.ts.map
│ │ │ │ │ ├── websocket.js
│ │ │ │ │ └── websocket.js.map
│ │ │ │ ├── examples
│ │ │ │ │ ├── client
│ │ │ │ │ │ ├── multipleClientsParallel.d.ts
│ │ │ │ │ │ ├── multipleClientsParallel.d.ts.map
│ │ │ │ │ │ ├── multipleClientsParallel.js
│ │ │ │ │ │ ├── multipleClientsParallel.js.map
│ │ │ │ │ │ ├── parallelToolCallsClient.d.ts
│ │ │ │ │ │ ├── parallelToolCallsClient.d.ts.map
│ │ │ │ │ │ ├── parallelToolCallsClient.js
│ │ │ │ │ │ ├── parallelToolCallsClient.js.map
│ │ │ │ │ │ ├── simpleStreamableHttp.d.ts
│ │ │ │ │ │ ├── simpleStreamableHttp.d.ts.map
│ │ │ │ │ │ ├── simpleStreamableHttp.js
│ │ │ │ │ │ ├── simpleStreamableHttp.js.map
│ │ │ │ │ │ ├── streamableHttpWithSseFallbackClient.d.ts
│ │ │ │ │ │ ├── streamableHttpWithSseFallbackClient.d.ts.map
│ │ │ │ │ │ ├── streamableHttpWithSseFallbackClient.js
│ │ │ │ │ │ └── streamableHttpWithSseFallbackClient.js.map
│ │ │ │ │ ├── server
│ │ │ │ │ │ ├── jsonResponseStreamableHttp.d.ts
│ │ │ │ │ │ ├── jsonResponseStreamableHttp.d.ts.map
│ │ │ │ │ │ ├── jsonResponseStreamableHttp.js
│ │ │ │ │ │ ├── jsonResponseStreamableHttp.js.map
│ │ │ │ │ │ ├── simpleSseServer.d.ts
│ │ │ │ │ │ ├── simpleSseServer.d.ts.map
│ │ │ │ │ │ ├── simpleSseServer.js
│ │ │ │ │ │ ├── simpleSseServer.js.map
│ │ │ │ │ │ ├── simpleStatelessStreamableHttp.d.ts
│ │ │ │ │ │ ├── simpleStatelessStreamableHttp.d.ts.map
│ │ │ │ │ │ ├── simpleStatelessStreamableHttp.js
│ │ │ │ │ │ ├── simpleStatelessStreamableHttp.js.map
│ │ │ │ │ │ ├── simpleStreamableHttp.d.ts
│ │ │ │ │ │ ├── simpleStreamableHttp.d.ts.map
│ │ │ │ │ │ ├── simpleStreamableHttp.js
│ │ │ │ │ │ ├── simpleStreamableHttp.js.map
│ │ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.d.ts
│ │ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.d.ts.map
│ │ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.js
│ │ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.js.map
│ │ │ │ │ │ ├── standaloneSseWithGetStreamableHttp.d.ts
│ │ │ │ │ │ ├── standaloneSseWithGetStreamableHttp.d.ts.map
│ │ │ │ │ │ ├── standaloneSseWithGetStreamableHttp.js
│ │ │ │ │ │ └── standaloneSseWithGetStreamableHttp.js.map
│ │ │ │ │ └── shared
│ │ │ │ │ ├── inMemoryEventStore.d.ts
│ │ │ │ │ ├── inMemoryEventStore.d.ts.map
│ │ │ │ │ ├── inMemoryEventStore.js
│ │ │ │ │ └── inMemoryEventStore.js.map
│ │ │ │ ├── inMemory.d.ts
│ │ │ │ ├── inMemory.d.ts.map
│ │ │ │ ├── inMemory.js
│ │ │ │ ├── inMemory.js.map
│ │ │ │ ├── package.json
│ │ │ │ ├── server
│ │ │ │ │ ├── auth
│ │ │ │ │ │ ├── clients.d.ts
│ │ │ │ │ │ ├── clients.d.ts.map
│ │ │ │ │ │ ├── clients.js
│ │ │ │ │ │ ├── clients.js.map
│ │ │ │ │ │ ├── errors.d.ts
│ │ │ │ │ │ ├── errors.d.ts.map
│ │ │ │ │ │ ├── errors.js
│ │ │ │ │ │ ├── errors.js.map
│ │ │ │ │ │ ├── handlers
│ │ │ │ │ │ │ ├── authorize.d.ts
│ │ │ │ │ │ │ ├── authorize.d.ts.map
│ │ │ │ │ │ │ ├── authorize.js
│ │ │ │ │ │ │ ├── authorize.js.map
│ │ │ │ │ │ │ ├── metadata.d.ts
│ │ │ │ │ │ │ ├── metadata.d.ts.map
│ │ │ │ │ │ │ ├── metadata.js
│ │ │ │ │ │ │ ├── metadata.js.map
│ │ │ │ │ │ │ ├── register.d.ts
│ │ │ │ │ │ │ ├── register.d.ts.map
│ │ │ │ │ │ │ ├── register.js
│ │ │ │ │ │ │ ├── register.js.map
│ │ │ │ │ │ │ ├── revoke.d.ts
│ │ │ │ │ │ │ ├── revoke.d.ts.map
│ │ │ │ │ │ │ ├── revoke.js
│ │ │ │ │ │ │ ├── revoke.js.map
│ │ │ │ │ │ │ ├── token.d.ts
│ │ │ │ │ │ │ ├── token.d.ts.map
│ │ │ │ │ │ │ ├── token.js
│ │ │ │ │ │ │ └── token.js.map
│ │ │ │ │ │ ├── middleware
│ │ │ │ │ │ │ ├── allowedMethods.d.ts
│ │ │ │ │ │ │ ├── allowedMethods.d.ts.map
│ │ │ │ │ │ │ ├── allowedMethods.js
│ │ │ │ │ │ │ ├── allowedMethods.js.map
│ │ │ │ │ │ │ ├── bearerAuth.d.ts
│ │ │ │ │ │ │ ├── bearerAuth.d.ts.map
│ │ │ │ │ │ │ ├── bearerAuth.js
│ │ │ │ │ │ │ ├── bearerAuth.js.map
│ │ │ │ │ │ │ ├── clientAuth.d.ts
│ │ │ │ │ │ │ ├── clientAuth.d.ts.map
│ │ │ │ │ │ │ ├── clientAuth.js
│ │ │ │ │ │ │ └── clientAuth.js.map
│ │ │ │ │ │ ├── provider.d.ts
│ │ │ │ │ │ ├── provider.d.ts.map
│ │ │ │ │ │ ├── provider.js
│ │ │ │ │ │ ├── provider.js.map
│ │ │ │ │ │ ├── providers
│ │ │ │ │ │ │ ├── proxyProvider.d.ts
│ │ │ │ │ │ │ ├── proxyProvider.d.ts.map
│ │ │ │ │ │ │ ├── proxyProvider.js
│ │ │ │ │ │ │ └── proxyProvider.js.map
│ │ │ │ │ │ ├── router.d.ts
│ │ │ │ │ │ ├── router.d.ts.map
│ │ │ │ │ │ ├── router.js
│ │ │ │ │ │ ├── router.js.map
│ │ │ │ │ │ ├── types.d.ts
│ │ │ │ │ │ ├── types.d.ts.map
│ │ │ │ │ │ ├── types.js
│ │ │ │ │ │ └── types.js.map
│ │ │ │ │ ├── completable.d.ts
│ │ │ │ │ ├── completable.d.ts.map
│ │ │ │ │ ├── completable.js
│ │ │ │ │ ├── completable.js.map
│ │ │ │ │ ├── index.d.ts
│ │ │ │ │ ├── index.d.ts.map
│ │ │ │ │ ├── index.js
│ │ │ │ │ ├── index.js.map
│ │ │ │ │ ├── mcp.d.ts
│ │ │ │ │ ├── mcp.d.ts.map
│ │ │ │ │ ├── mcp.js
│ │ │ │ │ ├── mcp.js.map
│ │ │ │ │ ├── sse.d.ts
│ │ │ │ │ ├── sse.d.ts.map
│ │ │ │ │ ├── sse.js
│ │ │ │ │ ├── sse.js.map
│ │ │ │ │ ├── stdio.d.ts
│ │ │ │ │ ├── stdio.d.ts.map
│ │ │ │ │ ├── stdio.js
│ │ │ │ │ ├── stdio.js.map
│ │ │ │ │ ├── streamableHttp.d.ts
│ │ │ │ │ ├── streamableHttp.d.ts.map
│ │ │ │ │ ├── streamableHttp.js
│ │ │ │ │ └── streamableHttp.js.map
│ │ │ │ ├── shared
│ │ │ │ │ ├── auth.d.ts
│ │ │ │ │ ├── auth.d.ts.map
│ │ │ │ │ ├── auth.js
│ │ │ │ │ ├── auth.js.map
│ │ │ │ │ ├── protocol.d.ts
│ │ │ │ │ ├── protocol.d.ts.map
│ │ │ │ │ ├── protocol.js
│ │ │ │ │ ├── protocol.js.map
│ │ │ │ │ ├── stdio.d.ts
│ │ │ │ │ ├── stdio.d.ts.map
│ │ │ │ │ ├── stdio.js
│ │ │ │ │ ├── stdio.js.map
│ │ │ │ │ ├── transport.d.ts
│ │ │ │ │ ├── transport.d.ts.map
│ │ │ │ │ ├── transport.js
│ │ │ │ │ ├── transport.js.map
│ │ │ │ │ ├── uriTemplate.d.ts
│ │ │ │ │ ├── uriTemplate.d.ts.map
│ │ │ │ │ ├── uriTemplate.js
│ │ │ │ │ └── uriTemplate.js.map
│ │ │ │ ├── types.d.ts
│ │ │ │ ├── types.d.ts.map
│ │ │ │ ├── types.js
│ │ │ │ └── types.js.map
│ │ │ └── esm
│ │ │ ├── cli.d.ts
│ │ │ ├── cli.d.ts.map
│ │ │ ├── cli.js
│ │ │ ├── cli.js.map
│ │ │ ├── client
│ │ │ │ ├── auth.d.ts
│ │ │ │ ├── auth.d.ts.map
│ │ │ │ ├── auth.js
│ │ │ │ ├── auth.js.map
│ │ │ │ ├── index.d.ts
│ │ │ │ ├── index.d.ts.map
│ │ │ │ ├── index.js
│ │ │ │ ├── index.js.map
│ │ │ │ ├── sse.d.ts
│ │ │ │ ├── sse.d.ts.map
│ │ │ │ ├── sse.js
│ │ │ │ ├── sse.js.map
│ │ │ │ ├── stdio.d.ts
│ │ │ │ ├── stdio.d.ts.map
│ │ │ │ ├── stdio.js
│ │ │ │ ├── stdio.js.map
│ │ │ │ ├── streamableHttp.d.ts
│ │ │ │ ├── streamableHttp.d.ts.map
│ │ │ │ ├── streamableHttp.js
│ │ │ │ ├── streamableHttp.js.map
│ │ │ │ ├── websocket.d.ts
│ │ │ │ ├── websocket.d.ts.map
│ │ │ │ ├── websocket.js
│ │ │ │ └── websocket.js.map
│ │ │ ├── examples
│ │ │ │ ├── client
│ │ │ │ │ ├── multipleClientsParallel.d.ts
│ │ │ │ │ ├── multipleClientsParallel.d.ts.map
│ │ │ │ │ ├── multipleClientsParallel.js
│ │ │ │ │ ├── multipleClientsParallel.js.map
│ │ │ │ │ ├── parallelToolCallsClient.d.ts
│ │ │ │ │ ├── parallelToolCallsClient.d.ts.map
│ │ │ │ │ ├── parallelToolCallsClient.js
│ │ │ │ │ ├── parallelToolCallsClient.js.map
│ │ │ │ │ ├── simpleStreamableHttp.d.ts
│ │ │ │ │ ├── simpleStreamableHttp.d.ts.map
│ │ │ │ │ ├── simpleStreamableHttp.js
│ │ │ │ │ ├── simpleStreamableHttp.js.map
│ │ │ │ │ ├── streamableHttpWithSseFallbackClient.d.ts
│ │ │ │ │ ├── streamableHttpWithSseFallbackClient.d.ts.map
│ │ │ │ │ ├── streamableHttpWithSseFallbackClient.js
│ │ │ │ │ └── streamableHttpWithSseFallbackClient.js.map
│ │ │ │ ├── server
│ │ │ │ │ ├── jsonResponseStreamableHttp.d.ts
│ │ │ │ │ ├── jsonResponseStreamableHttp.d.ts.map
│ │ │ │ │ ├── jsonResponseStreamableHttp.js
│ │ │ │ │ ├── jsonResponseStreamableHttp.js.map
│ │ │ │ │ ├── simpleSseServer.d.ts
│ │ │ │ │ ├── simpleSseServer.d.ts.map
│ │ │ │ │ ├── simpleSseServer.js
│ │ │ │ │ ├── simpleSseServer.js.map
│ │ │ │ │ ├── simpleStatelessStreamableHttp.d.ts
│ │ │ │ │ ├── simpleStatelessStreamableHttp.d.ts.map
│ │ │ │ │ ├── simpleStatelessStreamableHttp.js
│ │ │ │ │ ├── simpleStatelessStreamableHttp.js.map
│ │ │ │ │ ├── simpleStreamableHttp.d.ts
│ │ │ │ │ ├── simpleStreamableHttp.d.ts.map
│ │ │ │ │ ├── simpleStreamableHttp.js
│ │ │ │ │ ├── simpleStreamableHttp.js.map
│ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.d.ts
│ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.d.ts.map
│ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.js
│ │ │ │ │ ├── sseAndStreamableHttpCompatibleServer.js.map
│ │ │ │ │ ├── standaloneSseWithGetStreamableHttp.d.ts
│ │ │ │ │ ├── standaloneSseWithGetStreamableHttp.d.ts.map
│ │ │ │ │ ├── standaloneSseWithGetStreamableHttp.js
│ │ │ │ │ └── standaloneSseWithGetStreamableHttp.js.map
│ │ │ │ └── shared
│ │ │ │ ├── inMemoryEventStore.d.ts
│ │ │ │ ├── inMemoryEventStore.d.ts.map
│ │ │ │ ├── inMemoryEventStore.js
│ │ │ │ └── inMemoryEventStore.js.map
│ │ │ ├── inMemory.d.ts
│ │ │ ├── inMemory.d.ts.map
│ │ │ ├── inMemory.js
│ │ │ ├── inMemory.js.map
│ │ │ ├── package.json
│ │ │ ├── server
│ │ │ │ ├── auth
│ │ │ │ │ ├── clients.d.ts
│ │ │ │ │ ├── clients.d.ts.map
│ │ │ │ │ ├── clients.js
│ │ │ │ │ ├── clients.js.map
│ │ │ │ │ ├── errors.d.ts
│ │ │ │ │ ├── errors.d.ts.map
│ │ │ │ │ ├── errors.js
│ │ │ │ │ ├── errors.js.map
│ │ │ │ │ ├── handlers
│ │ │ │ │ │ ├── authorize.d.ts
│ │ │ │ │ │ ├── authorize.d.ts.map
│ │ │ │ │ │ ├── authorize.js
│ │ │ │ │ │ ├── authorize.js.map
│ │ │ │ │ │ ├── metadata.d.ts
│ │ │ │ │ │ ├── metadata.d.ts.map
│ │ │ │ │ │ ├── metadata.js
│ │ │ │ │ │ ├── metadata.js.map
│ │ │ │ │ │ ├── register.d.ts
│ │ │ │ │ │ ├── register.d.ts.map
│ │ │ │ │ │ ├── register.js
│ │ │ │ │ │ ├── register.js.map
│ │ │ │ │ │ ├── revoke.d.ts
│ │ │ │ │ │ ├── revoke.d.ts.map
│ │ │ │ │ │ ├── revoke.js
│ │ │ │ │ │ ├── revoke.js.map
│ │ │ │ │ │ ├── token.d.ts
│ │ │ │ │ │ ├── token.d.ts.map
│ │ │ │ │ │ ├── token.js
│ │ │ │ │ │ └── token.js.map
│ │ │ │ │ ├── middleware
│ │ │ │ │ │ ├── allowedMethods.d.ts
│ │ │ │ │ │ ├── allowedMethods.d.ts.map
│ │ │ │ │ │ ├── allowedMethods.js
│ │ │ │ │ │ ├── allowedMethods.js.map
│ │ │ │ │ │ ├── bearerAuth.d.ts
│ │ │ │ │ │ ├── bearerAuth.d.ts.map
│ │ │ │ │ │ ├── bearerAuth.js
│ │ │ │ │ │ ├── bearerAuth.js.map
│ │ │ │ │ │ ├── clientAuth.d.ts
│ │ │ │ │ │ ├── clientAuth.d.ts.map
│ │ │ │ │ │ ├── clientAuth.js
│ │ │ │ │ │ └── clientAuth.js.map
│ │ │ │ │ ├── provider.d.ts
│ │ │ │ │ ├── provider.d.ts.map
│ │ │ │ │ ├── provider.js
│ │ │ │ │ ├── provider.js.map
│ │ │ │ │ ├── providers
│ │ │ │ │ │ ├── proxyProvider.d.ts
│ │ │ │ │ │ ├── proxyProvider.d.ts.map
│ │ │ │ │ │ ├── proxyProvider.js
│ │ │ │ │ │ └── proxyProvider.js.map
│ │ │ │ │ ├── router.d.ts
│ │ │ │ │ ├── router.d.ts.map
│ │ │ │ │ ├── router.js
│ │ │ │ │ ├── router.js.map
│ │ │ │ │ ├── types.d.ts
│ │ │ │ │ ├── types.d.ts.map
│ │ │ │ │ ├── types.js
│ │ │ │ │ └── types.js.map
│ │ │ │ ├── completable.d.ts
│ │ │ │ ├── completable.d.ts.map
│ │ │ │ ├── completable.js
│ │ │ │ ├── completable.js.map
│ │ │ │ ├── index.d.ts
│ │ │ │ ├── index.d.ts.map
│ │ │ │ ├── index.js
│ │ │ │ ├── index.js.map
│ │ │ │ ├── mcp.d.ts
│ │ │ │ ├── mcp.d.ts.map
│ │ │ │ ├── mcp.js
│ │ │ │ ├── mcp.js.map
│ │ │ │ ├── sse.d.ts
│ │ │ │ ├── sse.d.ts.map
│ │ │ │ ├── sse.js
│ │ │ │ ├── sse.js.map
│ │ │ │ ├── stdio.d.ts
│ │ │ │ ├── stdio.d.ts.map
│ │ │ │ ├── stdio.js
│ │ │ │ ├── stdio.js.map
│ │ │ │ ├── streamableHttp.d.ts
│ │ │ │ ├── streamableHttp.d.ts.map
│ │ │ │ ├── streamableHttp.js
│ │ │ │ └── streamableHttp.js.map
│ │ │ ├── shared
│ │ │ │ ├── auth.d.ts
│ │ │ │ ├── auth.d.ts.map
│ │ │ │ ├── auth.js
│ │ │ │ ├── auth.js.map
│ │ │ │ ├── protocol.d.ts
│ │ │ │ ├── protocol.d.ts.map
│ │ │ │ ├── protocol.js
│ │ │ │ ├── protocol.js.map
│ │ │ │ ├── stdio.d.ts
│ │ │ │ ├── stdio.d.ts.map
│ │ │ │ ├── stdio.js
│ │ │ │ ├── stdio.js.map
│ │ │ │ ├── transport.d.ts
│ │ │ │ ├── transport.d.ts.map
│ │ │ │ ├── transport.js
│ │ │ │ ├── transport.js.map
│ │ │ │ ├── uriTemplate.d.ts
│ │ │ │ ├── uriTemplate.d.ts.map
│ │ │ │ ├── uriTemplate.js
│ │ │ │ └── uriTemplate.js.map
│ │ │ ├── types.d.ts
│ │ │ ├── types.d.ts.map
│ │ │ ├── types.js
│ │ │ └── types.js.map
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── @types
│ │ └── node
│ │ ├── assert
│ │ │ └── strict.d.ts
│ │ ├── assert.d.ts
│ │ ├── async_hooks.d.ts
│ │ ├── buffer.buffer.d.ts
│ │ ├── buffer.d.ts
│ │ ├── child_process.d.ts
│ │ ├── cluster.d.ts
│ │ ├── compatibility
│ │ │ ├── disposable.d.ts
│ │ │ ├── index.d.ts
│ │ │ ├── indexable.d.ts
│ │ │ └── iterators.d.ts
│ │ ├── console.d.ts
│ │ ├── constants.d.ts
│ │ ├── crypto.d.ts
│ │ ├── dgram.d.ts
│ │ ├── diagnostics_channel.d.ts
│ │ ├── dns
│ │ │ └── promises.d.ts
│ │ ├── dns.d.ts
│ │ ├── dom-events.d.ts
│ │ ├── domain.d.ts
│ │ ├── events.d.ts
│ │ ├── fs
│ │ │ └── promises.d.ts
│ │ ├── fs.d.ts
│ │ ├── globals.d.ts
│ │ ├── globals.typedarray.d.ts
│ │ ├── http.d.ts
│ │ ├── http2.d.ts
│ │ ├── https.d.ts
│ │ ├── index.d.ts
│ │ ├── inspector.d.ts
│ │ ├── LICENSE
│ │ ├── module.d.ts
│ │ ├── net.d.ts
│ │ ├── os.d.ts
│ │ ├── package.json
│ │ ├── path.d.ts
│ │ ├── perf_hooks.d.ts
│ │ ├── process.d.ts
│ │ ├── punycode.d.ts
│ │ ├── querystring.d.ts
│ │ ├── readline
│ │ │ └── promises.d.ts
│ │ ├── readline.d.ts
│ │ ├── README.md
│ │ ├── repl.d.ts
│ │ ├── sea.d.ts
│ │ ├── stream
│ │ │ ├── consumers.d.ts
│ │ │ ├── promises.d.ts
│ │ │ └── web.d.ts
│ │ ├── stream.d.ts
│ │ ├── string_decoder.d.ts
│ │ ├── test.d.ts
│ │ ├── timers
│ │ │ └── promises.d.ts
│ │ ├── timers.d.ts
│ │ ├── tls.d.ts
│ │ ├── trace_events.d.ts
│ │ ├── ts5.6
│ │ │ ├── buffer.buffer.d.ts
│ │ │ ├── globals.typedarray.d.ts
│ │ │ └── index.d.ts
│ │ ├── tty.d.ts
│ │ ├── url.d.ts
│ │ ├── util.d.ts
│ │ ├── v8.d.ts
│ │ ├── vm.d.ts
│ │ ├── wasi.d.ts
│ │ ├── worker_threads.d.ts
│ │ └── zlib.d.ts
│ ├── accepts
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── body-parser
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── lib
│ │ │ ├── read.js
│ │ │ ├── types
│ │ │ │ ├── json.js
│ │ │ │ ├── raw.js
│ │ │ │ ├── text.js
│ │ │ │ └── urlencoded.js
│ │ │ └── utils.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── bytes
│ │ ├── History.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── Readme.md
│ ├── call-bind-apply-helpers
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── actualApply.d.ts
│ │ ├── actualApply.js
│ │ ├── applyBind.d.ts
│ │ ├── applyBind.js
│ │ ├── CHANGELOG.md
│ │ ├── functionApply.d.ts
│ │ ├── functionApply.js
│ │ ├── functionCall.d.ts
│ │ ├── functionCall.js
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── reflectApply.d.ts
│ │ ├── reflectApply.js
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── call-bound
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── content-disposition
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── content-type
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── cookie
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── SECURITY.md
│ ├── cookie-signature
│ │ ├── History.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── Readme.md
│ ├── cors
│ │ ├── CONTRIBUTING.md
│ │ ├── HISTORY.md
│ │ ├── lib
│ │ │ └── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── cross-spawn
│ │ ├── index.js
│ │ ├── lib
│ │ │ ├── enoent.js
│ │ │ ├── parse.js
│ │ │ └── util
│ │ │ ├── escape.js
│ │ │ ├── readShebang.js
│ │ │ └── resolveCommand.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── debug
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── src
│ │ ├── browser.js
│ │ ├── common.js
│ │ ├── index.js
│ │ └── node.js
│ ├── depd
│ │ ├── History.md
│ │ ├── index.js
│ │ ├── lib
│ │ │ └── browser
│ │ │ └── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── Readme.md
│ ├── dunder-proto
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── get.d.ts
│ │ ├── get.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── set.d.ts
│ │ ├── set.js
│ │ ├── test
│ │ │ ├── get.js
│ │ │ ├── index.js
│ │ │ └── set.js
│ │ └── tsconfig.json
│ ├── ee-first
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── encodeurl
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── es-define-property
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── es-errors
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── CHANGELOG.md
│ │ ├── eval.d.ts
│ │ ├── eval.js
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── range.d.ts
│ │ ├── range.js
│ │ ├── README.md
│ │ ├── ref.d.ts
│ │ ├── ref.js
│ │ ├── syntax.d.ts
│ │ ├── syntax.js
│ │ ├── test
│ │ │ └── index.js
│ │ ├── tsconfig.json
│ │ ├── type.d.ts
│ │ ├── type.js
│ │ ├── uri.d.ts
│ │ └── uri.js
│ ├── es-object-atoms
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── isObject.d.ts
│ │ ├── isObject.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── RequireObjectCoercible.d.ts
│ │ ├── RequireObjectCoercible.js
│ │ ├── test
│ │ │ └── index.js
│ │ ├── ToObject.d.ts
│ │ ├── ToObject.js
│ │ └── tsconfig.json
│ ├── escape-html
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── Readme.md
│ ├── etag
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── eventsource
│ │ ├── dist
│ │ │ ├── index.cjs
│ │ │ ├── index.cjs.map
│ │ │ ├── index.d.cts
│ │ │ ├── index.d.ts
│ │ │ ├── index.js
│ │ │ └── index.js.map
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── src
│ │ ├── errors.ts
│ │ ├── EventSource.ts
│ │ ├── index.ts
│ │ └── types.ts
│ ├── eventsource-parser
│ │ ├── dist
│ │ │ ├── index.cjs
│ │ │ ├── index.cjs.map
│ │ │ ├── index.d.cts
│ │ │ ├── index.d.ts
│ │ │ ├── index.esm.js
│ │ │ ├── index.esm.js.map
│ │ │ ├── index.js
│ │ │ ├── index.js.map
│ │ │ ├── stats.html
│ │ │ ├── stream.cjs
│ │ │ ├── stream.cjs.map
│ │ │ ├── stream.d.cts
│ │ │ ├── stream.d.ts
│ │ │ ├── stream.esm.js
│ │ │ ├── stream.esm.js.map
│ │ │ ├── stream.js
│ │ │ └── stream.js.map
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── src
│ │ │ ├── errors.ts
│ │ │ ├── index.ts
│ │ │ ├── parse.ts
│ │ │ ├── stream.ts
│ │ │ └── types.ts
│ │ └── stream.js
│ ├── express
│ │ ├── History.md
│ │ ├── index.js
│ │ ├── lib
│ │ │ ├── application.js
│ │ │ ├── express.js
│ │ │ ├── request.js
│ │ │ ├── response.js
│ │ │ ├── utils.js
│ │ │ └── view.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── Readme.md
│ ├── express-rate-limit
│ │ ├── dist
│ │ │ ├── index.cjs
│ │ │ ├── index.d.cts
│ │ │ ├── index.d.mts
│ │ │ ├── index.d.ts
│ │ │ └── index.mjs
│ │ ├── license.md
│ │ ├── package.json
│ │ ├── readme.md
│ │ └── tsconfig.json
│ ├── finalhandler
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── forwarded
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── fresh
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── function-bind
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ ├── FUNDING.yml
│ │ │ └── SECURITY.md
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── implementation.js
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── test
│ │ ├── .eslintrc
│ │ └── index.js
│ ├── get-intrinsic
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── test
│ │ └── GetIntrinsic.js
│ ├── get-proto
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── Object.getPrototypeOf.d.ts
│ │ ├── Object.getPrototypeOf.js
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── Reflect.getPrototypeOf.d.ts
│ │ ├── Reflect.getPrototypeOf.js
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── gopd
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── CHANGELOG.md
│ │ ├── gOPD.d.ts
│ │ ├── gOPD.js
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── has-symbols
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── shams.d.ts
│ │ ├── shams.js
│ │ ├── test
│ │ │ ├── index.js
│ │ │ ├── shams
│ │ │ │ ├── core-js.js
│ │ │ │ └── get-own-property-symbols.js
│ │ │ └── tests.js
│ │ └── tsconfig.json
│ ├── hasown
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── tsconfig.json
│ ├── http-errors
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── iconv-lite
│ │ ├── .github
│ │ │ └── dependabot.yml
│ │ ├── .idea
│ │ │ ├── codeStyles
│ │ │ │ ├── codeStyleConfig.xml
│ │ │ │ └── Project.xml
│ │ │ ├── iconv-lite.iml
│ │ │ ├── inspectionProfiles
│ │ │ │ └── Project_Default.xml
│ │ │ ├── modules.xml
│ │ │ └── vcs.xml
│ │ ├── Changelog.md
│ │ ├── encodings
│ │ │ ├── dbcs-codec.js
│ │ │ ├── dbcs-data.js
│ │ │ ├── index.js
│ │ │ ├── internal.js
│ │ │ ├── sbcs-codec.js
│ │ │ ├── sbcs-data-generated.js
│ │ │ ├── sbcs-data.js
│ │ │ ├── tables
│ │ │ │ ├── big5-added.json
│ │ │ │ ├── cp936.json
│ │ │ │ ├── cp949.json
│ │ │ │ ├── cp950.json
│ │ │ │ ├── eucjp.json
│ │ │ │ ├── gb18030-ranges.json
│ │ │ │ ├── gbk-added.json
│ │ │ │ └── shiftjis.json
│ │ │ ├── utf16.js
│ │ │ ├── utf32.js
│ │ │ └── utf7.js
│ │ ├── lib
│ │ │ ├── bom-handling.js
│ │ │ ├── index.d.ts
│ │ │ ├── index.js
│ │ │ └── streams.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── inherits
│ │ ├── inherits_browser.js
│ │ ├── inherits.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── ipaddr.js
│ │ ├── ipaddr.min.js
│ │ ├── lib
│ │ │ ├── ipaddr.js
│ │ │ └── ipaddr.js.d.ts
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── is-promise
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── index.mjs
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── readme.md
│ ├── isexe
│ │ ├── .npmignore
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── mode.js
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── basic.js
│ │ └── windows.js
│ ├── math-intrinsics
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── abs.d.ts
│ │ ├── abs.js
│ │ ├── CHANGELOG.md
│ │ ├── constants
│ │ │ ├── maxArrayLength.d.ts
│ │ │ ├── maxArrayLength.js
│ │ │ ├── maxSafeInteger.d.ts
│ │ │ ├── maxSafeInteger.js
│ │ │ ├── maxValue.d.ts
│ │ │ └── maxValue.js
│ │ ├── floor.d.ts
│ │ ├── floor.js
│ │ ├── isFinite.d.ts
│ │ ├── isFinite.js
│ │ ├── isInteger.d.ts
│ │ ├── isInteger.js
│ │ ├── isNaN.d.ts
│ │ ├── isNaN.js
│ │ ├── isNegativeZero.d.ts
│ │ ├── isNegativeZero.js
│ │ ├── LICENSE
│ │ ├── max.d.ts
│ │ ├── max.js
│ │ ├── min.d.ts
│ │ ├── min.js
│ │ ├── mod.d.ts
│ │ ├── mod.js
│ │ ├── package.json
│ │ ├── pow.d.ts
│ │ ├── pow.js
│ │ ├── README.md
│ │ ├── round.d.ts
│ │ ├── round.js
│ │ ├── sign.d.ts
│ │ ├── sign.js
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── media-typer
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── merge-descriptors
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── license
│ │ ├── package.json
│ │ └── readme.md
│ ├── mime-db
│ │ ├── db.json
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── mime-types
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── mimeScore.js
│ │ ├── package.json
│ │ └── README.md
│ ├── ms
│ │ ├── index.js
│ │ ├── license.md
│ │ ├── package.json
│ │ └── readme.md
│ ├── negotiator
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── lib
│ │ │ ├── charset.js
│ │ │ ├── encoding.js
│ │ │ ├── language.js
│ │ │ └── mediaType.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── object-assign
│ │ ├── index.js
│ │ ├── license
│ │ ├── package.json
│ │ └── readme.md
│ ├── object-inspect
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── example
│ │ │ ├── all.js
│ │ │ ├── circular.js
│ │ │ ├── fn.js
│ │ │ └── inspect.js
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package-support.json
│ │ ├── package.json
│ │ ├── readme.markdown
│ │ ├── test
│ │ │ ├── bigint.js
│ │ │ ├── browser
│ │ │ │ └── dom.js
│ │ │ ├── circular.js
│ │ │ ├── deep.js
│ │ │ ├── element.js
│ │ │ ├── err.js
│ │ │ ├── fakes.js
│ │ │ ├── fn.js
│ │ │ ├── global.js
│ │ │ ├── has.js
│ │ │ ├── holes.js
│ │ │ ├── indent-option.js
│ │ │ ├── inspect.js
│ │ │ ├── lowbyte.js
│ │ │ ├── number.js
│ │ │ ├── quoteStyle.js
│ │ │ ├── toStringTag.js
│ │ │ ├── undef.js
│ │ │ └── values.js
│ │ ├── test-core-js.js
│ │ └── util.inspect.js
│ ├── on-finished
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── once
│ │ ├── LICENSE
│ │ ├── once.js
│ │ ├── package.json
│ │ └── README.md
│ ├── parseurl
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── path-key
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── license
│ │ ├── package.json
│ │ └── readme.md
│ ├── path-to-regexp
│ │ ├── dist
│ │ │ ├── index.d.ts
│ │ │ ├── index.js
│ │ │ └── index.js.map
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── Readme.md
│ ├── pkce-challenge
│ │ ├── dist
│ │ │ ├── index.browser.d.ts
│ │ │ ├── index.browser.js
│ │ │ ├── index.node.cjs
│ │ │ ├── index.node.d.cts
│ │ │ ├── index.node.d.ts
│ │ │ └── index.node.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── proxy-addr
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── qs
│ │ ├── .editorconfig
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── dist
│ │ │ └── qs.js
│ │ ├── lib
│ │ │ ├── formats.js
│ │ │ ├── index.js
│ │ │ ├── parse.js
│ │ │ ├── stringify.js
│ │ │ └── utils.js
│ │ ├── LICENSE.md
│ │ ├── package.json
│ │ ├── README.md
│ │ └── test
│ │ ├── empty-keys-cases.js
│ │ ├── parse.js
│ │ ├── stringify.js
│ │ └── utils.js
│ ├── range-parser
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── raw-body
│ │ ├── HISTORY.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── SECURITY.md
│ ├── router
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── lib
│ │ │ ├── layer.js
│ │ │ └── route.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── safe-buffer
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── safer-buffer
│ │ ├── dangerous.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── Porting-Buffer.md
│ │ ├── Readme.md
│ │ ├── safer.js
│ │ └── tests.js
│ ├── send
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── serve-static
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── setprototypeof
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── test
│ │ └── index.js
│ ├── shebang-command
│ │ ├── index.js
│ │ ├── license
│ │ ├── package.json
│ │ └── readme.md
│ ├── shebang-regex
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── license
│ │ ├── package.json
│ │ └── readme.md
│ ├── side-channel
│ │ ├── .editorconfig
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── side-channel-list
│ │ ├── .editorconfig
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── list.d.ts
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── side-channel-map
│ │ ├── .editorconfig
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── side-channel-weakmap
│ │ ├── .editorconfig
│ │ ├── .eslintrc
│ │ ├── .github
│ │ │ └── FUNDING.yml
│ │ ├── .nycrc
│ │ ├── CHANGELOG.md
│ │ ├── index.d.ts
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── test
│ │ │ └── index.js
│ │ └── tsconfig.json
│ ├── statuses
│ │ ├── codes.json
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── toidentifier
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── type-is
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── typescript
│ │ ├── bin
│ │ │ ├── tsc
│ │ │ └── tsserver
│ │ ├── lib
│ │ │ ├── _tsc.js
│ │ │ ├── _tsserver.js
│ │ │ ├── _typingsInstaller.js
│ │ │ ├── cs
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── de
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── es
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── fr
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── it
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── ja
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── ko
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── lib.d.ts
│ │ │ ├── lib.decorators.d.ts
│ │ │ ├── lib.decorators.legacy.d.ts
│ │ │ ├── lib.dom.asynciterable.d.ts
│ │ │ ├── lib.dom.d.ts
│ │ │ ├── lib.dom.iterable.d.ts
│ │ │ ├── lib.es2015.collection.d.ts
│ │ │ ├── lib.es2015.core.d.ts
│ │ │ ├── lib.es2015.d.ts
│ │ │ ├── lib.es2015.generator.d.ts
│ │ │ ├── lib.es2015.iterable.d.ts
│ │ │ ├── lib.es2015.promise.d.ts
│ │ │ ├── lib.es2015.proxy.d.ts
│ │ │ ├── lib.es2015.reflect.d.ts
│ │ │ ├── lib.es2015.symbol.d.ts
│ │ │ ├── lib.es2015.symbol.wellknown.d.ts
│ │ │ ├── lib.es2016.array.include.d.ts
│ │ │ ├── lib.es2016.d.ts
│ │ │ ├── lib.es2016.full.d.ts
│ │ │ ├── lib.es2016.intl.d.ts
│ │ │ ├── lib.es2017.arraybuffer.d.ts
│ │ │ ├── lib.es2017.d.ts
│ │ │ ├── lib.es2017.date.d.ts
│ │ │ ├── lib.es2017.full.d.ts
│ │ │ ├── lib.es2017.intl.d.ts
│ │ │ ├── lib.es2017.object.d.ts
│ │ │ ├── lib.es2017.sharedmemory.d.ts
│ │ │ ├── lib.es2017.string.d.ts
│ │ │ ├── lib.es2017.typedarrays.d.ts
│ │ │ ├── lib.es2018.asyncgenerator.d.ts
│ │ │ ├── lib.es2018.asynciterable.d.ts
│ │ │ ├── lib.es2018.d.ts
│ │ │ ├── lib.es2018.full.d.ts
│ │ │ ├── lib.es2018.intl.d.ts
│ │ │ ├── lib.es2018.promise.d.ts
│ │ │ ├── lib.es2018.regexp.d.ts
│ │ │ ├── lib.es2019.array.d.ts
│ │ │ ├── lib.es2019.d.ts
│ │ │ ├── lib.es2019.full.d.ts
│ │ │ ├── lib.es2019.intl.d.ts
│ │ │ ├── lib.es2019.object.d.ts
│ │ │ ├── lib.es2019.string.d.ts
│ │ │ ├── lib.es2019.symbol.d.ts
│ │ │ ├── lib.es2020.bigint.d.ts
│ │ │ ├── lib.es2020.d.ts
│ │ │ ├── lib.es2020.date.d.ts
│ │ │ ├── lib.es2020.full.d.ts
│ │ │ ├── lib.es2020.intl.d.ts
│ │ │ ├── lib.es2020.number.d.ts
│ │ │ ├── lib.es2020.promise.d.ts
│ │ │ ├── lib.es2020.sharedmemory.d.ts
│ │ │ ├── lib.es2020.string.d.ts
│ │ │ ├── lib.es2020.symbol.wellknown.d.ts
│ │ │ ├── lib.es2021.d.ts
│ │ │ ├── lib.es2021.full.d.ts
│ │ │ ├── lib.es2021.intl.d.ts
│ │ │ ├── lib.es2021.promise.d.ts
│ │ │ ├── lib.es2021.string.d.ts
│ │ │ ├── lib.es2021.weakref.d.ts
│ │ │ ├── lib.es2022.array.d.ts
│ │ │ ├── lib.es2022.d.ts
│ │ │ ├── lib.es2022.error.d.ts
│ │ │ ├── lib.es2022.full.d.ts
│ │ │ ├── lib.es2022.intl.d.ts
│ │ │ ├── lib.es2022.object.d.ts
│ │ │ ├── lib.es2022.regexp.d.ts
│ │ │ ├── lib.es2022.string.d.ts
│ │ │ ├── lib.es2023.array.d.ts
│ │ │ ├── lib.es2023.collection.d.ts
│ │ │ ├── lib.es2023.d.ts
│ │ │ ├── lib.es2023.full.d.ts
│ │ │ ├── lib.es2023.intl.d.ts
│ │ │ ├── lib.es2024.arraybuffer.d.ts
│ │ │ ├── lib.es2024.collection.d.ts
│ │ │ ├── lib.es2024.d.ts
│ │ │ ├── lib.es2024.full.d.ts
│ │ │ ├── lib.es2024.object.d.ts
│ │ │ ├── lib.es2024.promise.d.ts
│ │ │ ├── lib.es2024.regexp.d.ts
│ │ │ ├── lib.es2024.sharedmemory.d.ts
│ │ │ ├── lib.es2024.string.d.ts
│ │ │ ├── lib.es5.d.ts
│ │ │ ├── lib.es6.d.ts
│ │ │ ├── lib.esnext.array.d.ts
│ │ │ ├── lib.esnext.collection.d.ts
│ │ │ ├── lib.esnext.d.ts
│ │ │ ├── lib.esnext.decorators.d.ts
│ │ │ ├── lib.esnext.disposable.d.ts
│ │ │ ├── lib.esnext.float16.d.ts
│ │ │ ├── lib.esnext.full.d.ts
│ │ │ ├── lib.esnext.intl.d.ts
│ │ │ ├── lib.esnext.iterator.d.ts
│ │ │ ├── lib.esnext.promise.d.ts
│ │ │ ├── lib.scripthost.d.ts
│ │ │ ├── lib.webworker.asynciterable.d.ts
│ │ │ ├── lib.webworker.d.ts
│ │ │ ├── lib.webworker.importscripts.d.ts
│ │ │ ├── lib.webworker.iterable.d.ts
│ │ │ ├── pl
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── pt-br
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── ru
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── tr
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ ├── tsc.js
│ │ │ ├── tsserver.js
│ │ │ ├── tsserverlibrary.d.ts
│ │ │ ├── tsserverlibrary.js
│ │ │ ├── typescript.d.ts
│ │ │ ├── typescript.js
│ │ │ ├── typesMap.json
│ │ │ ├── typingsInstaller.js
│ │ │ ├── watchGuard.js
│ │ │ ├── zh-cn
│ │ │ │ └── diagnosticMessages.generated.json
│ │ │ └── zh-tw
│ │ │ └── diagnosticMessages.generated.json
│ │ ├── LICENSE.txt
│ │ ├── package.json
│ │ ├── README.md
│ │ ├── SECURITY.md
│ │ └── ThirdPartyNoticeText.txt
│ ├── undici-types
│ │ ├── agent.d.ts
│ │ ├── api.d.ts
│ │ ├── balanced-pool.d.ts
│ │ ├── cache.d.ts
│ │ ├── client.d.ts
│ │ ├── connector.d.ts
│ │ ├── content-type.d.ts
│ │ ├── cookies.d.ts
│ │ ├── diagnostics-channel.d.ts
│ │ ├── dispatcher.d.ts
│ │ ├── env-http-proxy-agent.d.ts
│ │ ├── errors.d.ts
│ │ ├── eventsource.d.ts
│ │ ├── fetch.d.ts
│ │ ├── file.d.ts
│ │ ├── filereader.d.ts
│ │ ├── formdata.d.ts
│ │ ├── global-dispatcher.d.ts
│ │ ├── global-origin.d.ts
│ │ ├── handlers.d.ts
│ │ ├── header.d.ts
│ │ ├── index.d.ts
│ │ ├── interceptors.d.ts
│ │ ├── LICENSE
│ │ ├── mock-agent.d.ts
│ │ ├── mock-client.d.ts
│ │ ├── mock-errors.d.ts
│ │ ├── mock-interceptor.d.ts
│ │ ├── mock-pool.d.ts
│ │ ├── package.json
│ │ ├── patch.d.ts
│ │ ├── pool-stats.d.ts
│ │ ├── pool.d.ts
│ │ ├── proxy-agent.d.ts
│ │ ├── readable.d.ts
│ │ ├── README.md
│ │ ├── retry-agent.d.ts
│ │ ├── retry-handler.d.ts
│ │ ├── util.d.ts
│ │ ├── webidl.d.ts
│ │ └── websocket.d.ts
│ ├── unpipe
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── vary
│ │ ├── HISTORY.md
│ │ ├── index.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ ├── which
│ │ ├── bin
│ │ │ └── node-which
│ │ ├── CHANGELOG.md
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── which.js
│ ├── wrappy
│ │ ├── LICENSE
│ │ ├── package.json
│ │ ├── README.md
│ │ └── wrappy.js
│ ├── zod
│ │ ├── index.d.ts
│ │ ├── lib
│ │ │ ├── __tests__
│ │ │ │ ├── Mocker.d.ts
│ │ │ │ └── Mocker.js
│ │ │ ├── benchmarks
│ │ │ │ ├── datetime.d.ts
│ │ │ │ ├── datetime.js
│ │ │ │ ├── discriminatedUnion.d.ts
│ │ │ │ ├── discriminatedUnion.js
│ │ │ │ ├── index.d.ts
│ │ │ │ ├── index.js
│ │ │ │ ├── ipv4.d.ts
│ │ │ │ ├── ipv4.js
│ │ │ │ ├── object.d.ts
│ │ │ │ ├── object.js
│ │ │ │ ├── primitives.d.ts
│ │ │ │ ├── primitives.js
│ │ │ │ ├── realworld.d.ts
│ │ │ │ ├── realworld.js
│ │ │ │ ├── string.d.ts
│ │ │ │ ├── string.js
│ │ │ │ ├── union.d.ts
│ │ │ │ └── union.js
│ │ │ ├── errors.d.ts
│ │ │ ├── errors.js
│ │ │ ├── external.d.ts
│ │ │ ├── external.js
│ │ │ ├── helpers
│ │ │ │ ├── enumUtil.d.ts
│ │ │ │ ├── enumUtil.js
│ │ │ │ ├── errorUtil.d.ts
│ │ │ │ ├── errorUtil.js
│ │ │ │ ├── parseUtil.d.ts
│ │ │ │ ├── parseUtil.js
│ │ │ │ ├── partialUtil.d.ts
│ │ │ │ ├── partialUtil.js
│ │ │ │ ├── typeAliases.d.ts
│ │ │ │ ├── typeAliases.js
│ │ │ │ ├── util.d.ts
│ │ │ │ └── util.js
│ │ │ ├── index.d.ts
│ │ │ ├── index.js
│ │ │ ├── index.mjs
│ │ │ ├── index.umd.js
│ │ │ ├── locales
│ │ │ │ ├── en.d.ts
│ │ │ │ └── en.js
│ │ │ ├── standard-schema.d.ts
│ │ │ ├── standard-schema.js
│ │ │ ├── types.d.ts
│ │ │ ├── types.js
│ │ │ ├── ZodError.d.ts
│ │ │ └── ZodError.js
│ │ ├── LICENSE
│ │ ├── package.json
│ │ └── README.md
│ └── zod-to-json-schema
│ ├── .github
│ │ ├── CR_logotype-full-color.png
│ │ └── FUNDING.yml
│ ├── .prettierrc.json
│ ├── changelog.md
│ ├── contributing.md
│ ├── createIndex.ts
│ ├── dist
│ │ ├── cjs
│ │ │ ├── errorMessages.js
│ │ │ ├── index.js
│ │ │ ├── Options.js
│ │ │ ├── package.json
│ │ │ ├── parseDef.js
│ │ │ ├── parsers
│ │ │ │ ├── any.js
│ │ │ │ ├── array.js
│ │ │ │ ├── bigint.js
│ │ │ │ ├── boolean.js
│ │ │ │ ├── branded.js
│ │ │ │ ├── catch.js
│ │ │ │ ├── date.js
│ │ │ │ ├── default.js
│ │ │ │ ├── effects.js
│ │ │ │ ├── enum.js
│ │ │ │ ├── intersection.js
│ │ │ │ ├── literal.js
│ │ │ │ ├── map.js
│ │ │ │ ├── nativeEnum.js
│ │ │ │ ├── never.js
│ │ │ │ ├── null.js
│ │ │ │ ├── nullable.js
│ │ │ │ ├── number.js
│ │ │ │ ├── object.js
│ │ │ │ ├── optional.js
│ │ │ │ ├── pipeline.js
│ │ │ │ ├── promise.js
│ │ │ │ ├── readonly.js
│ │ │ │ ├── record.js
│ │ │ │ ├── set.js
│ │ │ │ ├── string.js
│ │ │ │ ├── tuple.js
│ │ │ │ ├── undefined.js
│ │ │ │ ├── union.js
│ │ │ │ └── unknown.js
│ │ │ ├── parseTypes.js
│ │ │ ├── Refs.js
│ │ │ ├── selectParser.js
│ │ │ └── zodToJsonSchema.js
│ │ ├── esm
│ │ │ ├── errorMessages.js
│ │ │ ├── index.js
│ │ │ ├── Options.js
│ │ │ ├── package.json
│ │ │ ├── parseDef.js
│ │ │ ├── parsers
│ │ │ │ ├── any.js
│ │ │ │ ├── array.js
│ │ │ │ ├── bigint.js
│ │ │ │ ├── boolean.js
│ │ │ │ ├── branded.js
│ │ │ │ ├── catch.js
│ │ │ │ ├── date.js
│ │ │ │ ├── default.js
│ │ │ │ ├── effects.js
│ │ │ │ ├── enum.js
│ │ │ │ ├── intersection.js
│ │ │ │ ├── literal.js
│ │ │ │ ├── map.js
│ │ │ │ ├── nativeEnum.js
│ │ │ │ ├── never.js
│ │ │ │ ├── null.js
│ │ │ │ ├── nullable.js
│ │ │ │ ├── number.js
│ │ │ │ ├── object.js
│ │ │ │ ├── optional.js
│ │ │ │ ├── pipeline.js
│ │ │ │ ├── promise.js
│ │ │ │ ├── readonly.js
│ │ │ │ ├── record.js
│ │ │ │ ├── set.js
│ │ │ │ ├── string.js
│ │ │ │ ├── tuple.js
│ │ │ │ ├── undefined.js
│ │ │ │ ├── union.js
│ │ │ │ └── unknown.js
│ │ │ ├── parseTypes.js
│ │ │ ├── Refs.js
│ │ │ ├── selectParser.js
│ │ │ └── zodToJsonSchema.js
│ │ └── types
│ │ ├── errorMessages.d.ts
│ │ ├── index.d.ts
│ │ ├── Options.d.ts
│ │ ├── parseDef.d.ts
│ │ ├── parsers
│ │ │ ├── any.d.ts
│ │ │ ├── array.d.ts
│ │ │ ├── bigint.d.ts
│ │ │ ├── boolean.d.ts
│ │ │ ├── branded.d.ts
│ │ │ ├── catch.d.ts
│ │ │ ├── date.d.ts
│ │ │ ├── default.d.ts
│ │ │ ├── effects.d.ts
│ │ │ ├── enum.d.ts
│ │ │ ├── intersection.d.ts
│ │ │ ├── literal.d.ts
│ │ │ ├── map.d.ts
│ │ │ ├── nativeEnum.d.ts
│ │ │ ├── never.d.ts
│ │ │ ├── null.d.ts
│ │ │ ├── nullable.d.ts
│ │ │ ├── number.d.ts
│ │ │ ├── object.d.ts
│ │ │ ├── optional.d.ts
│ │ │ ├── pipeline.d.ts
│ │ │ ├── promise.d.ts
│ │ │ ├── readonly.d.ts
│ │ │ ├── record.d.ts
│ │ │ ├── set.d.ts
│ │ │ ├── string.d.ts
│ │ │ ├── tuple.d.ts
│ │ │ ├── undefined.d.ts
│ │ │ ├── union.d.ts
│ │ │ └── unknown.d.ts
│ │ ├── parseTypes.d.ts
│ │ ├── Refs.d.ts
│ │ ├── selectParser.d.ts
│ │ └── zodToJsonSchema.d.ts
│ ├── LICENSE
│ ├── package.json
│ ├── postcjs.ts
│ ├── postesm.ts
│ ├── README.md
│ └── SECURITY.md
├── package-lock.json
├── package.json
├── README.md
├── serverMCP.js
└── terminalManager.js
```
# Files
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
```markdown
# MalwareAnalyzerMCP
A specialized MCP server for Claude Desktop that allows executing terminal commands for malware analysis.
## Features
- Execute terminal commands with configurable timeouts
- Read output from running or completed processes
- Specialized malware analysis commands (`file`, `strings`, `hexdump`, `objdump`, `xxd`)
- Clean process management with graceful shutdowns
- Pure JavaScript implementation - no build step required
## Installation
```bash
# Install dependencies
npm install
```
## Usage
### Running the Server
```bash
# Start the server directly
node index.js
# Or use npm script
npm start
# With debugging proxy (logs all communications)
npm run debug
```
### Integration with Claude Desktop
To integrate this MCP server with Claude Desktop:
1. Open Claude Desktop's settings (Claude menu → Settings)
2. Click on "Developer" and then "Edit Config"
3. Update your configuration to include:
```json
{
"mcpServers": {
"MalwareAnalysisMCP": {
"command": "node",
"args": [
"/path/to/MalwareAnalysisMCP/index.js"
]
}
}
}
```
> **Note**: Replace `/path/to/MalwareAnalysisMCP` with the actual path to your project directory.
4. Restart Claude Desktop
## Debugging
To see all communication between Claude Desktop and the MCP server:
1. Update your Claude Desktop configuration to use the debug proxy:
```json
{
"mcpServers": {
"MalwareAnalysisMCP": {
"command": "node",
"args": [
"/path/to/MalwareAnalysisMCP/mcp-debug-proxy.js"
]
}
}
}
```
2. Check the logs in the `logs` directory
## Compatibility Notes
- Requires Node.js 18 or higher
- Compatible with Node.js v22+ using ESM modules
## API
### Basic Tools
#### shell_command
Executes a terminal command and returns its process ID, output, and blocked status.
Parameters:
- `command` (string): The command to execute in the terminal
- `timeout_ms` (number, optional): Timeout in milliseconds (default: 30000)
Returns:
- `pid` (number): Process ID
- `output` (string): Command output
- `isBlocked` (boolean): Whether the command execution is blocked/timed out
#### read_output
Reads output from a running or completed process.
Parameters:
- `pid` (number): The process ID to read output from
Returns:
- `output` (string | null): The process output, or null if the process is not found
### Specialized Malware Analysis Tools
The following specialized tools are available for malware analysis:
#### file
Analyze a file and determine its type.
Parameters:
- `target` (string): Target file to analyze
- `options` (string, optional): Additional command-line options
Example:
```json
{
"target": "suspicious.exe",
"options": "-b"
}
```
#### strings
Extract printable strings from a file.
Parameters:
- `target` (string): Target file to analyze
- `minLength` (number, optional): Minimum string length to display
- `encoding` (string, optional): String encoding (s=7-bit, S=8-bit, b=16-bit big-endian, l=16-bit little-endian, etc.)
- `options` (string, optional): Additional command-line options
Example:
```json
{
"target": "suspicious.exe",
"minLength": 10,
"encoding": "l"
}
```
#### hexdump
Display file contents in hexadecimal format.
Parameters:
- `target` (string): Target file to analyze
- `length` (number, optional): Number of bytes to display
- `offset` (number, optional): Starting offset in the file
- `options` (string, optional): Additional command-line options
Example:
```json
{
"target": "suspicious.exe",
"length": 256,
"offset": 1024
}
```
#### objdump
Display information from object files.
Parameters:
- `target` (string): Target file to analyze
- `disassemble` (boolean, optional): Disassemble executable sections
- `headers` (boolean, optional): Display the contents of the section headers
- `options` (string, optional): Additional command-line options
Example:
```json
{
"target": "suspicious.exe",
"disassemble": true
}
```
#### xxd
Create a hexdump with ASCII representation.
Parameters:
- `target` (string): Target file to analyze
- `length` (number, optional): Number of bytes to display
- `offset` (number, optional): Starting offset in the file
- `cols` (number, optional): Format output into specified number of columns
- `bits` (boolean, optional): Switch to bits (binary) dump
- `options` (string, optional): Additional command-line options
Example:
```json
{
"target": "suspicious.exe",
"cols": 16,
"bits": true
}
```
## License
ISC
```
--------------------------------------------------------------------------------
/.vscode/settings.json:
--------------------------------------------------------------------------------
```json
{
"workbench.colorCustomizations": {
"editorIndentGuide.activeBackground": "#ffea00",
"editorIndentGuide.background": "#ff00ff",
"tree.indentGuidesStroke": "#0073ff"
}
}
```
--------------------------------------------------------------------------------
/index.js:
--------------------------------------------------------------------------------
```javascript
#!/usr/bin/env node
/**
* MalwareAnalyzerMCP - Main Entry Point
*
* This file serves as the main entry point for the MalwareAnalyzerMCP server.
* It simply imports and runs the serverMCP.js module.
*/
import './serverMCP.js';
// The server is started by the imported module.
```
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
```json
{
"name": "malwareanalyzermcp",
"version": "1.0.0",
"description": "A specialized MCP server for Claude Desktop that allows executing terminal commands for malware analysis.",
"main": "index.js",
"type": "module",
"bin": {
"malwareanalyzermcp": "index.js"
},
"scripts": {
"start": "node index.js",
"debug": "node loader.js"
},
"keywords": [
"mcp",
"claude",
"malware",
"analysis",
"terminal"
],
"author": "",
"license": "ISC",
"dependencies": {
"@modelcontextprotocol/sdk": "^1.11.0",
"zod": "^3.24.3",
"zod-to-json-schema": "^3.24.5"
},
"engines": {
"node": ">=18.0.0"
}
}
```
--------------------------------------------------------------------------------
/loader.js:
--------------------------------------------------------------------------------
```javascript
import { spawn } from 'child_process';
import fs from 'fs';
import path from 'path';
import { fileURLToPath } from 'url';
// Get current file directory (equivalent to __dirname in CommonJS)
const __filename = fileURLToPath(import.meta.url);
const __dirname = path.dirname(__filename);
// Configure paths
const serverPath = path.resolve(__dirname, './serverMCP.js');
const logDir = path.resolve(__dirname, './logs');
const logFile = path.join(logDir, `mcp-debug-${new Date().toISOString().replace(/:/g, '-')}.log`);
// Ensure log directory exists
if (!fs.existsSync(logDir)) {
fs.mkdirSync(logDir, { recursive: true });
}
// Create log stream
const logger = fs.createWriteStream(logFile, { flags: 'a' });
// Log startup information
logger.write(`\n\n=== MCP DEBUG PROXY STARTED AT ${new Date().toISOString()} ===\n\n`);
console.error(`[PROXY] Starting debug proxy for ${serverPath}`);
console.error(`[PROXY] Logging to ${logFile}`);
// Spawn the real MCP server
const realServer = spawn('node', [serverPath], {
stdio: ['pipe', 'pipe', 'inherit'] // Redirect stderr to parent process
});
// Log messages with timestamp and direction
function logMessage(direction, data) {
const timestamp = new Date().toISOString();
const separator = '='.repeat(80);
try {
// Try to parse and pretty-print if it's JSON
const jsonData = JSON.parse(data.toString().trim());
const prettyJson = JSON.stringify(jsonData, null, 2);
logger.write(`\n${separator}\n[${timestamp}] ${direction}\n${separator}\n${prettyJson}\n`);
} catch (e) {
// If not JSON or parse error, log as raw string
const dataStr = data.toString().trim();
logger.write(`\n${separator}\n[${timestamp}] ${direction} (RAW)\n${separator}\n${dataStr}\n`);
}
}
// Intercept stdin (Claude -> Server)
process.stdin.on('data', (data) => {
logMessage('CLAUDE → SERVER', data);
// Forward to real server
if (!realServer.stdin.write(data)) {
process.stdin.pause();
realServer.stdin.once('drain', () => {
process.stdin.resume();
});
}
});
// Intercept stdout (Server -> Claude)
realServer.stdout.on('data', (data) => {
logMessage('SERVER → CLAUDE', data);
// Forward to Claude
if (!process.stdout.write(data)) {
realServer.stdout.pause();
process.stdout.once('drain', () => {
realServer.stdout.resume();
});
}
});
// Handle process events
realServer.on('exit', (code, signal) => {
logger.write(`\n\n=== SERVER EXITED (code: ${code}, signal: ${signal}) AT ${new Date().toISOString()} ===\n\n`);
console.error(`[PROXY] Server exited with code ${code} (signal: ${signal})`);
process.exit(code);
});
process.on('SIGINT', () => {
logger.write(`\n\n=== PROXY RECEIVED SIGINT AT ${new Date().toISOString()} ===\n\n`);
console.error(`[PROXY] Received SIGINT, shutting down`);
realServer.kill('SIGINT');
});
process.on('SIGTERM', () => {
logger.write(`\n\n=== PROXY RECEIVED SIGTERM AT ${new Date().toISOString()} ===\n\n`);
console.error(`[PROXY] Received SIGTERM, shutting down`);
realServer.kill('SIGTERM');
});
// Log uncaught exceptions to avoid crashes
process.on('uncaughtException', (err) => {
logger.write(`\n\n=== PROXY ERROR AT ${new Date().toISOString()} ===\n${err.stack}\n\n`);
console.error(`[PROXY] Uncaught exception:`, err);
});
```
--------------------------------------------------------------------------------
/terminalManager.js:
--------------------------------------------------------------------------------
```javascript
/**
* Terminal Manager for MalwareAnalyzerMCP
* Manages terminal processes, executes commands, and reads output
*
* @author: abdessamad el amrani ,
*/
import { spawn } from 'child_process';
const DEF_TIMEOUT = 40000;
export class TerminalManager {
constructor() {
// Map of active terminal sessions by PID
this.sessions = new Map();
// Map of completed sessions by PID
this.completedSessions = new Map();
}
/**
* Execute a terminal command with optional timeout
* @param {string} command - The command to execute
* @param {number} timeoutMs - Timeout
* @returns {Promise<object>} Result with pid, output, and blocked status
*/
async shellCommand(command, timeoutMs = DEF_TIMEOUT) {
const process = spawn(command, [], { shell: true });
let output = '';
// Ensure process.pid is defined before proceeding
if (!process.pid) {
return {
pid: -1, // Use -1 to indicate an error state
output: 'Error: Failed to get process ID. The command could not be executed.',
isBlocked: false
};
}
// Create a session object to track this process
const session = {
pid: process.pid,
process,
lastOutput: '',
isBlocked: false,
startTime: new Date()
};
this.sessions.set(process.pid, session);
return new Promise((resolve) => {
// Handle standard output
process.stdout.on('data', (data) => {
const text = data.toString();
output += text;
session.lastOutput += text;
});
// Handle error output
process.stderr.on('data', (data) => {
const text = data.toString();
output += text;
session.lastOutput += text;
});
// Set timeout to mark process as blocked if it exceeds timeoutMs
setTimeout(() => {
session.isBlocked = true;
resolve({
pid: process.pid,
output,
isBlocked: true
});
}, timeoutMs);
// Handle process completion
process.on('exit', (code) => {
if (process.pid) {
// Store completed session before removing active session
this.completedSessions.set(process.pid, {
pid: process.pid,
output: output + session.lastOutput, // Combine all output
exitCode: code,
startTime: session.startTime,
endTime: new Date()
});
// Keep only last 50 completed sessions
if (this.completedSessions.size > 50) {
const oldestKey = Array.from(this.completedSessions.keys())[0];
this.completedSessions.delete(oldestKey);
}
this.sessions.delete(process.pid);
}
resolve({
pid: process.pid,
output,
isBlocked: false
});
});
});
}
/**
* Read output from a running or completed process
* @param {number} pid - Process ID to read output from
* @returns {object} Result with output string or null
*/
readOutput(pid) {
// First check active sessions
const session = this.sessions.get(pid);
if (session) {
const output = session.lastOutput;
session.lastOutput = ''; // Clear the buffer after reading
return { output };
}
// Then check completed sessions
const completedSession = this.completedSessions.get(pid);
if (completedSession) {
// Format completion message with exit code and runtime
const runtime = (completedSession.endTime.getTime() - completedSession.startTime.getTime()) / 1000;
const outputStr = `Process completed with exit code ${completedSession.exitCode}\nRuntime: ${runtime.toFixed(2)}s\nFinal output:\n${completedSession.output}`;
// Remove from completed sessions as we've delivered the final output
this.completedSessions.delete(pid);
return { output: outputStr };
}
// Return null if PID not found
return { output: null };
}
/**
* Get status of terminal manager
* @returns {object} Count of active and completed sessions
*/
getStatus() {
return {
activeSessions: this.sessions.size,
completedSessions: this.completedSessions.size
};
}
/**
* Shut down the terminal manager and terminate all processes
*/
shutdown() {
// Terminate all active sessions
for (const session of this.sessions.values()) {
try {
session.process.kill('SIGINT');
setTimeout(() => {
session.process.kill('SIGKILL');
}, 500);
} catch (error) {
console.error(`Failed to terminate process ${session.pid}:`, error);
}
}
this.sessions.clear();
this.completedSessions.clear();
}
}
```
--------------------------------------------------------------------------------
/IMPLEMENTATION.md:
--------------------------------------------------------------------------------
```markdown
# MalwareAnalyzerMCP Implementation
This document describes the implementation details of the MalwareAnalyzerMCP server, with a particular focus on the specialized malware analysis commands.
## Project Structure
The project consists of several key files:
- `index.js` - Main entry point that imports and runs the server
- `serverMCP.js` - Core MCP server implementation with tool handlers
- `terminalManager.js` - Manages terminal processes, executes commands, and reads output
- `commands.js` - Configuration for specialized malware analysis commands
- `loader.js` - Debug proxy for logging communications between Claude and the server
## Implementation Approach
For the specialized malware analysis commands, a configuration-driven approach was chosen to maximize code reuse and make it easy to add new commands in the future.
### Design Decision
Three potential designs were considered:
1. **Direct Extension** - Adding each new tool as a completely separate MCP tool with its own schema and handler
2. **Specialized Command Factory** - Creating a command factory that generates commands based on tool name
3. **Command Configuration Approach** - Defining a configuration object for each command with its parameters and logic
The **Command Configuration Approach** was selected for its balance of flexibility, maintainability, and code reuse.
### Key Components
#### 1. Command Configuration (`commands.js`)
Each specialized command is defined as an object with:
- `name`: Command name
- `description`: Human-readable description
- `schema`: Zod schema for validating parameters
- `buildCommand`: Function to construct the command string from parameters
- `helpText`: Usage examples
All commands share a base schema with common parameters:
- `target`: Target file to analyze
- `options`: Additional command-line options
Each command then extends this base schema with its own specific parameters.
```javascript
export const commands = {
file: {
name: 'file',
description: 'Analyze a file and determine its type',
schema: baseCommandSchema,
buildCommand: (args) => {...},
helpText: '...'
},
// Additional commands...
};
```
#### 2. MCP Server Integration (`serverMCP.js`)
The server integrates the specialized commands in two main ways:
1. **Tool Registration**:
```javascript
const specializedTools = Object.values(commands).map(cmd => ({
name: cmd.name,
description: cmd.description + (cmd.helpText ? '\n' + cmd.helpText : ''),
inputSchema: zodToJsonSchema(cmd.schema),
}));
```
2. **Command Execution**:
```javascript
if (commands[name]) {
// Validate arguments against schema
const validationResult = cmdConfig.schema.safeParse(args);
// Build the command string
const commandStr = cmdConfig.buildCommand(validationResult.data);
// Execute via terminal manager
const result = await terminalManager.shellCommand(commandStr);
}
```
#### 3. Terminal Manager (`terminalManager.js`)
The `TerminalManager` class provides the core functionality for executing commands and tracking their output. Key methods:
- `shellCommand(command, timeoutMs)`: Executes a command and returns a promise with result
- `readOutput(pid)`: Reads output from a running or completed process
- `shutdown()`: Terminates all active processes
## Execution Flow
1. Claude sends a request to execute a specialized command (e.g., `strings`)
2. The server validates the request parameters against the command's schema
3. The `buildCommand` function constructs the command string with all options
4. The command is executed via the `TerminalManager.shellCommand` method
5. The command's output is captured and made available via the `read_output` tool
## Adding New Commands
To add a new specialized command:
1. Add a new entry to the `commands` object in `commands.js`
2. Define the command's schema, extending `baseCommandSchema` as needed
3. Implement the `buildCommand` function to construct the command string
4. Add usage examples in the `helpText` property
No changes to `serverMCP.js` are required, as it automatically discovers and registers all commands defined in the configuration.
## Security Considerations
- All user input is validated against defined schemas
- Command execution is handled through the `spawn` function from Node.js `child_process` module
- Timeouts prevent long-running commands from blocking the server
- Process termination is gracefully handled during shutdown
## Error Handling
Errors at different levels are handled appropriately:
1. Schema validation errors return detailed feedback
2. Command execution errors are logged and reported
3. Process errors are captured and included in the output
## Future Improvements
Potential enhancements:
1. Add file path validation to prevent path traversal attacks
2. Implement command caching to improve performance for repeated analyses
3. Add support for batch processing of multiple files
4. Create specialized output parsers for structured results
5. Add support for command chaining and pipelines
```
--------------------------------------------------------------------------------
/commands.js:
--------------------------------------------------------------------------------
```javascript
/**
* Malware Analysis Commands Configuration
*
* This file contains the configuration for specialized malware analysis commands.
* Each command has a name, description, arguments schema, and optional help text.
*/
import { z } from 'zod';
/**
* Base schema for all malware analysis commands
* Common parameters that apply to most commands
*/
const baseCommandSchema = z.object({
target: z.string().min(1).describe("Target file or data to analyze"),
options: z.string().optional().describe("Additional command-line options")
});
/**
* Command configuration object
* Defines each specialized command with its parameters and description
*/
export const commands = {
// File command - determine file type
file: {
name: 'file',
description: 'Analyze a file and determine its type',
schema: baseCommandSchema,
buildCommand: (args) => {
const options = args.options ? args.options : '';
return `file ${options} ${args.target}`;
},
helpText: `
Example usage:
- Basic file identification: { "target": "suspicious.exe" }
- With options: { "target": "suspicious.exe", "options": "-b" }
`
},
// Strings command - extract printable strings
strings: {
name: 'strings',
description: 'Extract printable strings from a file',
schema: baseCommandSchema.extend({
minLength: z.number().optional().describe("Minimum string length to display"),
encoding: z.enum(['s', 'S', 'b', 'l', 'B', 'L']).optional().describe("String encoding (s=7-bit, S=8-bit, b=16-bit big-endian, l=16-bit little-endian, etc.)")
}),
buildCommand: (args) => {
let options = args.options ? args.options : '';
if (args.minLength) {
options += ` -n ${args.minLength}`;
}
if (args.encoding) {
options += ` -e ${args.encoding}`;
}
return `strings ${options} ${args.target}`;
},
helpText: `
Example usage:
- Basic strings extraction: { "target": "suspicious.exe" }
- With minimum length: { "target": "suspicious.exe", "minLength": 10 }
- With encoding: { "target": "suspicious.exe", "encoding": "l" }
`
},
// Hexdump command - display file contents in hex format
hexdump: {
name: 'hexdump',
description: 'Display file contents in hexadecimal format',
schema: baseCommandSchema.extend({
length: z.number().optional().describe("Number of bytes to display"),
offset: z.number().optional().describe("Starting offset in the file")
}),
buildCommand: (args) => {
let options = args.options ? args.options : '-C'; // Default to canonical hex+ASCII display
if (args.length) {
options += ` -n ${args.length}`;
}
if (args.offset) {
options += ` -s ${args.offset}`;
}
return `hexdump ${options} ${args.target}`;
},
helpText: `
Example usage:
- Standard hexdump: { "target": "suspicious.exe" }
- With length limit: { "target": "suspicious.exe", "length": 256 }
- With offset: { "target": "suspicious.exe", "offset": 1024 }
`
},
// Objdump command - display object file information
objdump: {
name: 'objdump',
description: 'Display information from object files',
schema: baseCommandSchema.extend({
disassemble: z.boolean().optional().describe("Disassemble executable sections"),
headers: z.boolean().optional().describe("Display the contents of the section headers")
}),
buildCommand: (args) => {
let options = args.options ? args.options : '';
if (args.disassemble) {
options += ' -d';
}
if (args.headers) {
options += ' -h';
}
// Default to displaying file headers if no specific options provided
if (!options && !args.disassemble && !args.headers) {
options = ' -f';
}
return `objdump${options} ${args.target}`;
},
helpText: `
Example usage:
- Display file headers: { "target": "suspicious.o" }
- Disassemble code: { "target": "suspicious.exe", "disassemble": true }
- Show section headers: { "target": "suspicious.exe", "headers": true }
`
},
// XXD command - hexdump with ASCII representation
xxd: {
name: 'xxd',
description: 'Create a hexdump with ASCII representation',
schema: baseCommandSchema.extend({
length: z.number().optional().describe("Number of bytes to display"),
offset: z.number().optional().describe("Starting offset in the file"),
cols: z.number().optional().describe("Format output into specified number of columns"),
bits: z.boolean().optional().describe("Switch to bits (binary) dump")
}),
buildCommand: (args) => {
let options = args.options ? args.options : '';
if (args.length) {
options += ` -l ${args.length}`;
}
if (args.offset) {
options += ` -s ${args.offset}`;
}
if (args.cols) {
options += ` -c ${args.cols}`;
}
if (args.bits) {
options += ' -b';
}
return `xxd ${options} ${args.target}`;
},
helpText: `
Example usage:
- Standard xxd dump: { "target": "suspicious.exe" }
- With length limit: { "target": "suspicious.exe", "length": 256 }
- With column formatting: { "target": "suspicious.exe", "cols": 16 }
- Binary bits mode: { "target": "suspicious.exe", "bits": true }
`
}
};
```
--------------------------------------------------------------------------------
/serverMCP.js:
--------------------------------------------------------------------------------
```javascript
#!/usr/bin/env node
/**
* MalwareAnalyzerMCP
*
* MCP server for Claude Desktop that allows executing terminal commands for malware analysis.
* Implements the Model Context Protocol with tools for command execution and output reading.
*/
import { Server } from '@modelcontextprotocol/sdk/server/index.js';
import { CallToolRequestSchema, ListToolsRequestSchema } from '@modelcontextprotocol/sdk/types.js';
import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js';
import { zodToJsonSchema } from 'zod-to-json-schema';
import { z } from 'zod';
import { TerminalManager } from './terminalManager.js';
import { commands } from './commands.js';
/**
* Custom stdio transport with filtering capability
* Handles communication between Claude Desktop and our server
*/
class FilteredStdioTransport extends StdioServerTransport {
constructor() {
// Create a proxy for stdout that only allows valid JSON
const originalStdoutWrite = process.stdout.write;
process.stdout.write = function(buffer) {
// Only intercept string output that doesn't look like JSON
if (typeof buffer === 'string' && !buffer.trim().startsWith('{')) {
return process.stderr.write(buffer);
}
return originalStdoutWrite.apply(process.stdout, arguments);
};
super();
// Log initialization to stderr
process.stderr.write(`[malware-analyzer] Initialized FilteredStdioTransport\n`);
}
}
/**
* Schema for shellCommand tool
* Defines parameters for executing terminal commands
*/
const shellCommandSchema = z.object({
command: z.string().min(1).describe("The command to execute in the terminal"),
timeout_ms: z.number().optional().describe("Optional timeout in milliseconds (default: 30000)")
});
/**
* Schema for read_output tool
* Defines parameters for reading process output
*/
const readOutputSchema = z.object({
pid: z.number().int().describe("The process ID to read output from")
});
/**
* Main entry point for the MCP server
* Configures and starts the server with tool handlers
*/
async function main() {
try {
// Setup error handling
process.on('uncaughtException', (error) => {
console.error(`Uncaught exception: ${error instanceof Error ? error.message : String(error)}`);
process.exit(1);
});
process.on('unhandledRejection', (reason) => {
console.error(`Unhandled rejection: ${reason instanceof Error ? reason.message : String(reason)}`);
process.exit(1);
});
console.error("Initializing MalwareAnalyzerMCP server...");
// Initialize transport
const transport = new FilteredStdioTransport();
// Initialize terminal manager for process handling
const terminalManager = new TerminalManager();
// Create server instance
const server = new Server(
{
name: "malware-analyzer",
version: "1.0.0",
},
{
capabilities: {
tools: {}, // Enable tools capability
},
}
);
// Configure tools list handler
server.setRequestHandler(ListToolsRequestSchema, async () => {
// List of basic tools
const basicTools = [
{
name: 'shell_command',
description: 'Execute a command in the terminal with timeout. Command will continue running in background if it doesn\'t complete within timeout.',
inputSchema: zodToJsonSchema(shellCommandSchema),
},
{
name: 'read_output',
description: 'Read output from a running or completed process.',
inputSchema: zodToJsonSchema(readOutputSchema),
},
];
// Generate tools from commands configuration
const specializedTools = Object.values(commands).map(cmd => ({
name: cmd.name,
description: cmd.description + (cmd.helpText ? '\n' + cmd.helpText : ''),
inputSchema: zodToJsonSchema(cmd.schema),
}));
return {
tools: [...basicTools, ...specializedTools],
};
});
// Configure tool execution handler
server.setRequestHandler(CallToolRequestSchema, async (request) => {
try {
const { name, arguments: args } = request.params;
// Check if this is a specialized command
if (commands[name]) {
try {
const cmdConfig = commands[name];
// Validate arguments against schema
const validationResult = cmdConfig.schema.safeParse(args);
if (!validationResult.success) {
return {
content: [{
type: "text",
text: `Error: Invalid parameters for ${name} command.\n${JSON.stringify(validationResult.error.format())}`
}],
isError: true,
};
}
// Build the command string
const commandStr = cmdConfig.buildCommand(validationResult.data);
console.error(`Executing specialized command: ${commandStr}`);
// Execute the command via the terminal manager
const result = await terminalManager.shellCommand(commandStr);
console.error(`${name} command executed with PID: ${result.pid}, blocked: ${result.isBlocked}`);
return {
content: [{ type: "text", text: JSON.stringify(result) }],
};
} catch (error) {
console.error(`Error executing ${name} command:`, error);
return {
content: [{ type: "text", text: `Error: ${error instanceof Error ? error.message : String(error)}` }],
isError: true,
};
}
}
// Handle basic tools
switch (name) {
case 'shell_command':
try {
// Type-check and validate arguments
if (!args || typeof args.command !== 'string') {
return {
content: [{ type: "text", text: "Error: Invalid command parameter" }],
isError: true,
};
}
console.error(`Executing command: ${args.command}`);
const result = await terminalManager.shellCommand(
args.command,
typeof args.timeout_ms === 'number' ? args.timeout_ms : undefined
);
console.error(`Command executed with PID: ${result.pid}, blocked: ${result.isBlocked}`);
return {
content: [{ type: "text", text: JSON.stringify(result) }],
};
} catch (error) {
console.error('Error executing command:', error);
return {
content: [{ type: "text", text: `Error: ${error instanceof Error ? error.message : String(error)}` }],
isError: true,
};
}
case 'read_output':
try {
// Type-check and validate arguments
if (!args || typeof args.pid !== 'number') {
return {
content: [{ type: "text", text: "Error: Invalid PID parameter" }],
isError: true,
};
}
console.error(`Reading output for PID: ${args.pid}`);
const result = terminalManager.readOutput(args.pid);
return {
content: [{ type: "text", text: JSON.stringify(result) }],
};
} catch (error) {
console.error('Error reading output:', error);
return {
content: [{ type: "text", text: `Error: ${error instanceof Error ? error.message : String(error)}` }],
isError: true,
};
}
default:
return {
content: [{ type: "text", text: `Error: Unknown tool: ${name}` }],
isError: true,
};
}
} catch (error) {
const errorMessage = error instanceof Error ? error.message : String(error);
return {
content: [{ type: "text", text: `Error: ${errorMessage}` }],
isError: true,
};
}
});
// Setup graceful shutdown handler
const cleanup = () => {
console.error('Initiating server cleanup...');
terminalManager.shutdown();
server.close().then(() => {
console.error('Server closed.');
process.exit(0);
}).catch((err) => {
console.error('Error closing server:', err);
process.exit(1);
});
// Force exit after a timeout if cleanup hangs
setTimeout(() => {
console.error('Cleanup timed out. Forcing exit.');
process.exit(1);
}, 5000);
};
// Register shutdown handlers
process.on('SIGINT', cleanup);
process.on('SIGTERM', cleanup);
// Connect server to transport
console.error('Starting MalwareAnalyzerMCP server...');
await server.connect(transport);
console.error('Server started and listening.');
} catch (error) {
console.error('Fatal error during server startup:');
console.error(error instanceof Error ? error.message : String(error));
console.error(error instanceof Error && error.stack ? error.stack : 'No stack trace available');
process.exit(1);
}
}
// Start the server
main().catch(error => {
console.error('Fatal error during server initialization:');
console.error(error instanceof Error ? error.message : String(error));
process.exit(1);
});
```