@dereekb/firebase-server 13.11.18 → 13.12.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/index.cjs.js +218 -31
- package/index.esm.js +217 -34
- package/mailgun/package.json +9 -9
- package/mcp/index.cjs.default.js +1 -0
- package/mcp/index.cjs.js +3646 -0
- package/mcp/index.cjs.mjs +2 -0
- package/mcp/index.d.ts +1 -0
- package/mcp/index.esm.js +3609 -0
- package/mcp/package.json +33 -0
- package/mcp/src/index.d.ts +1 -0
- package/mcp/src/lib/controller/index.d.ts +2 -0
- package/mcp/src/lib/controller/mcp.controller.d.ts +19 -0
- package/mcp/src/lib/controller/mcp.wellknown.controller.d.ts +25 -0
- package/mcp/src/lib/index.d.ts +5 -0
- package/mcp/src/lib/mcp.config.d.ts +100 -0
- package/mcp/src/lib/mcp.module.d.ts +49 -0
- package/mcp/src/lib/service/index.d.ts +8 -0
- package/mcp/src/lib/service/mcp.manifest.d.ts +150 -0
- package/mcp/src/lib/service/mcp.response-formatter.d.ts +36 -0
- package/mcp/src/lib/service/mcp.server.factory.d.ts +124 -0
- package/mcp/src/lib/service/mcp.tool-generator.d.ts +235 -0
- package/mcp/src/lib/service/mcp.visibility.d.ts +99 -0
- package/mcp/src/lib/service/tools/mcp.tool.model-decode.d.ts +87 -0
- package/mcp/src/lib/service/tools/mcp.tool.model-get.d.ts +81 -0
- package/mcp/src/lib/service/tools/mcp.tool.model-info.d.ts +84 -0
- package/mcp/src/lib/service/tools/mcp.tool.whoami.d.ts +72 -0
- package/mcp/src/lib/transport/index.d.ts +1 -0
- package/mcp/src/lib/transport/streamable-http.transport.d.ts +21 -0
- package/model/index.cjs.js +639 -266
- package/model/index.esm.js +640 -270
- package/model/package.json +9 -9
- package/model/src/lib/storagefile/extension/compress.pdf.d.ts +29 -1
- package/model/src/lib/storagefile/index.d.ts +1 -0
- package/model/src/lib/storagefile/storagefile.action.server.d.ts +29 -2
- package/model/src/lib/storagefile/storagefile.mcp.d.ts +32 -0
- package/model/src/lib/storagefile/storagefile.module.d.ts +20 -3
- package/oidc/index.cjs.js +322 -147
- package/oidc/index.esm.js +321 -148
- package/oidc/package.json +10 -10
- package/oidc/src/lib/controller/oidc.wellknown.controller.d.ts +6 -15
- package/oidc/src/lib/middleware/oauth-auth.middleware.d.ts +22 -2
- package/oidc/src/lib/middleware/oauth-auth.module.d.ts +57 -0
- package/oidc/src/lib/oidc.config.d.ts +73 -0
- package/oidc/src/lib/oidc.module.d.ts +44 -2
- package/package.json +16 -10
- package/src/lib/auth/auth.service.d.ts +16 -1
- package/src/lib/auth/auth.service.error.util.d.ts +24 -5
- package/src/lib/env/env.config.d.ts +16 -0
- package/src/lib/env/env.service.d.ts +9 -0
- package/src/lib/nest/controller/model/model.api.get.service.d.ts +35 -1
- package/src/lib/nest/env/env.service.d.ts +1 -0
- package/src/lib/nest/model/api.details.d.ts +116 -5
- package/src/lib/nest/model/crud.assert.function.d.ts +1 -1
- package/src/lib/nest/model/index.d.ts +1 -0
- package/src/lib/nest/model/invoke.model.function.d.ts +89 -0
- package/test/package.json +11 -11
- package/twilio/LICENSE +21 -0
- package/twilio/index.cjs.default.js +1 -0
- package/twilio/index.cjs.js +404 -0
- package/twilio/index.cjs.mjs +2 -0
- package/twilio/index.d.ts +1 -0
- package/twilio/index.esm.js +398 -0
- package/twilio/package.json +25 -0
- package/twilio/src/index.d.ts +1 -0
- package/twilio/src/lib/index.d.ts +1 -0
- package/twilio/src/lib/notification.send.service.twilio.d.ts +148 -0
- package/zoho/package.json +9 -9
package/oidc/index.cjs.js
CHANGED
|
@@ -183,6 +183,46 @@ function _define_property$f(obj, key, value) {
|
|
|
183
183
|
* since those are typically protected by AppCheck.
|
|
184
184
|
*/ _define_property$f(this, "protectedPaths", void 0);
|
|
185
185
|
/**
|
|
186
|
+
* Map of recognized OAuth resource indicator URLs (RFC 8707) to their
|
|
187
|
+
* {@link OidcResourceServerInfo}. When non-empty, oidc-provider's
|
|
188
|
+
* `features.resourceIndicators.getResourceServerInfo` is wired to look up
|
|
189
|
+
* each requested `resource` parameter against this map and reject unknown
|
|
190
|
+
* resources with `invalid_target`.
|
|
191
|
+
*
|
|
192
|
+
* Required for OAuth-aware MCP clients (Claude, mcp-inspector) — they pass
|
|
193
|
+
* the MCP URL from the protected-resource discovery doc as the `resource`
|
|
194
|
+
* parameter on `/authorize` and `/token`, and oidc-provider rejects every
|
|
195
|
+
* such request with `invalid_target` unless that URL is recognized here.
|
|
196
|
+
*
|
|
197
|
+
* @example
|
|
198
|
+
* ```ts
|
|
199
|
+
* resourceServers: {
|
|
200
|
+
* 'http://localhost:9902/dereekb-components/us-central1/api/mcp': {
|
|
201
|
+
* scope: 'openid profile email offline_access demo model.create model.read model.update model.delete model.query model.invoke',
|
|
202
|
+
* audience: 'http://localhost:9902/dereekb-components/us-central1/api/mcp'
|
|
203
|
+
* }
|
|
204
|
+
* }
|
|
205
|
+
* ```
|
|
206
|
+
*/ _define_property$f(this, "resourceServers", void 0);
|
|
207
|
+
/**
|
|
208
|
+
* Absolute URL of the OAuth 2.0 Protected Resource Metadata document
|
|
209
|
+
* (RFC 9728) for the resources guarded by {@link protectedPaths}.
|
|
210
|
+
*
|
|
211
|
+
* When set, the OIDC bearer middleware emits
|
|
212
|
+
* `WWW-Authenticate: Bearer resource_metadata="<url>", error="invalid_token"`
|
|
213
|
+
* on 401 responses, so OAuth-aware clients (Claude, mcp-inspector) can
|
|
214
|
+
* locate the discovery doc without relying on RFC 9728's origin-rooted
|
|
215
|
+
* path-walkback rule — which only works when the resource server is
|
|
216
|
+
* actually mounted at the origin root.
|
|
217
|
+
*
|
|
218
|
+
* Typically derived from `appMcpUrl` (or the equivalent protected-resource
|
|
219
|
+
* URL) — e.g. for `appMcpUrl = https://api.example.com/mcp`, the value is
|
|
220
|
+
* `https://api.example.com/.well-known/oauth-protected-resource`.
|
|
221
|
+
*
|
|
222
|
+
* @example
|
|
223
|
+
* resourceMetadataUrl: 'http://localhost:9902/dereekb-components/us-central1/api/.well-known/oauth-protected-resource'
|
|
224
|
+
*/ _define_property$f(this, "resourceMetadataUrl", void 0);
|
|
225
|
+
/**
|
|
186
226
|
* Supported token endpoint authentication methods.
|
|
187
227
|
*
|
|
188
228
|
* Overrides the default methods (`client_secret_post`, `client_secret_basic`)
|
|
@@ -3863,6 +3903,41 @@ function _ts_generator$5(thisArg, body) {
|
|
|
3863
3903
|
},
|
|
3864
3904
|
registrationManagement: {
|
|
3865
3905
|
enabled: this.providerConfigService.oidcRegistrationRouteEnabled
|
|
3906
|
+
},
|
|
3907
|
+
resourceIndicators: {
|
|
3908
|
+
enabled: true,
|
|
3909
|
+
// useGrantedResource: return true so the token endpoint will bind tokens to a previously
|
|
3910
|
+
// granted resource without requiring the client to re-send the `resource` parameter on each
|
|
3911
|
+
// refresh — Claude and other MCP clients send `resource` on `/authorize` but not on
|
|
3912
|
+
// `/token` refresh.
|
|
3913
|
+
useGrantedResource: function useGrantedResource() {
|
|
3914
|
+
return true;
|
|
3915
|
+
},
|
|
3916
|
+
getResourceServerInfo: function getResourceServerInfo(_ctx, resourceIndicator) {
|
|
3917
|
+
return _async_to_generator$5(function() {
|
|
3918
|
+
var _config_resourceServers, info;
|
|
3919
|
+
return _ts_generator$5(this, function(_state) {
|
|
3920
|
+
info = (_config_resourceServers = config.resourceServers) === null || _config_resourceServers === void 0 ? void 0 : _config_resourceServers[resourceIndicator];
|
|
3921
|
+
if (!info) {
|
|
3922
|
+
throw new oidcProvider.errors.InvalidTarget("Unrecognized resource indicator: ".concat(resourceIndicator));
|
|
3923
|
+
}
|
|
3924
|
+
return [
|
|
3925
|
+
2,
|
|
3926
|
+
_object_spread$2({
|
|
3927
|
+
scope: info.scope
|
|
3928
|
+
}, info.audience === undefined ? {} : {
|
|
3929
|
+
audience: info.audience
|
|
3930
|
+
}, info.accessTokenTTL === undefined ? {} : {
|
|
3931
|
+
accessTokenTTL: info.accessTokenTTL
|
|
3932
|
+
}, info.accessTokenFormat === undefined ? {
|
|
3933
|
+
accessTokenFormat: 'opaque'
|
|
3934
|
+
} : {
|
|
3935
|
+
accessTokenFormat: info.accessTokenFormat
|
|
3936
|
+
})
|
|
3937
|
+
];
|
|
3938
|
+
});
|
|
3939
|
+
})();
|
|
3940
|
+
}
|
|
3866
3941
|
}
|
|
3867
3942
|
},
|
|
3868
3943
|
extraParams: [
|
|
@@ -4098,6 +4173,175 @@ exports.OidcService = __decorate([
|
|
|
4098
4173
|
__param(5, common.Inject(exports.OidcEncryptionService))
|
|
4099
4174
|
], exports.OidcService);
|
|
4100
4175
|
|
|
4176
|
+
function _class_call_check$5(instance, Constructor) {
|
|
4177
|
+
if (!(instance instanceof Constructor)) {
|
|
4178
|
+
throw new TypeError("Cannot call a class as a function");
|
|
4179
|
+
}
|
|
4180
|
+
}
|
|
4181
|
+
function _define_property$6(obj, key, value) {
|
|
4182
|
+
if (key in obj) {
|
|
4183
|
+
Object.defineProperty(obj, key, {
|
|
4184
|
+
value: value,
|
|
4185
|
+
enumerable: true,
|
|
4186
|
+
configurable: true,
|
|
4187
|
+
writable: true
|
|
4188
|
+
});
|
|
4189
|
+
} else {
|
|
4190
|
+
obj[key] = value;
|
|
4191
|
+
}
|
|
4192
|
+
return obj;
|
|
4193
|
+
}
|
|
4194
|
+
// MARK: Config
|
|
4195
|
+
/**
|
|
4196
|
+
* Configuration for `OidcAuthBearerTokenMiddleware` route protection.
|
|
4197
|
+
*
|
|
4198
|
+
* Works in reverse of `FirebaseAppCheckMiddlewareConfig`: instead of protecting
|
|
4199
|
+
* all routes and ignoring some, this only protects explicitly specified paths.
|
|
4200
|
+
* Routes under the global API prefix (protected by AppCheck) are excluded.
|
|
4201
|
+
*
|
|
4202
|
+
* @example
|
|
4203
|
+
* Manual configuration without going through `oidcModuleMetadata`:
|
|
4204
|
+
* ```ts
|
|
4205
|
+
* @Module({
|
|
4206
|
+
* providers: [
|
|
4207
|
+
* {
|
|
4208
|
+
* provide: OidcAuthMiddlewareConfig,
|
|
4209
|
+
* useValue: {
|
|
4210
|
+
* protectedPaths: ['/api/model', '/mcp'],
|
|
4211
|
+
* resourceMetadataUrl: 'https://api.example.com/.well-known/oauth-protected-resource'
|
|
4212
|
+
* } satisfies OidcAuthMiddlewareConfig
|
|
4213
|
+
* }
|
|
4214
|
+
* ]
|
|
4215
|
+
* })
|
|
4216
|
+
* export class MyApiModule {}
|
|
4217
|
+
* ```
|
|
4218
|
+
*/ var OidcAuthMiddlewareConfig = function OidcAuthMiddlewareConfig() {
|
|
4219
|
+
_class_call_check$5(this, OidcAuthMiddlewareConfig);
|
|
4220
|
+
/**
|
|
4221
|
+
* Path prefixes that require OAuth bearer token verification.
|
|
4222
|
+
*
|
|
4223
|
+
* Only requests matching one of these prefixes will be checked.
|
|
4224
|
+
* Paths under the global API route prefix should not be included
|
|
4225
|
+
* since those are protected by AppCheck.
|
|
4226
|
+
*/ _define_property$6(this, "protectedPaths", void 0);
|
|
4227
|
+
/**
|
|
4228
|
+
* Absolute URL of the OAuth 2.0 Protected Resource Metadata document
|
|
4229
|
+
* (RFC 9728). When set, included as the `resource_metadata` parameter
|
|
4230
|
+
* of the `WWW-Authenticate: Bearer` header on 401 responses so OAuth
|
|
4231
|
+
* clients can locate the discovery doc explicitly rather than relying on
|
|
4232
|
+
* origin-rooted path-walkback (which fails when the function isn't
|
|
4233
|
+
* mounted at `/` — e.g. behind the Firebase Functions emulator URL prefix).
|
|
4234
|
+
*/ _define_property$6(this, "resourceMetadataUrl", void 0);
|
|
4235
|
+
};
|
|
4236
|
+
// MARK: WWW-Authenticate
|
|
4237
|
+
/**
|
|
4238
|
+
* Builds the `WWW-Authenticate: Bearer ...` challenge string emitted on 401
|
|
4239
|
+
* responses to OAuth-protected routes.
|
|
4240
|
+
*
|
|
4241
|
+
* Per RFC 6750 §3 / RFC 7235, auth-params are comma-separated (optionally
|
|
4242
|
+
* with surrounding whitespace). When `resourceMetadataUrl` is provided, it's
|
|
4243
|
+
* included as the RFC 9728 `resource_metadata` hint so clients can locate the
|
|
4244
|
+
* discovery doc directly instead of relying on origin-rooted path-walkback.
|
|
4245
|
+
*
|
|
4246
|
+
* @param error - The RFC 6750 `error` token (e.g. `invalid_token`, `invalid_request`).
|
|
4247
|
+
* @param resourceMetadataUrl - Optional protected-resource metadata URL.
|
|
4248
|
+
* @returns Header value, e.g. `Bearer resource_metadata="…", error="invalid_token"`.
|
|
4249
|
+
*/ function buildBearerChallenge(error, resourceMetadataUrl) {
|
|
4250
|
+
var params = [];
|
|
4251
|
+
if (resourceMetadataUrl) {
|
|
4252
|
+
params.push('resource_metadata="'.concat(resourceMetadataUrl, '"'));
|
|
4253
|
+
}
|
|
4254
|
+
params.push('error="'.concat(error, '"'));
|
|
4255
|
+
return "Bearer ".concat(params.join(', '));
|
|
4256
|
+
}
|
|
4257
|
+
// MARK: Module
|
|
4258
|
+
var _logger = new common.Logger('applyOidcAuthMiddleware');
|
|
4259
|
+
// MARK: Express-Level Helper
|
|
4260
|
+
/**
|
|
4261
|
+
* Applies OAuth bearer token verification as global Express middleware on
|
|
4262
|
+
* the given NestJS application.
|
|
4263
|
+
*
|
|
4264
|
+
* Resolves `OidcService` and `OidcAuthMiddlewareConfig` from the app's DI container,
|
|
4265
|
+
* then registers an Express middleware that verifies bearer tokens for the configured
|
|
4266
|
+
* protected paths and attaches auth data to `req.auth`.
|
|
4267
|
+
*
|
|
4268
|
+
* This is an alternative to {@link ConfigureOidcAuthMiddlewareModule} for cases where
|
|
4269
|
+
* NestJS module scoping makes the module approach impractical.
|
|
4270
|
+
*
|
|
4271
|
+
* @param nestApp - The NestJS application instance used to resolve dependencies and register the middleware.
|
|
4272
|
+
*
|
|
4273
|
+
* @example
|
|
4274
|
+
* ```ts
|
|
4275
|
+
* export const APP_NEST_SERVER_CONFIG: NestServerInstanceConfig<AppModule> = {
|
|
4276
|
+
* moduleClass: AppModule,
|
|
4277
|
+
* configureNestServerInstance: (nestApp) => {
|
|
4278
|
+
* applyOidcAuthMiddleware(nestApp);
|
|
4279
|
+
* }
|
|
4280
|
+
* };
|
|
4281
|
+
* ```
|
|
4282
|
+
*
|
|
4283
|
+
* Pair with `oidcModuleMetadata` (passing `resourceMetadataUrl` on `config`) so
|
|
4284
|
+
* the 401 emits an RFC 9728 `WWW-Authenticate: Bearer resource_metadata="..."`
|
|
4285
|
+
* header — required when the resource server isn't mounted at the origin root
|
|
4286
|
+
* (e.g. behind the Firebase Functions emulator URL prefix), since RFC 9728's
|
|
4287
|
+
* default path-walkback lands at a 404 in that case.
|
|
4288
|
+
*
|
|
4289
|
+
* @example
|
|
4290
|
+
* ```ts
|
|
4291
|
+
* oidcModuleMetadata({
|
|
4292
|
+
* dependencyModule: MyOidcDependencyModule,
|
|
4293
|
+
* config: {
|
|
4294
|
+
* protectedPaths: ['/api/model', '/mcp'],
|
|
4295
|
+
* resourceMetadataUrl: 'http://localhost:9902/dereekb-components/us-central1/api/.well-known/oauth-protected-resource'
|
|
4296
|
+
* }
|
|
4297
|
+
* })
|
|
4298
|
+
* ```
|
|
4299
|
+
*/ function applyOidcAuthMiddleware(nestApp) {
|
|
4300
|
+
var _ref;
|
|
4301
|
+
var oidcService = nestApp.get(exports.OidcService);
|
|
4302
|
+
var config = nestApp.get(OidcAuthMiddlewareConfig);
|
|
4303
|
+
var protectedPaths = (_ref = config === null || config === void 0 ? void 0 : config.protectedPaths) !== null && _ref !== void 0 ? _ref : [];
|
|
4304
|
+
var resourceMetadataUrl = config === null || config === void 0 ? void 0 : config.resourceMetadataUrl;
|
|
4305
|
+
if (protectedPaths.length === 0) {
|
|
4306
|
+
return;
|
|
4307
|
+
}
|
|
4308
|
+
var logger = new common.Logger('OidcAuthMiddleware');
|
|
4309
|
+
var respond401 = function respond401(res, error, message) {
|
|
4310
|
+
res.setHeader('WWW-Authenticate', buildBearerChallenge(error, resourceMetadataUrl));
|
|
4311
|
+
res.status(401).json({
|
|
4312
|
+
statusCode: 401,
|
|
4313
|
+
message: message
|
|
4314
|
+
});
|
|
4315
|
+
};
|
|
4316
|
+
nestApp.use(function(req, res, next) {
|
|
4317
|
+
var isProtected = protectedPaths.some(function(prefix) {
|
|
4318
|
+
return req.path.startsWith(prefix);
|
|
4319
|
+
});
|
|
4320
|
+
if (isProtected) {
|
|
4321
|
+
var authHeader = req.headers.authorization;
|
|
4322
|
+
if (authHeader === null || authHeader === void 0 ? void 0 : authHeader.startsWith('Bearer ')) {
|
|
4323
|
+
var token = authHeader.slice(7);
|
|
4324
|
+
oidcService.verifyAccessToken(token).then(function(oauthAuth) {
|
|
4325
|
+
if (oauthAuth) {
|
|
4326
|
+
req.auth = oauthAuth;
|
|
4327
|
+
next();
|
|
4328
|
+
} else {
|
|
4329
|
+
respond401(res, 'invalid_token', 'Invalid or expired access token');
|
|
4330
|
+
}
|
|
4331
|
+
}).catch(function(err) {
|
|
4332
|
+
logger.error('Bearer token verification failed', err);
|
|
4333
|
+
respond401(res, 'invalid_token', 'Token verification failed');
|
|
4334
|
+
});
|
|
4335
|
+
} else {
|
|
4336
|
+
respond401(res, 'invalid_request', 'Missing or invalid Authorization header');
|
|
4337
|
+
}
|
|
4338
|
+
} else {
|
|
4339
|
+
next();
|
|
4340
|
+
}
|
|
4341
|
+
});
|
|
4342
|
+
_logger.debug("Applied OAuth bearer token middleware for paths: ".concat(protectedPaths.join(', ')));
|
|
4343
|
+
}
|
|
4344
|
+
|
|
4101
4345
|
function asyncGeneratorStep$4(gen, resolve, reject, _next, _throw, key, arg) {
|
|
4102
4346
|
try {
|
|
4103
4347
|
var info = gen[key](arg);
|
|
@@ -4127,7 +4371,7 @@ function _async_to_generator$4(fn) {
|
|
|
4127
4371
|
});
|
|
4128
4372
|
};
|
|
4129
4373
|
}
|
|
4130
|
-
function _class_call_check$
|
|
4374
|
+
function _class_call_check$4(instance, Constructor) {
|
|
4131
4375
|
if (!(instance instanceof Constructor)) {
|
|
4132
4376
|
throw new TypeError("Cannot call a class as a function");
|
|
4133
4377
|
}
|
|
@@ -4145,7 +4389,7 @@ function _create_class$4(Constructor, protoProps, staticProps) {
|
|
|
4145
4389
|
if (protoProps) _defineProperties$4(Constructor.prototype, protoProps);
|
|
4146
4390
|
return Constructor;
|
|
4147
4391
|
}
|
|
4148
|
-
function _define_property$
|
|
4392
|
+
function _define_property$5(obj, key, value) {
|
|
4149
4393
|
if (key in obj) {
|
|
4150
4394
|
Object.defineProperty(obj, key, {
|
|
4151
4395
|
value: value,
|
|
@@ -4273,20 +4517,39 @@ function _ts_generator$4(thisArg, body) {
|
|
|
4273
4517
|
* verifies it via the provider's AccessToken model, and attaches the
|
|
4274
4518
|
* auth context to the request as {@link OidcAuthData}.
|
|
4275
4519
|
*
|
|
4520
|
+
* On 401, emits an RFC 9728 `WWW-Authenticate: Bearer ...` header — including
|
|
4521
|
+
* the `resource_metadata` discovery URL when `OidcAuthMiddlewareConfig.resourceMetadataUrl`
|
|
4522
|
+
* is configured — so OAuth-aware clients (Claude, mcp-inspector, etc.) can
|
|
4523
|
+
* locate the discovery doc explicitly.
|
|
4524
|
+
*
|
|
4276
4525
|
* Applied to routes via {@link ConfigureOidcAuthMiddlewareModule}.
|
|
4277
4526
|
*
|
|
4527
|
+
* @example
|
|
4528
|
+
* Wired automatically when `protectedPaths` is set on `oidcModuleMetadata`:
|
|
4529
|
+
* ```ts
|
|
4530
|
+
* oidcModuleMetadata({
|
|
4531
|
+
* dependencyModule: MyOidcDependencyModule,
|
|
4532
|
+
* config: {
|
|
4533
|
+
* protectedPaths: ['/api/model', '/mcp'],
|
|
4534
|
+
* resourceMetadataUrl: 'https://api.example.com/.well-known/oauth-protected-resource'
|
|
4535
|
+
* }
|
|
4536
|
+
* })
|
|
4537
|
+
* ```
|
|
4538
|
+
*
|
|
4278
4539
|
* @throws {UnauthorizedException} When the Authorization header is missing, malformed, or the token is invalid/expired.
|
|
4279
4540
|
*/ exports.OidcAuthBearerTokenMiddleware = /*#__PURE__*/ function() {
|
|
4280
|
-
function OidcAuthBearerTokenMiddleware(oidcService) {
|
|
4281
|
-
_class_call_check$
|
|
4282
|
-
_define_property$
|
|
4283
|
-
_define_property$
|
|
4541
|
+
function OidcAuthBearerTokenMiddleware(oidcService, config) {
|
|
4542
|
+
_class_call_check$4(this, OidcAuthBearerTokenMiddleware);
|
|
4543
|
+
_define_property$5(this, "oidcService", void 0);
|
|
4544
|
+
_define_property$5(this, "config", void 0);
|
|
4545
|
+
_define_property$5(this, "logger", new common.Logger('OidcAuthBearerTokenMiddleware'));
|
|
4284
4546
|
this.oidcService = oidcService;
|
|
4547
|
+
this.config = config;
|
|
4285
4548
|
}
|
|
4286
4549
|
_create_class$4(OidcAuthBearerTokenMiddleware, [
|
|
4287
4550
|
{
|
|
4288
4551
|
key: "use",
|
|
4289
|
-
value: function use(req,
|
|
4552
|
+
value: function use(req, res, next) {
|
|
4290
4553
|
return _async_to_generator$4(function() {
|
|
4291
4554
|
var authHeader, token, oauthAuth, err;
|
|
4292
4555
|
return _ts_generator$4(this, function(_state) {
|
|
@@ -4294,6 +4557,7 @@ function _ts_generator$4(thisArg, body) {
|
|
|
4294
4557
|
case 0:
|
|
4295
4558
|
authHeader = req.headers.authorization;
|
|
4296
4559
|
if (!(authHeader === null || authHeader === void 0 ? void 0 : authHeader.startsWith('Bearer '))) {
|
|
4560
|
+
this._setWwwAuthenticate(res, 'invalid_request');
|
|
4297
4561
|
throw new common.UnauthorizedException('Missing or invalid Authorization header');
|
|
4298
4562
|
}
|
|
4299
4563
|
token = authHeader.slice(7);
|
|
@@ -4312,6 +4576,7 @@ function _ts_generator$4(thisArg, body) {
|
|
|
4312
4576
|
case 2:
|
|
4313
4577
|
oauthAuth = _state.sent();
|
|
4314
4578
|
if (!oauthAuth) {
|
|
4579
|
+
this._setWwwAuthenticate(res, 'invalid_token');
|
|
4315
4580
|
throw new common.UnauthorizedException('Invalid or expired access token');
|
|
4316
4581
|
}
|
|
4317
4582
|
req.auth = oauthAuth;
|
|
@@ -4326,6 +4591,7 @@ function _ts_generator$4(thisArg, body) {
|
|
|
4326
4591
|
throw err;
|
|
4327
4592
|
}
|
|
4328
4593
|
this.logger.error('Bearer token verification failed', err);
|
|
4594
|
+
this._setWwwAuthenticate(res, 'invalid_token');
|
|
4329
4595
|
throw new common.UnauthorizedException('Token verification failed');
|
|
4330
4596
|
case 4:
|
|
4331
4597
|
return [
|
|
@@ -4335,122 +4601,23 @@ function _ts_generator$4(thisArg, body) {
|
|
|
4335
4601
|
});
|
|
4336
4602
|
}).call(this);
|
|
4337
4603
|
}
|
|
4604
|
+
},
|
|
4605
|
+
{
|
|
4606
|
+
key: "_setWwwAuthenticate",
|
|
4607
|
+
value: function _setWwwAuthenticate(res, error) {
|
|
4608
|
+
var _this_config;
|
|
4609
|
+
res.setHeader('WWW-Authenticate', buildBearerChallenge(error, (_this_config = this.config) === null || _this_config === void 0 ? void 0 : _this_config.resourceMetadataUrl));
|
|
4610
|
+
}
|
|
4338
4611
|
}
|
|
4339
4612
|
]);
|
|
4340
4613
|
return OidcAuthBearerTokenMiddleware;
|
|
4341
4614
|
}();
|
|
4342
4615
|
exports.OidcAuthBearerTokenMiddleware = __decorate([
|
|
4343
4616
|
common.Injectable(),
|
|
4344
|
-
__param(0, common.Inject(exports.OidcService))
|
|
4617
|
+
__param(0, common.Inject(exports.OidcService)),
|
|
4618
|
+
__param(1, common.Inject(OidcAuthMiddlewareConfig))
|
|
4345
4619
|
], exports.OidcAuthBearerTokenMiddleware);
|
|
4346
4620
|
|
|
4347
|
-
function _class_call_check$4(instance, Constructor) {
|
|
4348
|
-
if (!(instance instanceof Constructor)) {
|
|
4349
|
-
throw new TypeError("Cannot call a class as a function");
|
|
4350
|
-
}
|
|
4351
|
-
}
|
|
4352
|
-
function _define_property$5(obj, key, value) {
|
|
4353
|
-
if (key in obj) {
|
|
4354
|
-
Object.defineProperty(obj, key, {
|
|
4355
|
-
value: value,
|
|
4356
|
-
enumerable: true,
|
|
4357
|
-
configurable: true,
|
|
4358
|
-
writable: true
|
|
4359
|
-
});
|
|
4360
|
-
} else {
|
|
4361
|
-
obj[key] = value;
|
|
4362
|
-
}
|
|
4363
|
-
return obj;
|
|
4364
|
-
}
|
|
4365
|
-
// MARK: Config
|
|
4366
|
-
/**
|
|
4367
|
-
* Configuration for `OidcAuthBearerTokenMiddleware` route protection.
|
|
4368
|
-
*
|
|
4369
|
-
* Works in reverse of `FirebaseAppCheckMiddlewareConfig`: instead of protecting
|
|
4370
|
-
* all routes and ignoring some, this only protects explicitly specified paths.
|
|
4371
|
-
* Routes under the global API prefix (protected by AppCheck) are excluded.
|
|
4372
|
-
*/ var OidcAuthMiddlewareConfig = function OidcAuthMiddlewareConfig() {
|
|
4373
|
-
_class_call_check$4(this, OidcAuthMiddlewareConfig);
|
|
4374
|
-
/**
|
|
4375
|
-
* Path prefixes that require OAuth bearer token verification.
|
|
4376
|
-
*
|
|
4377
|
-
* Only requests matching one of these prefixes will be checked.
|
|
4378
|
-
* Paths under the global API route prefix should not be included
|
|
4379
|
-
* since those are protected by AppCheck.
|
|
4380
|
-
*/ _define_property$5(this, "protectedPaths", void 0);
|
|
4381
|
-
};
|
|
4382
|
-
// MARK: Module
|
|
4383
|
-
var _logger = new common.Logger('applyOidcAuthMiddleware');
|
|
4384
|
-
// MARK: Express-Level Helper
|
|
4385
|
-
/**
|
|
4386
|
-
* Applies OAuth bearer token verification as global Express middleware on
|
|
4387
|
-
* the given NestJS application.
|
|
4388
|
-
*
|
|
4389
|
-
* Resolves `OidcService` and `OidcAuthMiddlewareConfig` from the app's DI container,
|
|
4390
|
-
* then registers an Express middleware that verifies bearer tokens for the configured
|
|
4391
|
-
* protected paths and attaches auth data to `req.auth`.
|
|
4392
|
-
*
|
|
4393
|
-
* This is an alternative to {@link ConfigureOidcAuthMiddlewareModule} for cases where
|
|
4394
|
-
* NestJS module scoping makes the module approach impractical.
|
|
4395
|
-
*
|
|
4396
|
-
* @param nestApp - The NestJS application instance used to resolve dependencies and register the middleware.
|
|
4397
|
-
*
|
|
4398
|
-
* @example
|
|
4399
|
-
* ```ts
|
|
4400
|
-
* export const APP_NEST_SERVER_CONFIG: NestServerInstanceConfig<AppModule> = {
|
|
4401
|
-
* moduleClass: AppModule,
|
|
4402
|
-
* configureNestServerInstance: (nestApp) => {
|
|
4403
|
-
* applyOidcAuthMiddleware(nestApp);
|
|
4404
|
-
* }
|
|
4405
|
-
* };
|
|
4406
|
-
* ```
|
|
4407
|
-
*/ function applyOidcAuthMiddleware(nestApp) {
|
|
4408
|
-
var _ref;
|
|
4409
|
-
var oidcService = nestApp.get(exports.OidcService);
|
|
4410
|
-
var config = nestApp.get(OidcAuthMiddlewareConfig);
|
|
4411
|
-
var protectedPaths = (_ref = config === null || config === void 0 ? void 0 : config.protectedPaths) !== null && _ref !== void 0 ? _ref : [];
|
|
4412
|
-
if (protectedPaths.length === 0) {
|
|
4413
|
-
return;
|
|
4414
|
-
}
|
|
4415
|
-
var logger = new common.Logger('OidcAuthMiddleware');
|
|
4416
|
-
nestApp.use(function(req, res, next) {
|
|
4417
|
-
var isProtected = protectedPaths.some(function(prefix) {
|
|
4418
|
-
return req.path.startsWith(prefix);
|
|
4419
|
-
});
|
|
4420
|
-
if (isProtected) {
|
|
4421
|
-
var authHeader = req.headers.authorization;
|
|
4422
|
-
if (authHeader === null || authHeader === void 0 ? void 0 : authHeader.startsWith('Bearer ')) {
|
|
4423
|
-
var token = authHeader.slice(7);
|
|
4424
|
-
oidcService.verifyAccessToken(token).then(function(oauthAuth) {
|
|
4425
|
-
if (oauthAuth) {
|
|
4426
|
-
req.auth = oauthAuth;
|
|
4427
|
-
next();
|
|
4428
|
-
} else {
|
|
4429
|
-
res.status(401).json({
|
|
4430
|
-
statusCode: 401,
|
|
4431
|
-
message: 'Invalid or expired access token'
|
|
4432
|
-
});
|
|
4433
|
-
}
|
|
4434
|
-
}).catch(function(err) {
|
|
4435
|
-
logger.error('Bearer token verification failed', err);
|
|
4436
|
-
res.status(401).json({
|
|
4437
|
-
statusCode: 401,
|
|
4438
|
-
message: 'Token verification failed'
|
|
4439
|
-
});
|
|
4440
|
-
});
|
|
4441
|
-
} else {
|
|
4442
|
-
res.status(401).json({
|
|
4443
|
-
statusCode: 401,
|
|
4444
|
-
message: 'Missing or invalid Authorization header'
|
|
4445
|
-
});
|
|
4446
|
-
}
|
|
4447
|
-
} else {
|
|
4448
|
-
next();
|
|
4449
|
-
}
|
|
4450
|
-
});
|
|
4451
|
-
_logger.debug("Applied OAuth bearer token middleware for paths: ".concat(protectedPaths.join(', ')));
|
|
4452
|
-
}
|
|
4453
|
-
|
|
4454
4621
|
// MARK: Express-Level Helper
|
|
4455
4622
|
/**
|
|
4456
4623
|
* Enables CORS on the NestJS app for OIDC cross-origin requests originating from the frontend.
|
|
@@ -6104,14 +6271,16 @@ function _ts_generator(thisArg, body) {
|
|
|
6104
6271
|
}
|
|
6105
6272
|
// MARK: Well-Known Controller
|
|
6106
6273
|
/**
|
|
6107
|
-
* Controller for
|
|
6274
|
+
* Controller for OIDC discovery and JWKS endpoints under `/.well-known`.
|
|
6275
|
+
*
|
|
6276
|
+
* The protected-resource discovery doc (`/.well-known/oauth-protected-resource`)
|
|
6277
|
+
* is owned by the protected resource itself (the MCP module's
|
|
6278
|
+
* `McpWellKnownController`), not the authorization server, per RFC 9728.
|
|
6108
6279
|
*/ exports.OidcWellKnownController = /*#__PURE__*/ function() {
|
|
6109
|
-
function OidcWellKnownController(
|
|
6280
|
+
function OidcWellKnownController(providerConfigService, jwksService) {
|
|
6110
6281
|
_class_call_check(this, OidcWellKnownController);
|
|
6111
|
-
_define_property$1(this, "config", void 0);
|
|
6112
6282
|
_define_property$1(this, "providerConfigService", void 0);
|
|
6113
6283
|
_define_property$1(this, "jwksService", void 0);
|
|
6114
|
-
this.config = config;
|
|
6115
6284
|
this.providerConfigService = providerConfigService;
|
|
6116
6285
|
this.jwksService = jwksService;
|
|
6117
6286
|
}
|
|
@@ -6164,23 +6333,6 @@ function _ts_generator(thisArg, body) {
|
|
|
6164
6333
|
});
|
|
6165
6334
|
}).call(this);
|
|
6166
6335
|
}
|
|
6167
|
-
},
|
|
6168
|
-
{
|
|
6169
|
-
/**
|
|
6170
|
-
* OAuth Protected Resource discovery endpoint (RFC 8707).
|
|
6171
|
-
*
|
|
6172
|
-
* Returns the authorization server(s) that protect this resource,
|
|
6173
|
-
* allowing clients to discover which authorization server to use.
|
|
6174
|
-
*
|
|
6175
|
-
* @returns The protected resource metadata with authorization server URLs.
|
|
6176
|
-
*/ key: "getProtectedResource",
|
|
6177
|
-
value: function getProtectedResource() {
|
|
6178
|
-
return {
|
|
6179
|
-
authorization_servers: [
|
|
6180
|
-
this.config.issuer
|
|
6181
|
-
]
|
|
6182
|
-
};
|
|
6183
|
-
}
|
|
6184
6336
|
}
|
|
6185
6337
|
]);
|
|
6186
6338
|
return OidcWellKnownController;
|
|
@@ -6191,14 +6343,10 @@ __decorate([
|
|
|
6191
6343
|
__decorate([
|
|
6192
6344
|
common.Get('jwks.json')
|
|
6193
6345
|
], exports.OidcWellKnownController.prototype, "getJwks", null);
|
|
6194
|
-
__decorate([
|
|
6195
|
-
common.Get('oauth-protected-resource')
|
|
6196
|
-
], exports.OidcWellKnownController.prototype, "getProtectedResource", null);
|
|
6197
6346
|
exports.OidcWellKnownController = __decorate([
|
|
6198
6347
|
common.Controller('.well-known'),
|
|
6199
|
-
__param(0, common.Inject(
|
|
6200
|
-
__param(1, common.Inject(exports.
|
|
6201
|
-
__param(2, common.Inject(exports.JwksService))
|
|
6348
|
+
__param(0, common.Inject(exports.OidcProviderConfigService)),
|
|
6349
|
+
__param(1, common.Inject(exports.JwksService))
|
|
6202
6350
|
], exports.OidcWellKnownController);
|
|
6203
6351
|
|
|
6204
6352
|
function _array_like_to_array(arr, len) {
|
|
@@ -6395,6 +6543,7 @@ function _unsupported_iterable_to_array(o, minLen) {
|
|
|
6395
6543
|
tokenLifetimes: DEFAULT_OIDC_TOKEN_LIFETIMES,
|
|
6396
6544
|
trustProxy: envService.isProduction,
|
|
6397
6545
|
trustProxyInNonProduction: false,
|
|
6546
|
+
resourceMetadataUrl: deriveResourceMetadataUrlFromEnv(envService),
|
|
6398
6547
|
jwksServiceConfig: {
|
|
6399
6548
|
encryptionSecret: encryptionSecret
|
|
6400
6549
|
},
|
|
@@ -6405,6 +6554,27 @@ function _unsupported_iterable_to_array(o, minLen) {
|
|
|
6405
6554
|
OidcModuleConfig.assertValidConfig(config);
|
|
6406
6555
|
return config;
|
|
6407
6556
|
}
|
|
6557
|
+
/**
|
|
6558
|
+
* Derives the RFC 9728 protected-resource metadata URL from `envService.appMcpUrl`.
|
|
6559
|
+
*
|
|
6560
|
+
* For `appMcpUrl = http://localhost:9902/dereekb-components/us-central1/api/mcp`, this
|
|
6561
|
+
* returns `http://localhost:9902/dereekb-components/us-central1/api/.well-known/oauth-protected-resource` —
|
|
6562
|
+
* i.e. the discovery doc colocated with the MCP endpoint, regardless of any URL prefix
|
|
6563
|
+
* imposed by the runtime (Firebase Functions emulator, Cloud Run path, etc.).
|
|
6564
|
+
*
|
|
6565
|
+
* Returns `undefined` when no `appMcpUrl` is configured.
|
|
6566
|
+
*
|
|
6567
|
+
* @param envService - The Firebase server environment service.
|
|
6568
|
+
* @returns The discovery URL, or `undefined` if `appMcpUrl` is not set.
|
|
6569
|
+
*/ function deriveResourceMetadataUrlFromEnv(envService) {
|
|
6570
|
+
var mcpUrl = envService.appMcpUrl;
|
|
6571
|
+
if (!mcpUrl) {
|
|
6572
|
+
return undefined;
|
|
6573
|
+
}
|
|
6574
|
+
var parsed = new URL(mcpUrl);
|
|
6575
|
+
var trimmedPath = parsed.pathname.replace(/\/[^/]*\/?$/, '');
|
|
6576
|
+
return "".concat(parsed.origin).concat(trimmedPath, "/.well-known/oauth-protected-resource");
|
|
6577
|
+
}
|
|
6408
6578
|
/**
|
|
6409
6579
|
* Factory that creates {@link OidcServerFirestoreCollections} using the provided Firestore context
|
|
6410
6580
|
* and JWKS encryption config from {@link OidcModuleConfig}.
|
|
@@ -6435,7 +6605,7 @@ function _unsupported_iterable_to_array(o, minLen) {
|
|
|
6435
6605
|
* @param metadataConfig - The configuration for generating the OIDC module metadata.
|
|
6436
6606
|
* @returns The NestJS module metadata for the OIDC module.
|
|
6437
6607
|
*/ function oidcModuleMetadata(metadataConfig) {
|
|
6438
|
-
var dependencyModule = metadataConfig.dependencyModule, config$1 = metadataConfig.config, imports = metadataConfig.imports, exports$1 = metadataConfig.exports, providers = metadataConfig.providers;
|
|
6608
|
+
var dependencyModule = metadataConfig.dependencyModule, config$1 = metadataConfig.config, configFactory = metadataConfig.configFactory, imports = metadataConfig.imports, exports$1 = metadataConfig.exports, providers = metadataConfig.providers;
|
|
6439
6609
|
var dependencyModuleImport = [
|
|
6440
6610
|
dependencyModule
|
|
6441
6611
|
];
|
|
@@ -6465,10 +6635,12 @@ function _unsupported_iterable_to_array(o, minLen) {
|
|
|
6465
6635
|
],
|
|
6466
6636
|
useFactory: function useFactory(configService, envService) {
|
|
6467
6637
|
var moduleConfig = oidcModuleConfigFactory(configService, envService);
|
|
6638
|
+
var dynamicOverrides = configFactory ? configFactory(envService, configService) : undefined;
|
|
6639
|
+
var merged = config$1 || dynamicOverrides ? _object_spread({}, config$1, dynamicOverrides) : undefined;
|
|
6468
6640
|
var result = moduleConfig;
|
|
6469
|
-
if (
|
|
6470
|
-
result = _object_spread({}, moduleConfig,
|
|
6471
|
-
if (
|
|
6641
|
+
if (merged) {
|
|
6642
|
+
result = _object_spread({}, moduleConfig, merged);
|
|
6643
|
+
if (merged.trustProxyInNonProduction && !envService.isProduction) {
|
|
6472
6644
|
result.trustProxy = true;
|
|
6473
6645
|
}
|
|
6474
6646
|
}
|
|
@@ -6480,7 +6652,8 @@ function _unsupported_iterable_to_array(o, minLen) {
|
|
|
6480
6652
|
useFactory: function useFactory(x) {
|
|
6481
6653
|
var _x_protectedPaths;
|
|
6482
6654
|
return {
|
|
6483
|
-
protectedPaths: (_x_protectedPaths = x.protectedPaths) !== null && _x_protectedPaths !== void 0 ? _x_protectedPaths : []
|
|
6655
|
+
protectedPaths: (_x_protectedPaths = x.protectedPaths) !== null && _x_protectedPaths !== void 0 ? _x_protectedPaths : [],
|
|
6656
|
+
resourceMetadataUrl: x.resourceMetadataUrl
|
|
6484
6657
|
};
|
|
6485
6658
|
},
|
|
6486
6659
|
inject: [
|
|
@@ -6591,10 +6764,12 @@ exports.activeJwksKeysQuery = activeJwksKeysQuery;
|
|
|
6591
6764
|
exports.appOidcModelModuleMetadata = appOidcModelModuleMetadata;
|
|
6592
6765
|
exports.applyOidcAuthMiddleware = applyOidcAuthMiddleware;
|
|
6593
6766
|
exports.applyOidcCorsMiddleware = applyOidcCorsMiddleware;
|
|
6767
|
+
exports.buildBearerChallenge = buildBearerChallenge;
|
|
6594
6768
|
exports.createAdapterFactory = createAdapterFactory;
|
|
6595
6769
|
exports.createOidcClientFactory = createOidcClientFactory;
|
|
6596
6770
|
exports.deleteOidcClientFactory = deleteOidcClientFactory;
|
|
6597
6771
|
exports.deleteOidcTokenFactory = deleteOidcTokenFactory;
|
|
6772
|
+
exports.deriveResourceMetadataUrlFromEnv = deriveResourceMetadataUrlFromEnv;
|
|
6598
6773
|
exports.getOidcScopesFromRequest = getOidcScopesFromRequest;
|
|
6599
6774
|
exports.jwksKeyCollectionReference = jwksKeyCollectionReference;
|
|
6600
6775
|
exports.jwksKeyConverter = jwksKeyConverter;
|