fastmcp 3.35.0 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/FastMCP.cjs +2 -2
- package/dist/FastMCP.d.cts +2 -2
- package/dist/FastMCP.d.ts +2 -2
- package/dist/FastMCP.js +1 -1
- package/dist/{OAuthProvider-R8buLRa8.d.cts → OAuthProvider-BV6EpF_k.d.cts} +38 -3
- package/dist/{OAuthProvider-R8buLRa8.d.ts → OAuthProvider-BV6EpF_k.d.ts} +38 -3
- package/dist/auth/index.cjs +2 -2
- package/dist/auth/index.d.cts +2 -2
- package/dist/auth/index.d.ts +2 -2
- package/dist/auth/index.js +1 -1
- package/dist/{chunk-7UDY4VFQ.cjs → chunk-SSVFQCSN.cjs} +99 -46
- package/dist/chunk-SSVFQCSN.cjs.map +1 -0
- package/dist/{chunk-H4VC4YTC.js → chunk-UN72PIH2.js} +96 -43
- package/dist/chunk-UN72PIH2.js.map +1 -0
- package/dist/examples/custom-routes.cjs +1 -1
- package/dist/examples/custom-routes.js +1 -1
- package/package.json +1 -1
- package/dist/chunk-7UDY4VFQ.cjs.map +0 -1
- package/dist/chunk-H4VC4YTC.js.map +0 -1
package/dist/FastMCP.cjs
CHANGED
|
@@ -20,7 +20,7 @@ var _chunkJP7QSER3cjs = require('./chunk-JP7QSER3.cjs');
|
|
|
20
20
|
|
|
21
21
|
|
|
22
22
|
|
|
23
|
-
var
|
|
23
|
+
var _chunkSSVFQCSNcjs = require('./chunk-SSVFQCSN.cjs');
|
|
24
24
|
|
|
25
25
|
|
|
26
26
|
|
|
@@ -41,5 +41,5 @@ var _chunk7UDY4VFQcjs = require('./chunk-7UDY4VFQ.cjs');
|
|
|
41
41
|
|
|
42
42
|
|
|
43
43
|
|
|
44
|
-
exports.AuthProvider =
|
|
44
|
+
exports.AuthProvider = _chunkSSVFQCSNcjs.AuthProvider; exports.AzureProvider = _chunkSSVFQCSNcjs.AzureProvider; exports.DiscoveryDocumentCache = _chunkJP7QSER3cjs.DiscoveryDocumentCache; exports.FastMCP = _chunkJP7QSER3cjs.FastMCP; exports.FastMCPSession = _chunkJP7QSER3cjs.FastMCPSession; exports.GitHubProvider = _chunkSSVFQCSNcjs.GitHubProvider; exports.GoogleProvider = _chunkSSVFQCSNcjs.GoogleProvider; exports.OAuthProvider = _chunkSSVFQCSNcjs.OAuthProvider; exports.ServerState = _chunkJP7QSER3cjs.ServerState; exports.UnexpectedStateError = _chunkJP7QSER3cjs.UnexpectedStateError; exports.UserError = _chunkJP7QSER3cjs.UserError; exports.audioContent = _chunkJP7QSER3cjs.audioContent; exports.getAuthSession = _chunkSSVFQCSNcjs.getAuthSession; exports.imageContent = _chunkJP7QSER3cjs.imageContent; exports.requireAll = _chunkSSVFQCSNcjs.requireAll; exports.requireAny = _chunkSSVFQCSNcjs.requireAny; exports.requireAuth = _chunkSSVFQCSNcjs.requireAuth; exports.requireRole = _chunkSSVFQCSNcjs.requireRole; exports.requireScopes = _chunkSSVFQCSNcjs.requireScopes;
|
|
45
45
|
//# sourceMappingURL=FastMCP.cjs.map
|
package/dist/FastMCP.d.cts
CHANGED
|
@@ -10,8 +10,8 @@ import { Hono } from 'hono';
|
|
|
10
10
|
import http from 'http';
|
|
11
11
|
import { StrictEventEmitter } from 'strict-event-emitter-types';
|
|
12
12
|
import { z } from 'zod';
|
|
13
|
-
import { A as AuthProvider, O as OAuthSession, a as OAuthProxy } from './OAuthProvider-
|
|
14
|
-
export { j as AuthProviderConfig, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, d as OAuthProvider, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from './OAuthProvider-
|
|
13
|
+
import { A as AuthProvider, O as OAuthSession, a as OAuthProxy } from './OAuthProvider-BV6EpF_k.cjs';
|
|
14
|
+
export { j as AuthProviderConfig, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, d as OAuthProvider, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from './OAuthProvider-BV6EpF_k.cjs';
|
|
15
15
|
import 'node:http';
|
|
16
16
|
|
|
17
17
|
declare class DiscoveryDocumentCache {
|
package/dist/FastMCP.d.ts
CHANGED
|
@@ -10,8 +10,8 @@ import { Hono } from 'hono';
|
|
|
10
10
|
import http from 'http';
|
|
11
11
|
import { StrictEventEmitter } from 'strict-event-emitter-types';
|
|
12
12
|
import { z } from 'zod';
|
|
13
|
-
import { A as AuthProvider, O as OAuthSession, a as OAuthProxy } from './OAuthProvider-
|
|
14
|
-
export { j as AuthProviderConfig, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, d as OAuthProvider, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from './OAuthProvider-
|
|
13
|
+
import { A as AuthProvider, O as OAuthSession, a as OAuthProxy } from './OAuthProvider-BV6EpF_k.js';
|
|
14
|
+
export { j as AuthProviderConfig, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, d as OAuthProvider, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from './OAuthProvider-BV6EpF_k.js';
|
|
15
15
|
import 'node:http';
|
|
16
16
|
|
|
17
17
|
declare class DiscoveryDocumentCache {
|
package/dist/FastMCP.js
CHANGED
|
@@ -185,7 +185,23 @@ interface OAuthProviderConfig {
|
|
|
185
185
|
interface OAuthProxyConfig {
|
|
186
186
|
/** Access token TTL in seconds (default: 3600) */
|
|
187
187
|
accessTokenTtl?: number;
|
|
188
|
-
/**
|
|
188
|
+
/**
|
|
189
|
+
* Allow-list of redirect URI patterns accepted by Dynamic Client Registration.
|
|
190
|
+
*
|
|
191
|
+
* A client calling POST /oauth/register must present a `redirect_uri` that
|
|
192
|
+
* matches one of these patterns (exact string or glob with `*` / `?`);
|
|
193
|
+
* otherwise the registration is rejected with `invalid_redirect_uri`. Once
|
|
194
|
+
* registered, the same exact URI must be echoed back at /oauth/authorize —
|
|
195
|
+
* the proxy performs exact string comparison per RFC 6749 §3.1.2.3.
|
|
196
|
+
*
|
|
197
|
+
* Default: `[]` (DCR rejects everything — explicit opt-in required).
|
|
198
|
+
*
|
|
199
|
+
* Prior versions defaulted to `["https://*", "http://localhost:*"]` with an
|
|
200
|
+
* implicit fallback that allowed any https URL. This enabled CWE-601
|
|
201
|
+
* open-redirect / authorization-code theft: an attacker could DCR their own
|
|
202
|
+
* URL and then steal victim codes via /oauth/authorize. Do not loosen this
|
|
203
|
+
* default without understanding that threat model.
|
|
204
|
+
*/
|
|
189
205
|
allowedRedirectUriPatterns?: string[];
|
|
190
206
|
/** Authorization code TTL in seconds (default: 300) */
|
|
191
207
|
authorizationCodeTtl?: number;
|
|
@@ -548,7 +564,16 @@ declare class OAuthProxy {
|
|
|
548
564
|
*/
|
|
549
565
|
private startCleanup;
|
|
550
566
|
/**
|
|
551
|
-
* Validate redirect URI against
|
|
567
|
+
* Validate a redirect URI against the configured allow-list.
|
|
568
|
+
*
|
|
569
|
+
* Returns `true` only if the URI is syntactically valid AND matches one of
|
|
570
|
+
* the explicitly configured `allowedRedirectUriPatterns`. An empty or unset
|
|
571
|
+
* pattern list means DCR will reject every URI — framework users must
|
|
572
|
+
* opt-in by listing the exact URIs (or wildcards) they trust.
|
|
573
|
+
*
|
|
574
|
+
* Prior versions also fell back to allowing any https URL or localhost,
|
|
575
|
+
* which enabled attackers to DCR an arbitrary URL and then abuse it via
|
|
576
|
+
* /oauth/authorize (CWE-601). Do not re-introduce that fallback.
|
|
552
577
|
*/
|
|
553
578
|
private validateRedirectUri;
|
|
554
579
|
}
|
|
@@ -573,7 +598,17 @@ declare class OAuthProxyError extends Error {
|
|
|
573
598
|
* Configuration common to all OAuth providers.
|
|
574
599
|
*/
|
|
575
600
|
interface AuthProviderConfig {
|
|
576
|
-
/**
|
|
601
|
+
/**
|
|
602
|
+
* Allow-list of redirect URI patterns accepted by Dynamic Client
|
|
603
|
+
* Registration. Required for any deployment that exposes /oauth/register
|
|
604
|
+
* or /oauth/authorize — an empty/unset list rejects every URI.
|
|
605
|
+
*
|
|
606
|
+
* Example: `["https://yourapp.example.com/*"]`
|
|
607
|
+
*
|
|
608
|
+
* Prior versions defaulted to `["http://localhost:*", "https://*"]`, which
|
|
609
|
+
* enabled CWE-601 open-redirect / authorization-code theft. See the
|
|
610
|
+
* SECURITY advisory before loosening this.
|
|
611
|
+
*/
|
|
577
612
|
allowedRedirectUriPatterns?: string[];
|
|
578
613
|
/** Base URL where the MCP server is accessible */
|
|
579
614
|
baseUrl: string;
|
|
@@ -185,7 +185,23 @@ interface OAuthProviderConfig {
|
|
|
185
185
|
interface OAuthProxyConfig {
|
|
186
186
|
/** Access token TTL in seconds (default: 3600) */
|
|
187
187
|
accessTokenTtl?: number;
|
|
188
|
-
/**
|
|
188
|
+
/**
|
|
189
|
+
* Allow-list of redirect URI patterns accepted by Dynamic Client Registration.
|
|
190
|
+
*
|
|
191
|
+
* A client calling POST /oauth/register must present a `redirect_uri` that
|
|
192
|
+
* matches one of these patterns (exact string or glob with `*` / `?`);
|
|
193
|
+
* otherwise the registration is rejected with `invalid_redirect_uri`. Once
|
|
194
|
+
* registered, the same exact URI must be echoed back at /oauth/authorize —
|
|
195
|
+
* the proxy performs exact string comparison per RFC 6749 §3.1.2.3.
|
|
196
|
+
*
|
|
197
|
+
* Default: `[]` (DCR rejects everything — explicit opt-in required).
|
|
198
|
+
*
|
|
199
|
+
* Prior versions defaulted to `["https://*", "http://localhost:*"]` with an
|
|
200
|
+
* implicit fallback that allowed any https URL. This enabled CWE-601
|
|
201
|
+
* open-redirect / authorization-code theft: an attacker could DCR their own
|
|
202
|
+
* URL and then steal victim codes via /oauth/authorize. Do not loosen this
|
|
203
|
+
* default without understanding that threat model.
|
|
204
|
+
*/
|
|
189
205
|
allowedRedirectUriPatterns?: string[];
|
|
190
206
|
/** Authorization code TTL in seconds (default: 300) */
|
|
191
207
|
authorizationCodeTtl?: number;
|
|
@@ -548,7 +564,16 @@ declare class OAuthProxy {
|
|
|
548
564
|
*/
|
|
549
565
|
private startCleanup;
|
|
550
566
|
/**
|
|
551
|
-
* Validate redirect URI against
|
|
567
|
+
* Validate a redirect URI against the configured allow-list.
|
|
568
|
+
*
|
|
569
|
+
* Returns `true` only if the URI is syntactically valid AND matches one of
|
|
570
|
+
* the explicitly configured `allowedRedirectUriPatterns`. An empty or unset
|
|
571
|
+
* pattern list means DCR will reject every URI — framework users must
|
|
572
|
+
* opt-in by listing the exact URIs (or wildcards) they trust.
|
|
573
|
+
*
|
|
574
|
+
* Prior versions also fell back to allowing any https URL or localhost,
|
|
575
|
+
* which enabled attackers to DCR an arbitrary URL and then abuse it via
|
|
576
|
+
* /oauth/authorize (CWE-601). Do not re-introduce that fallback.
|
|
552
577
|
*/
|
|
553
578
|
private validateRedirectUri;
|
|
554
579
|
}
|
|
@@ -573,7 +598,17 @@ declare class OAuthProxyError extends Error {
|
|
|
573
598
|
* Configuration common to all OAuth providers.
|
|
574
599
|
*/
|
|
575
600
|
interface AuthProviderConfig {
|
|
576
|
-
/**
|
|
601
|
+
/**
|
|
602
|
+
* Allow-list of redirect URI patterns accepted by Dynamic Client
|
|
603
|
+
* Registration. Required for any deployment that exposes /oauth/register
|
|
604
|
+
* or /oauth/authorize — an empty/unset list rejects every URI.
|
|
605
|
+
*
|
|
606
|
+
* Example: `["https://yourapp.example.com/*"]`
|
|
607
|
+
*
|
|
608
|
+
* Prior versions defaulted to `["http://localhost:*", "https://*"]`, which
|
|
609
|
+
* enabled CWE-601 open-redirect / authorization-code theft. See the
|
|
610
|
+
* SECURITY advisory before loosening this.
|
|
611
|
+
*/
|
|
577
612
|
allowedRedirectUriPatterns?: string[];
|
|
578
613
|
/** Base URL where the MCP server is accessible */
|
|
579
614
|
baseUrl: string;
|
package/dist/auth/index.cjs
CHANGED
|
@@ -24,7 +24,7 @@
|
|
|
24
24
|
|
|
25
25
|
|
|
26
26
|
|
|
27
|
-
var
|
|
27
|
+
var _chunkSSVFQCSNcjs = require('../chunk-SSVFQCSN.cjs');
|
|
28
28
|
|
|
29
29
|
|
|
30
30
|
|
|
@@ -51,5 +51,5 @@ var _chunk7UDY4VFQcjs = require('../chunk-7UDY4VFQ.cjs');
|
|
|
51
51
|
|
|
52
52
|
|
|
53
53
|
|
|
54
|
-
exports.AuthProvider =
|
|
54
|
+
exports.AuthProvider = _chunkSSVFQCSNcjs.AuthProvider; exports.AzureProvider = _chunkSSVFQCSNcjs.AzureProvider; exports.ConsentManager = _chunkSSVFQCSNcjs.ConsentManager; exports.DEFAULT_ACCESS_TOKEN_TTL = _chunkSSVFQCSNcjs.DEFAULT_ACCESS_TOKEN_TTL; exports.DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH = _chunkSSVFQCSNcjs.DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH; exports.DEFAULT_AUTHORIZATION_CODE_TTL = _chunkSSVFQCSNcjs.DEFAULT_AUTHORIZATION_CODE_TTL; exports.DEFAULT_REFRESH_TOKEN_TTL = _chunkSSVFQCSNcjs.DEFAULT_REFRESH_TOKEN_TTL; exports.DEFAULT_TRANSACTION_TTL = _chunkSSVFQCSNcjs.DEFAULT_TRANSACTION_TTL; exports.DiskStore = _chunkSSVFQCSNcjs.DiskStore; exports.EncryptedTokenStorage = _chunkSSVFQCSNcjs.EncryptedTokenStorage; exports.GitHubProvider = _chunkSSVFQCSNcjs.GitHubProvider; exports.GoogleProvider = _chunkSSVFQCSNcjs.GoogleProvider; exports.JWKSVerifier = _chunkSSVFQCSNcjs.JWKSVerifier; exports.JWTIssuer = _chunkSSVFQCSNcjs.JWTIssuer; exports.MemoryTokenStorage = _chunkSSVFQCSNcjs.MemoryTokenStorage; exports.OAuthProvider = _chunkSSVFQCSNcjs.OAuthProvider; exports.OAuthProxy = _chunkSSVFQCSNcjs.OAuthProxy; exports.OAuthProxyError = _chunkSSVFQCSNcjs.OAuthProxyError; exports.PKCEUtils = _chunkSSVFQCSNcjs.PKCEUtils; exports.getAuthSession = _chunkSSVFQCSNcjs.getAuthSession; exports.requireAll = _chunkSSVFQCSNcjs.requireAll; exports.requireAny = _chunkSSVFQCSNcjs.requireAny; exports.requireAuth = _chunkSSVFQCSNcjs.requireAuth; exports.requireRole = _chunkSSVFQCSNcjs.requireRole; exports.requireScopes = _chunkSSVFQCSNcjs.requireScopes;
|
|
55
55
|
//# sourceMappingURL=index.cjs.map
|
package/dist/auth/index.d.cts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { p as OAuthTransaction, C as ConsentData, T as TokenStorage, q as TokenVerifier, s as TokenVerificationResult, P as PKCEPair } from '../OAuthProvider-
|
|
2
|
-
export { A as AuthProvider, j as AuthProviderConfig, y as AuthorizationParams, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, z as ClientCode, B as DCRClientMetadata, E as DCRRequest, F as DCRResponse, D as DEFAULT_ACCESS_TOKEN_TTL, u as DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH, v as DEFAULT_AUTHORIZATION_CODE_TTL, w as DEFAULT_REFRESH_TOKEN_TTL, x as DEFAULT_TRANSACTION_TTL, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, H as OAuthError, d as OAuthProvider, I as OAuthProviderConfig, a as OAuthProxy, J as OAuthProxyConfig, t as OAuthProxyError, O as OAuthSession, K as ProxyDCRClient, R as RefreshRequest, L as TokenMapping, M as TokenRequest, N as TokenResponse, U as UpstreamTokenSet, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from '../OAuthProvider-
|
|
1
|
+
import { p as OAuthTransaction, C as ConsentData, T as TokenStorage, q as TokenVerifier, s as TokenVerificationResult, P as PKCEPair } from '../OAuthProvider-BV6EpF_k.cjs';
|
|
2
|
+
export { A as AuthProvider, j as AuthProviderConfig, y as AuthorizationParams, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, z as ClientCode, B as DCRClientMetadata, E as DCRRequest, F as DCRResponse, D as DEFAULT_ACCESS_TOKEN_TTL, u as DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH, v as DEFAULT_AUTHORIZATION_CODE_TTL, w as DEFAULT_REFRESH_TOKEN_TTL, x as DEFAULT_TRANSACTION_TTL, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, H as OAuthError, d as OAuthProvider, I as OAuthProviderConfig, a as OAuthProxy, J as OAuthProxyConfig, t as OAuthProxyError, O as OAuthSession, K as ProxyDCRClient, R as RefreshRequest, L as TokenMapping, M as TokenRequest, N as TokenResponse, U as UpstreamTokenSet, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from '../OAuthProvider-BV6EpF_k.cjs';
|
|
3
3
|
import 'node:http';
|
|
4
4
|
|
|
5
5
|
/**
|
package/dist/auth/index.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import { p as OAuthTransaction, C as ConsentData, T as TokenStorage, q as TokenVerifier, s as TokenVerificationResult, P as PKCEPair } from '../OAuthProvider-
|
|
2
|
-
export { A as AuthProvider, j as AuthProviderConfig, y as AuthorizationParams, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, z as ClientCode, B as DCRClientMetadata, E as DCRRequest, F as DCRResponse, D as DEFAULT_ACCESS_TOKEN_TTL, u as DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH, v as DEFAULT_AUTHORIZATION_CODE_TTL, w as DEFAULT_REFRESH_TOKEN_TTL, x as DEFAULT_TRANSACTION_TTL, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, H as OAuthError, d as OAuthProvider, I as OAuthProviderConfig, a as OAuthProxy, J as OAuthProxyConfig, t as OAuthProxyError, O as OAuthSession, K as ProxyDCRClient, R as RefreshRequest, L as TokenMapping, M as TokenRequest, N as TokenResponse, U as UpstreamTokenSet, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from '../OAuthProvider-
|
|
1
|
+
import { p as OAuthTransaction, C as ConsentData, T as TokenStorage, q as TokenVerifier, s as TokenVerificationResult, P as PKCEPair } from '../OAuthProvider-BV6EpF_k.js';
|
|
2
|
+
export { A as AuthProvider, j as AuthProviderConfig, y as AuthorizationParams, b as AzureProvider, k as AzureProviderConfig, l as AzureSession, z as ClientCode, B as DCRClientMetadata, E as DCRRequest, F as DCRResponse, D as DEFAULT_ACCESS_TOKEN_TTL, u as DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH, v as DEFAULT_AUTHORIZATION_CODE_TTL, w as DEFAULT_REFRESH_TOKEN_TTL, x as DEFAULT_TRANSACTION_TTL, m as GenericOAuthProviderConfig, G as GitHubProvider, n as GitHubSession, c as GoogleProvider, o as GoogleSession, H as OAuthError, d as OAuthProvider, I as OAuthProviderConfig, a as OAuthProxy, J as OAuthProxyConfig, t as OAuthProxyError, O as OAuthSession, K as ProxyDCRClient, R as RefreshRequest, L as TokenMapping, M as TokenRequest, N as TokenResponse, U as UpstreamTokenSet, g as getAuthSession, r as requireAll, e as requireAny, f as requireAuth, h as requireRole, i as requireScopes } from '../OAuthProvider-BV6EpF_k.js';
|
|
3
3
|
import 'node:http';
|
|
4
4
|
|
|
5
5
|
/**
|
package/dist/auth/index.js
CHANGED
|
@@ -863,7 +863,11 @@ var OAuthProxy = (_class4 = class {
|
|
|
863
863
|
__init9() {this.transactions = /* @__PURE__ */ new Map()}
|
|
864
864
|
constructor(config) {;_class4.prototype.__init5.call(this);_class4.prototype.__init6.call(this);_class4.prototype.__init7.call(this);_class4.prototype.__init8.call(this);_class4.prototype.__init9.call(this);
|
|
865
865
|
this.config = {
|
|
866
|
-
|
|
866
|
+
// Empty by default. Framework users must explicitly configure the URIs they
|
|
867
|
+
// trust, per RFC 6819 §4.1.5. The previous default (`["https://*", "http://localhost:*"]`)
|
|
868
|
+
// allowed open DCR registration of any https URL, enabling CWE-601 open-redirect
|
|
869
|
+
// attacks against /oauth/authorize.
|
|
870
|
+
allowedRedirectUriPatterns: [],
|
|
867
871
|
authorizationCodeTtl: DEFAULT_AUTHORIZATION_CODE_TTL,
|
|
868
872
|
consentRequired: true,
|
|
869
873
|
enableTokenSwap: true,
|
|
@@ -913,6 +917,15 @@ var OAuthProxy = (_class4 = class {
|
|
|
913
917
|
"Only 'code' response type is supported"
|
|
914
918
|
);
|
|
915
919
|
}
|
|
920
|
+
if (params.client_id !== this.config.upstreamClientId) {
|
|
921
|
+
throw new OAuthProxyError("invalid_client", "Unknown client_id");
|
|
922
|
+
}
|
|
923
|
+
if (!this.registeredClients.has(params.redirect_uri)) {
|
|
924
|
+
throw new OAuthProxyError(
|
|
925
|
+
"invalid_request",
|
|
926
|
+
"redirect_uri is not registered for this client"
|
|
927
|
+
);
|
|
928
|
+
}
|
|
916
929
|
if (params.code_challenge && !params.code_challenge_method) {
|
|
917
930
|
throw new OAuthProxyError(
|
|
918
931
|
"invalid_request",
|
|
@@ -950,6 +963,9 @@ var OAuthProxy = (_class4 = class {
|
|
|
950
963
|
"Only authorization_code grant type is supported"
|
|
951
964
|
);
|
|
952
965
|
}
|
|
966
|
+
if (request.client_id !== this.config.upstreamClientId) {
|
|
967
|
+
throw new OAuthProxyError("invalid_client", "Unknown client_id");
|
|
968
|
+
}
|
|
953
969
|
const clientCode = this.clientCodes.get(request.code);
|
|
954
970
|
if (!clientCode) {
|
|
955
971
|
throw new OAuthProxyError(
|
|
@@ -1063,6 +1079,13 @@ var OAuthProxy = (_class4 = class {
|
|
|
1063
1079
|
if (!transaction) {
|
|
1064
1080
|
throw new OAuthProxyError("invalid_request", "Invalid or expired state");
|
|
1065
1081
|
}
|
|
1082
|
+
if (!this.registeredClients.has(transaction.clientCallbackUrl)) {
|
|
1083
|
+
this.transactions.delete(state);
|
|
1084
|
+
throw new OAuthProxyError(
|
|
1085
|
+
"invalid_request",
|
|
1086
|
+
"Transaction callback URL is not registered"
|
|
1087
|
+
);
|
|
1088
|
+
}
|
|
1066
1089
|
const upstreamTokens = await this.exchangeUpstreamCode(code, transaction);
|
|
1067
1090
|
const clientCode = this.generateAuthorizationCode(
|
|
1068
1091
|
transaction,
|
|
@@ -1098,6 +1121,12 @@ var OAuthProxy = (_class4 = class {
|
|
|
1098
1121
|
}
|
|
1099
1122
|
if (action === "deny") {
|
|
1100
1123
|
this.transactions.delete(transactionId);
|
|
1124
|
+
if (!this.registeredClients.has(transaction.clientCallbackUrl)) {
|
|
1125
|
+
throw new OAuthProxyError(
|
|
1126
|
+
"invalid_request",
|
|
1127
|
+
"Transaction callback URL is not registered"
|
|
1128
|
+
);
|
|
1129
|
+
}
|
|
1101
1130
|
const redirectUrl = new URL(transaction.clientCallbackUrl);
|
|
1102
1131
|
redirectUrl.searchParams.set("error", "access_denied");
|
|
1103
1132
|
redirectUrl.searchParams.set(
|
|
@@ -1176,7 +1205,9 @@ var OAuthProxy = (_class4 = class {
|
|
|
1176
1205
|
},
|
|
1177
1206
|
registeredAt: /* @__PURE__ */ new Date()
|
|
1178
1207
|
};
|
|
1179
|
-
|
|
1208
|
+
for (const uri of request.redirect_uris) {
|
|
1209
|
+
this.registeredClients.set(uri, client);
|
|
1210
|
+
}
|
|
1180
1211
|
const response = {
|
|
1181
1212
|
client_id: clientId,
|
|
1182
1213
|
client_id_issued_at: Math.floor(Date.now() / 1e3),
|
|
@@ -1287,11 +1318,16 @@ var OAuthProxy = (_class4 = class {
|
|
|
1287
1318
|
method: "POST"
|
|
1288
1319
|
});
|
|
1289
1320
|
if (!tokenResponse.ok) {
|
|
1290
|
-
|
|
1291
|
-
|
|
1292
|
-
|
|
1293
|
-
error.
|
|
1294
|
-
|
|
1321
|
+
let errorCode = "server_error";
|
|
1322
|
+
let errorDescription;
|
|
1323
|
+
try {
|
|
1324
|
+
const error = await tokenResponse.json();
|
|
1325
|
+
errorCode = error.error || "server_error";
|
|
1326
|
+
errorDescription = error.error_description;
|
|
1327
|
+
} catch (e3) {
|
|
1328
|
+
errorDescription = `Upstream returned HTTP ${tokenResponse.status} ${tokenResponse.statusText}`;
|
|
1329
|
+
}
|
|
1330
|
+
throw new OAuthProxyError(errorCode, errorDescription);
|
|
1295
1331
|
}
|
|
1296
1332
|
const tokens = await this.parseTokenResponse(tokenResponse);
|
|
1297
1333
|
return {
|
|
@@ -1425,11 +1461,16 @@ var OAuthProxy = (_class4 = class {
|
|
|
1425
1461
|
method: "POST"
|
|
1426
1462
|
});
|
|
1427
1463
|
if (!tokenResponse.ok) {
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
|
|
1431
|
-
error.
|
|
1432
|
-
|
|
1464
|
+
let errorCode = "invalid_grant";
|
|
1465
|
+
let errorDescription;
|
|
1466
|
+
try {
|
|
1467
|
+
const error = await tokenResponse.json();
|
|
1468
|
+
errorCode = error.error || "invalid_grant";
|
|
1469
|
+
errorDescription = error.error_description;
|
|
1470
|
+
} catch (e4) {
|
|
1471
|
+
errorDescription = `Upstream returned HTTP ${tokenResponse.status} ${tokenResponse.statusText}`;
|
|
1472
|
+
}
|
|
1473
|
+
throw new OAuthProxyError(errorCode, errorDescription);
|
|
1433
1474
|
}
|
|
1434
1475
|
const tokens = await this.parseTokenResponse(tokenResponse);
|
|
1435
1476
|
return {
|
|
@@ -1737,11 +1778,16 @@ var OAuthProxy = (_class4 = class {
|
|
|
1737
1778
|
method: "POST"
|
|
1738
1779
|
});
|
|
1739
1780
|
if (!tokenResponse.ok) {
|
|
1740
|
-
|
|
1741
|
-
|
|
1742
|
-
|
|
1743
|
-
error
|
|
1744
|
-
|
|
1781
|
+
let errorCode = "invalid_grant";
|
|
1782
|
+
let errorDescription = "Upstream refresh failed";
|
|
1783
|
+
try {
|
|
1784
|
+
const error = await tokenResponse.json();
|
|
1785
|
+
errorCode = error.error || "invalid_grant";
|
|
1786
|
+
errorDescription = error.error_description || "Upstream refresh failed";
|
|
1787
|
+
} catch (e5) {
|
|
1788
|
+
errorDescription = `Upstream returned HTTP ${tokenResponse.status} ${tokenResponse.statusText}`;
|
|
1789
|
+
}
|
|
1790
|
+
throw new OAuthProxyError(errorCode, errorDescription);
|
|
1745
1791
|
}
|
|
1746
1792
|
const tokens = await this.parseTokenResponse(tokenResponse);
|
|
1747
1793
|
return {
|
|
@@ -1764,21 +1810,28 @@ var OAuthProxy = (_class4 = class {
|
|
|
1764
1810
|
}, 6e4);
|
|
1765
1811
|
}
|
|
1766
1812
|
/**
|
|
1767
|
-
* Validate redirect URI against
|
|
1813
|
+
* Validate a redirect URI against the configured allow-list.
|
|
1814
|
+
*
|
|
1815
|
+
* Returns `true` only if the URI is syntactically valid AND matches one of
|
|
1816
|
+
* the explicitly configured `allowedRedirectUriPatterns`. An empty or unset
|
|
1817
|
+
* pattern list means DCR will reject every URI — framework users must
|
|
1818
|
+
* opt-in by listing the exact URIs (or wildcards) they trust.
|
|
1819
|
+
*
|
|
1820
|
+
* Prior versions also fell back to allowing any https URL or localhost,
|
|
1821
|
+
* which enabled attackers to DCR an arbitrary URL and then abuse it via
|
|
1822
|
+
* /oauth/authorize (CWE-601). Do not re-introduce that fallback.
|
|
1768
1823
|
*/
|
|
1769
1824
|
validateRedirectUri(uri) {
|
|
1770
1825
|
try {
|
|
1771
|
-
|
|
1772
|
-
|
|
1773
|
-
|
|
1774
|
-
|
|
1775
|
-
|
|
1776
|
-
|
|
1777
|
-
}
|
|
1778
|
-
return url.protocol === "https:" || url.hostname === "localhost" || url.hostname === "127.0.0.1";
|
|
1779
|
-
} catch (e3) {
|
|
1826
|
+
new URL(uri);
|
|
1827
|
+
} catch (e6) {
|
|
1828
|
+
return false;
|
|
1829
|
+
}
|
|
1830
|
+
const patterns = this.config.allowedRedirectUriPatterns || [];
|
|
1831
|
+
if (patterns.length === 0) {
|
|
1780
1832
|
return false;
|
|
1781
1833
|
}
|
|
1834
|
+
return patterns.some((pattern) => this.matchesPattern(uri, pattern));
|
|
1782
1835
|
}
|
|
1783
1836
|
}, _class4);
|
|
1784
1837
|
var OAuthProxyError = class extends Error {
|
|
@@ -1883,10 +1936,10 @@ var AzureProvider = class extends AuthProvider {
|
|
|
1883
1936
|
}
|
|
1884
1937
|
createProxy() {
|
|
1885
1938
|
return new OAuthProxy({
|
|
1886
|
-
|
|
1887
|
-
|
|
1888
|
-
|
|
1889
|
-
|
|
1939
|
+
// No fallback default: framework users must explicitly list the URIs
|
|
1940
|
+
// they trust. A previous default of ["http://localhost:*", "https://*"]
|
|
1941
|
+
// enabled CWE-601 open-redirect / code-theft via /oauth/authorize.
|
|
1942
|
+
allowedRedirectUriPatterns: this.config.allowedRedirectUriPatterns,
|
|
1890
1943
|
baseUrl: this.config.baseUrl,
|
|
1891
1944
|
consentRequired: _nullishCoalesce(this.config.consentRequired, () => ( true)),
|
|
1892
1945
|
encryptionKey: this.config.encryptionKey,
|
|
@@ -1917,10 +1970,10 @@ var GitHubProvider = class extends AuthProvider {
|
|
|
1917
1970
|
}
|
|
1918
1971
|
createProxy() {
|
|
1919
1972
|
return new OAuthProxy({
|
|
1920
|
-
|
|
1921
|
-
|
|
1922
|
-
|
|
1923
|
-
|
|
1973
|
+
// No fallback default: framework users must explicitly list the URIs
|
|
1974
|
+
// they trust. A previous default of ["http://localhost:*", "https://*"]
|
|
1975
|
+
// enabled CWE-601 open-redirect / code-theft via /oauth/authorize.
|
|
1976
|
+
allowedRedirectUriPatterns: this.config.allowedRedirectUriPatterns,
|
|
1924
1977
|
baseUrl: this.config.baseUrl,
|
|
1925
1978
|
consentRequired: _nullishCoalesce(this.config.consentRequired, () => ( true)),
|
|
1926
1979
|
encryptionKey: this.config.encryptionKey,
|
|
@@ -1951,10 +2004,10 @@ var GoogleProvider = class extends AuthProvider {
|
|
|
1951
2004
|
}
|
|
1952
2005
|
createProxy() {
|
|
1953
2006
|
return new OAuthProxy({
|
|
1954
|
-
|
|
1955
|
-
|
|
1956
|
-
|
|
1957
|
-
|
|
2007
|
+
// No fallback default: framework users must explicitly list the URIs
|
|
2008
|
+
// they trust. A previous default of ["http://localhost:*", "https://*"]
|
|
2009
|
+
// enabled CWE-601 open-redirect / code-theft via /oauth/authorize.
|
|
2010
|
+
allowedRedirectUriPatterns: this.config.allowedRedirectUriPatterns,
|
|
1958
2011
|
baseUrl: this.config.baseUrl,
|
|
1959
2012
|
consentRequired: _nullishCoalesce(this.config.consentRequired, () => ( true)),
|
|
1960
2013
|
encryptionKey: this.config.encryptionKey,
|
|
@@ -1987,10 +2040,10 @@ var OAuthProvider = class extends AuthProvider {
|
|
|
1987
2040
|
}
|
|
1988
2041
|
createProxy() {
|
|
1989
2042
|
return new OAuthProxy({
|
|
1990
|
-
|
|
1991
|
-
|
|
1992
|
-
|
|
1993
|
-
|
|
2043
|
+
// No fallback default: framework users must explicitly list the URIs
|
|
2044
|
+
// they trust. A previous default of ["http://localhost:*", "https://*"]
|
|
2045
|
+
// enabled CWE-601 open-redirect / code-theft via /oauth/authorize.
|
|
2046
|
+
allowedRedirectUriPatterns: this.config.allowedRedirectUriPatterns,
|
|
1994
2047
|
baseUrl: this.config.baseUrl,
|
|
1995
2048
|
consentRequired: _nullishCoalesce(this.config.consentRequired, () => ( true)),
|
|
1996
2049
|
encryptionKey: this.config.encryptionKey,
|
|
@@ -2054,7 +2107,7 @@ var DiskStore = (_class5 = class {
|
|
|
2054
2107
|
console.warn(`Failed to read/parse file ${file}, deleting:`, error);
|
|
2055
2108
|
try {
|
|
2056
2109
|
await _promises.rm.call(void 0, _path.join.call(void 0, this.directory, file));
|
|
2057
|
-
} catch (
|
|
2110
|
+
} catch (e7) {
|
|
2058
2111
|
}
|
|
2059
2112
|
}
|
|
2060
2113
|
}
|
|
@@ -2131,7 +2184,7 @@ var DiskStore = (_class5 = class {
|
|
|
2131
2184
|
await this.ensureDirectory();
|
|
2132
2185
|
const files = await _promises.readdir.call(void 0, this.directory);
|
|
2133
2186
|
return files.filter((f) => f.endsWith(this.fileExtension)).length;
|
|
2134
|
-
} catch (
|
|
2187
|
+
} catch (e8) {
|
|
2135
2188
|
return 0;
|
|
2136
2189
|
}
|
|
2137
2190
|
}
|
|
@@ -2325,4 +2378,4 @@ Original error: ${error.message}`
|
|
|
2325
2378
|
|
|
2326
2379
|
|
|
2327
2380
|
exports.getAuthSession = getAuthSession; exports.requireAll = requireAll; exports.requireAny = requireAny; exports.requireAuth = requireAuth; exports.requireRole = requireRole; exports.requireScopes = requireScopes; exports.DEFAULT_ACCESS_TOKEN_TTL = DEFAULT_ACCESS_TOKEN_TTL; exports.DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH = DEFAULT_ACCESS_TOKEN_TTL_NO_REFRESH; exports.DEFAULT_REFRESH_TOKEN_TTL = DEFAULT_REFRESH_TOKEN_TTL; exports.DEFAULT_AUTHORIZATION_CODE_TTL = DEFAULT_AUTHORIZATION_CODE_TTL; exports.DEFAULT_TRANSACTION_TTL = DEFAULT_TRANSACTION_TTL; exports.ConsentManager = ConsentManager; exports.JWTIssuer = JWTIssuer; exports.PKCEUtils = PKCEUtils; exports.EncryptedTokenStorage = EncryptedTokenStorage; exports.MemoryTokenStorage = MemoryTokenStorage; exports.OAuthProxy = OAuthProxy; exports.OAuthProxyError = OAuthProxyError; exports.AuthProvider = AuthProvider; exports.AzureProvider = AzureProvider; exports.GitHubProvider = GitHubProvider; exports.GoogleProvider = GoogleProvider; exports.OAuthProvider = OAuthProvider; exports.DiskStore = DiskStore; exports.JWKSVerifier = JWKSVerifier;
|
|
2328
|
-
//# sourceMappingURL=chunk-
|
|
2381
|
+
//# sourceMappingURL=chunk-SSVFQCSN.cjs.map
|