@riktajs/core 0.1.0 → 0.2.1
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/README.md +96 -161
- package/dist/core/constants.d.ts +4 -0
- package/dist/core/constants.d.ts.map +1 -1
- package/dist/core/constants.js +5 -1
- package/dist/core/constants.js.map +1 -1
- package/dist/core/decorators/controller.decorator.d.ts.map +1 -1
- package/dist/core/decorators/controller.decorator.js +1 -0
- package/dist/core/decorators/controller.decorator.js.map +1 -1
- package/dist/core/decorators/param.decorator.d.ts +111 -11
- package/dist/core/decorators/param.decorator.d.ts.map +1 -1
- package/dist/core/decorators/param.decorator.js +87 -8
- package/dist/core/decorators/param.decorator.js.map +1 -1
- package/dist/core/exceptions/index.d.ts +1 -0
- package/dist/core/exceptions/index.d.ts.map +1 -1
- package/dist/core/exceptions/index.js +4 -1
- package/dist/core/exceptions/index.js.map +1 -1
- package/dist/core/exceptions/validation.exception.d.ts +60 -0
- package/dist/core/exceptions/validation.exception.d.ts.map +1 -0
- package/dist/core/exceptions/validation.exception.js +71 -0
- package/dist/core/exceptions/validation.exception.js.map +1 -0
- package/dist/core/guards/can-activate.interface.d.ts +77 -0
- package/dist/core/guards/can-activate.interface.d.ts.map +1 -0
- package/dist/core/guards/can-activate.interface.js +3 -0
- package/dist/core/guards/can-activate.interface.js.map +1 -0
- package/dist/core/guards/execution-context.d.ts +72 -0
- package/dist/core/guards/execution-context.d.ts.map +1 -0
- package/dist/core/guards/execution-context.js +37 -0
- package/dist/core/guards/execution-context.js.map +1 -0
- package/dist/core/guards/index.d.ts +4 -0
- package/dist/core/guards/index.d.ts.map +1 -0
- package/dist/core/guards/index.js +10 -0
- package/dist/core/guards/index.js.map +1 -0
- package/dist/core/guards/use-guards.decorator.d.ts +82 -0
- package/dist/core/guards/use-guards.decorator.d.ts.map +1 -0
- package/dist/core/guards/use-guards.decorator.js +104 -0
- package/dist/core/guards/use-guards.decorator.js.map +1 -0
- package/dist/core/index.d.ts +3 -0
- package/dist/core/index.d.ts.map +1 -1
- package/dist/core/index.js +7 -0
- package/dist/core/index.js.map +1 -1
- package/dist/core/router/router.d.ts +9 -1
- package/dist/core/router/router.d.ts.map +1 -1
- package/dist/core/router/router.js +68 -5
- package/dist/core/router/router.js.map +1 -1
- package/package.json +3 -2
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-guards.decorator.d.ts","sourceRoot":"","sources":["../../../src/core/guards/use-guards.decorator.ts"],"names":[],"mappings":"AAAA,OAAO,kBAAkB,CAAC;AAE1B,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,UAAU,CAAC;AAC5C,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAE5D;;GAEG;AACH,MAAM,MAAM,UAAU,GAAG,WAAW,CAAC,WAAW,CAAC,CAAC;AAElD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAgEG;AACH,wBAAgB,SAAS,CAAC,GAAG,MAAM,EAAE,UAAU,EAAE,GAAG,cAAc,GAAG,eAAe,CA2BnF;AAED;;;;;;GAMG;AACH,wBAAgB,iBAAiB,CAC/B,MAAM,EAAE,WAAW,EACnB,WAAW,CAAC,EAAE,MAAM,GAAG,MAAM,GAC5B,UAAU,EAAE,CAed"}
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.UseGuards = UseGuards;
|
|
4
|
+
exports.getGuardsMetadata = getGuardsMetadata;
|
|
5
|
+
require("reflect-metadata");
|
|
6
|
+
const constants_1 = require("../constants");
|
|
7
|
+
/**
|
|
8
|
+
* @UseGuards() Decorator
|
|
9
|
+
*
|
|
10
|
+
* Applies one or more guards to a controller or route handler.
|
|
11
|
+
* Guards are executed in order before the handler runs.
|
|
12
|
+
*
|
|
13
|
+
* Guards are resolved from the DI container, so they can have
|
|
14
|
+
* injected dependencies. Make sure guards are decorated with @Injectable().
|
|
15
|
+
*
|
|
16
|
+
* @param guards - Guard classes to apply
|
|
17
|
+
*
|
|
18
|
+
* @example Apply guard to entire controller
|
|
19
|
+
* ```typescript
|
|
20
|
+
* @Controller('/admin')
|
|
21
|
+
* @UseGuards(AuthGuard)
|
|
22
|
+
* class AdminController {
|
|
23
|
+
* @Get('/dashboard')
|
|
24
|
+
* getDashboard() {
|
|
25
|
+
* return { message: 'Admin dashboard' };
|
|
26
|
+
* }
|
|
27
|
+
* }
|
|
28
|
+
* ```
|
|
29
|
+
*
|
|
30
|
+
* @example Apply guard to specific route
|
|
31
|
+
* ```typescript
|
|
32
|
+
* @Controller('/users')
|
|
33
|
+
* class UserController {
|
|
34
|
+
* @Get()
|
|
35
|
+
* findAll() {
|
|
36
|
+
* return []; // Public route
|
|
37
|
+
* }
|
|
38
|
+
*
|
|
39
|
+
* @Post()
|
|
40
|
+
* @UseGuards(AuthGuard)
|
|
41
|
+
* create() {
|
|
42
|
+
* return {}; // Protected route
|
|
43
|
+
* }
|
|
44
|
+
* }
|
|
45
|
+
* ```
|
|
46
|
+
*
|
|
47
|
+
* @example Multiple guards (AND logic - all must pass)
|
|
48
|
+
* ```typescript
|
|
49
|
+
* @Controller('/admin')
|
|
50
|
+
* @UseGuards(AuthGuard, RolesGuard)
|
|
51
|
+
* class AdminController {
|
|
52
|
+
* // User must be authenticated AND have correct role
|
|
53
|
+
* }
|
|
54
|
+
* ```
|
|
55
|
+
*
|
|
56
|
+
* @example Combined controller and method guards
|
|
57
|
+
* ```typescript
|
|
58
|
+
* @Controller('/api')
|
|
59
|
+
* @UseGuards(AuthGuard) // Applied to all routes
|
|
60
|
+
* class ApiController {
|
|
61
|
+
* @Get('/public')
|
|
62
|
+
* // Only AuthGuard runs
|
|
63
|
+
* getPublic() {}
|
|
64
|
+
*
|
|
65
|
+
* @Post('/admin')
|
|
66
|
+
* @UseGuards(AdminGuard) // Additional guard
|
|
67
|
+
* // Both AuthGuard AND AdminGuard run
|
|
68
|
+
* adminAction() {}
|
|
69
|
+
* }
|
|
70
|
+
* ```
|
|
71
|
+
*/
|
|
72
|
+
function UseGuards(...guards) {
|
|
73
|
+
return (target, propertyKey) => {
|
|
74
|
+
if (propertyKey !== undefined) {
|
|
75
|
+
// Method decorator - store on the method
|
|
76
|
+
const existingGuards = Reflect.getMetadata(constants_1.GUARDS_METADATA, target.constructor, propertyKey) ?? [];
|
|
77
|
+
Reflect.defineMetadata(constants_1.GUARDS_METADATA, [...existingGuards, ...guards], target.constructor, propertyKey);
|
|
78
|
+
}
|
|
79
|
+
else {
|
|
80
|
+
// Class decorator - store on the class
|
|
81
|
+
const existingGuards = Reflect.getMetadata(constants_1.GUARDS_METADATA, target) ?? [];
|
|
82
|
+
Reflect.defineMetadata(constants_1.GUARDS_METADATA, [...existingGuards, ...guards], target);
|
|
83
|
+
}
|
|
84
|
+
};
|
|
85
|
+
}
|
|
86
|
+
/**
|
|
87
|
+
* Get guards metadata from a controller class and/or method
|
|
88
|
+
*
|
|
89
|
+
* @param target - Controller class
|
|
90
|
+
* @param propertyKey - Method name (optional)
|
|
91
|
+
* @returns Combined array of guard classes (controller + method)
|
|
92
|
+
*/
|
|
93
|
+
function getGuardsMetadata(target, propertyKey) {
|
|
94
|
+
// Get class-level guards
|
|
95
|
+
const classGuards = Reflect.getMetadata(constants_1.GUARDS_METADATA, target) ?? [];
|
|
96
|
+
if (!propertyKey) {
|
|
97
|
+
return classGuards;
|
|
98
|
+
}
|
|
99
|
+
// Get method-level guards
|
|
100
|
+
const methodGuards = Reflect.getMetadata(constants_1.GUARDS_METADATA, target, propertyKey) ?? [];
|
|
101
|
+
// Combine: class guards run first, then method guards
|
|
102
|
+
return [...classGuards, ...methodGuards];
|
|
103
|
+
}
|
|
104
|
+
//# sourceMappingURL=use-guards.decorator.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"use-guards.decorator.js","sourceRoot":"","sources":["../../../src/core/guards/use-guards.decorator.ts"],"names":[],"mappings":";;AA2EA,8BA2BC;AASD,8CAkBC;AAjID,4BAA0B;AAC1B,4CAA+C;AAS/C;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAgEG;AACH,SAAgB,SAAS,CAAC,GAAG,MAAoB;IAC/C,OAAO,CACL,MAAc,EACd,WAA6B,EAEvB,EAAE;QACR,IAAI,WAAW,KAAK,SAAS,EAAE,CAAC;YAC9B,yCAAyC;YACzC,MAAM,cAAc,GAClB,OAAO,CAAC,WAAW,CAAC,2BAAe,EAAE,MAAM,CAAC,WAAW,EAAE,WAAW,CAAC,IAAI,EAAE,CAAC;YAC9E,OAAO,CAAC,cAAc,CACpB,2BAAe,EACf,CAAC,GAAG,cAAc,EAAE,GAAG,MAAM,CAAC,EAC9B,MAAM,CAAC,WAAW,EAClB,WAAW,CACZ,CAAC;QACJ,CAAC;aAAM,CAAC;YACN,uCAAuC;YACvC,MAAM,cAAc,GAClB,OAAO,CAAC,WAAW,CAAC,2BAAe,EAAE,MAAM,CAAC,IAAI,EAAE,CAAC;YACrD,OAAO,CAAC,cAAc,CACpB,2BAAe,EACf,CAAC,GAAG,cAAc,EAAE,GAAG,MAAM,CAAC,EAC9B,MAAM,CACP,CAAC;QACJ,CAAC;IACH,CAAC,CAAC;AACJ,CAAC;AAED;;;;;;GAMG;AACH,SAAgB,iBAAiB,CAC/B,MAAmB,EACnB,WAA6B;IAE7B,yBAAyB;IACzB,MAAM,WAAW,GACf,OAAO,CAAC,WAAW,CAAC,2BAAe,EAAE,MAAM,CAAC,IAAI,EAAE,CAAC;IAErD,IAAI,CAAC,WAAW,EAAE,CAAC;QACjB,OAAO,WAAW,CAAC;IACrB,CAAC;IAED,0BAA0B;IAC1B,MAAM,YAAY,GAChB,OAAO,CAAC,WAAW,CAAC,2BAAe,EAAE,MAAM,EAAE,WAAW,CAAC,IAAI,EAAE,CAAC;IAElE,sDAAsD;IACtD,OAAO,CAAC,GAAG,WAAW,EAAE,GAAG,YAAY,CAAC,CAAC;AAC3C,CAAC"}
|
package/dist/core/index.d.ts
CHANGED
|
@@ -8,4 +8,7 @@ export * from './router/router';
|
|
|
8
8
|
export * from './application';
|
|
9
9
|
export * from './decorators';
|
|
10
10
|
export * from './exceptions';
|
|
11
|
+
export * from './guards';
|
|
12
|
+
export { z } from 'zod';
|
|
13
|
+
export type { ZodType, ZodSchema, ZodError, ZodIssue, infer as ZodInfer } from 'zod';
|
|
11
14
|
//# sourceMappingURL=index.d.ts.map
|
package/dist/core/index.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/core/index.ts"],"names":[],"mappings":"AACA,cAAc,SAAS,CAAC;AACxB,cAAc,aAAa,CAAC;AAC5B,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,aAAa,CAAC;AAC5B,cAAc,iBAAiB,CAAC;AAChC,cAAc,eAAe,CAAC;AAC9B,cAAc,cAAc,CAAC;AAC7B,cAAc,cAAc,CAAC"}
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/core/index.ts"],"names":[],"mappings":"AACA,cAAc,SAAS,CAAC;AACxB,cAAc,aAAa,CAAC;AAC5B,cAAc,aAAa,CAAC;AAC5B,cAAc,YAAY,CAAC;AAC3B,cAAc,aAAa,CAAC;AAC5B,cAAc,aAAa,CAAC;AAC5B,cAAc,iBAAiB,CAAC;AAChC,cAAc,eAAe,CAAC;AAC9B,cAAc,cAAc,CAAC;AAC7B,cAAc,cAAc,CAAC;AAC7B,cAAc,UAAU,CAAC;AAKzB,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,YAAY,EAAE,OAAO,EAAE,SAAS,EAAE,QAAQ,EAAE,QAAQ,EAAE,KAAK,IAAI,QAAQ,EAAE,MAAM,KAAK,CAAC"}
|
package/dist/core/index.js
CHANGED
|
@@ -14,6 +14,7 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
|
14
14
|
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
15
15
|
};
|
|
16
16
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
17
|
+
exports.z = void 0;
|
|
17
18
|
// Core exports
|
|
18
19
|
__exportStar(require("./types"), exports);
|
|
19
20
|
__exportStar(require("./constants"), exports);
|
|
@@ -25,4 +26,10 @@ __exportStar(require("./router/router"), exports);
|
|
|
25
26
|
__exportStar(require("./application"), exports);
|
|
26
27
|
__exportStar(require("./decorators"), exports);
|
|
27
28
|
__exportStar(require("./exceptions"), exports);
|
|
29
|
+
__exportStar(require("./guards"), exports);
|
|
30
|
+
// Re-export Zod for convenience
|
|
31
|
+
// This allows users to import everything from '@riktajs/core':
|
|
32
|
+
// import { z, Body, Controller } from '@riktajs/core';
|
|
33
|
+
var zod_1 = require("zod");
|
|
34
|
+
Object.defineProperty(exports, "z", { enumerable: true, get: function () { return zod_1.z; } });
|
|
28
35
|
//# sourceMappingURL=index.js.map
|
package/dist/core/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/core/index.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/core/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,eAAe;AACf,0CAAwB;AACxB,8CAA4B;AAC5B,8CAA4B;AAC5B,6CAA2B;AAC3B,8CAA4B;AAC5B,8CAA4B;AAC5B,kDAAgC;AAChC,gDAA8B;AAC9B,+CAA6B;AAC7B,+CAA6B;AAC7B,2CAAyB;AAEzB,gCAAgC;AAChC,+DAA+D;AAC/D,uDAAuD;AACvD,2BAAwB;AAAf,wFAAA,CAAC,OAAA"}
|
|
@@ -32,8 +32,16 @@ export declare class Router {
|
|
|
32
32
|
*/
|
|
33
33
|
private resolveParams;
|
|
34
34
|
/**
|
|
35
|
-
* Resolve a single parameter
|
|
35
|
+
* Resolve a single parameter with optional Zod validation
|
|
36
36
|
*/
|
|
37
37
|
private resolveParam;
|
|
38
|
+
/**
|
|
39
|
+
* Execute guards for a route
|
|
40
|
+
* Guards are executed in order (controller-level first, then method-level)
|
|
41
|
+
* All guards must pass (AND logic)
|
|
42
|
+
*
|
|
43
|
+
* @throws ForbiddenException if any guard returns false
|
|
44
|
+
*/
|
|
45
|
+
private executeGuards;
|
|
38
46
|
}
|
|
39
47
|
//# sourceMappingURL=router.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"router.d.ts","sourceRoot":"","sources":["../../../src/core/router/router.ts"],"names":[],"mappings":"AAAA,OAAO,kBAAkB,CAAC;AAC1B,OAAO,EAAE,eAAe,EAAgC,MAAM,SAAS,CAAC;AACxE,OAAO,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAC;AAQnD,OAAO,EAAE,WAAW,EAAiC,MAAM,UAAU,CAAC;
|
|
1
|
+
{"version":3,"file":"router.d.ts","sourceRoot":"","sources":["../../../src/core/router/router.ts"],"names":[],"mappings":"AAAA,OAAO,kBAAkB,CAAC;AAC1B,OAAO,EAAE,eAAe,EAAgC,MAAM,SAAS,CAAC;AACxE,OAAO,EAAE,SAAS,EAAE,MAAM,wBAAwB,CAAC;AAQnD,OAAO,EAAE,WAAW,EAAiC,MAAM,UAAU,CAAC;AAQtE;;;;;;;GAOG;AACH,qBAAa,MAAM;IAEf,OAAO,CAAC,QAAQ,CAAC,MAAM;IACvB,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,YAAY;gBAFZ,MAAM,EAAE,eAAe,EACvB,SAAS,EAAE,SAAS,EACpB,YAAY,GAAE,MAAW;IAG5C;;OAEG;IACH,kBAAkB,CAAC,eAAe,EAAE,WAAW,GAAG,IAAI;IAuBtD;;OAEG;IACH,OAAO,CAAC,aAAa;IAuErB;;OAEG;IACH,OAAO,CAAC,SAAS;IASjB;;OAEG;IACH,OAAO,CAAC,aAAa;IAmBrB;;OAEG;IACH,OAAO,CAAC,YAAY;IA8DpB;;;;;;OAMG;YACW,aAAa;CAgD5B"}
|
|
@@ -3,6 +3,10 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.Router = void 0;
|
|
4
4
|
require("reflect-metadata");
|
|
5
5
|
const constants_1 = require("../constants");
|
|
6
|
+
const validation_exception_1 = require("../exceptions/validation.exception");
|
|
7
|
+
const exceptions_1 = require("../exceptions/exceptions");
|
|
8
|
+
const execution_context_1 = require("../guards/execution-context");
|
|
9
|
+
const use_guards_decorator_1 = require("../guards/use-guards.decorator");
|
|
6
10
|
/**
|
|
7
11
|
* Router class
|
|
8
12
|
*
|
|
@@ -54,9 +58,15 @@ class Router {
|
|
|
54
58
|
const paramsMeta = Reflect.getMetadata(constants_1.PARAM_METADATA, controllerClass, route.handlerName) ?? [];
|
|
55
59
|
// Get HTTP status code if set
|
|
56
60
|
const statusCode = Reflect.getMetadata(constants_1.HTTP_CODE_METADATA, controllerClass, route.handlerName);
|
|
61
|
+
// Get guards for this route (controller-level + method-level)
|
|
62
|
+
const guards = (0, use_guards_decorator_1.getGuardsMetadata)(controllerClass, route.handlerName);
|
|
57
63
|
// Create the route handler
|
|
58
64
|
const routeHandler = async (request, reply) => {
|
|
59
65
|
try {
|
|
66
|
+
// Execute guards before handler
|
|
67
|
+
if (guards.length > 0) {
|
|
68
|
+
await this.executeGuards(guards, request, reply, controllerClass, route.handlerName);
|
|
69
|
+
}
|
|
60
70
|
// Build route context
|
|
61
71
|
const context = {
|
|
62
72
|
request,
|
|
@@ -115,26 +125,32 @@ class Router {
|
|
|
115
125
|
return args;
|
|
116
126
|
}
|
|
117
127
|
/**
|
|
118
|
-
* Resolve a single parameter
|
|
128
|
+
* Resolve a single parameter with optional Zod validation
|
|
119
129
|
*/
|
|
120
130
|
resolveParam(param, context) {
|
|
131
|
+
// Get raw value based on parameter type
|
|
132
|
+
let rawValue;
|
|
121
133
|
switch (param.type) {
|
|
122
134
|
case constants_1.ParamType.BODY:
|
|
123
|
-
|
|
135
|
+
rawValue = param.key
|
|
124
136
|
? context.body?.[param.key]
|
|
125
137
|
: context.body;
|
|
138
|
+
break;
|
|
126
139
|
case constants_1.ParamType.QUERY:
|
|
127
|
-
|
|
140
|
+
rawValue = param.key
|
|
128
141
|
? context.query[param.key]
|
|
129
142
|
: context.query;
|
|
143
|
+
break;
|
|
130
144
|
case constants_1.ParamType.PARAM:
|
|
131
|
-
|
|
145
|
+
rawValue = param.key
|
|
132
146
|
? context.params[param.key]
|
|
133
147
|
: context.params;
|
|
148
|
+
break;
|
|
134
149
|
case constants_1.ParamType.HEADERS:
|
|
135
|
-
|
|
150
|
+
rawValue = param.key
|
|
136
151
|
? context.request.headers[param.key.toLowerCase()]
|
|
137
152
|
: context.request.headers;
|
|
153
|
+
break;
|
|
138
154
|
case constants_1.ParamType.REQUEST:
|
|
139
155
|
return context.request;
|
|
140
156
|
case constants_1.ParamType.REPLY:
|
|
@@ -144,6 +160,53 @@ class Router {
|
|
|
144
160
|
default:
|
|
145
161
|
return undefined;
|
|
146
162
|
}
|
|
163
|
+
// If a Zod schema is provided, validate the raw value
|
|
164
|
+
if (param.zodSchema) {
|
|
165
|
+
const result = param.zodSchema.safeParse(rawValue);
|
|
166
|
+
if (!result.success) {
|
|
167
|
+
// Throw ValidationException with Zod error details
|
|
168
|
+
throw new validation_exception_1.ValidationException(result.error, `Validation failed for ${param.type}${param.key ? ` (${param.key})` : ''}`);
|
|
169
|
+
}
|
|
170
|
+
// Return the validated and transformed data
|
|
171
|
+
return result.data;
|
|
172
|
+
}
|
|
173
|
+
// No schema provided, return raw value (backward compatible)
|
|
174
|
+
return rawValue;
|
|
175
|
+
}
|
|
176
|
+
/**
|
|
177
|
+
* Execute guards for a route
|
|
178
|
+
* Guards are executed in order (controller-level first, then method-level)
|
|
179
|
+
* All guards must pass (AND logic)
|
|
180
|
+
*
|
|
181
|
+
* @throws ForbiddenException if any guard returns false
|
|
182
|
+
*/
|
|
183
|
+
async executeGuards(guards, request, reply, controllerClass, handlerName) {
|
|
184
|
+
// Create execution context
|
|
185
|
+
const context = new execution_context_1.ExecutionContextImpl(request, reply, controllerClass, handlerName);
|
|
186
|
+
// Execute each guard sequentially
|
|
187
|
+
for (const GuardClass of guards) {
|
|
188
|
+
// Resolve guard instance from DI container
|
|
189
|
+
let guardInstance;
|
|
190
|
+
try {
|
|
191
|
+
guardInstance = this.container.resolve(GuardClass);
|
|
192
|
+
}
|
|
193
|
+
catch (error) {
|
|
194
|
+
throw new Error(`Failed to resolve guard ${GuardClass.name}. ` +
|
|
195
|
+
`Make sure it is decorated with @Injectable(). ` +
|
|
196
|
+
`Original error: ${error instanceof Error ? error.message : String(error)}`);
|
|
197
|
+
}
|
|
198
|
+
// Verify the guard has canActivate method
|
|
199
|
+
if (typeof guardInstance.canActivate !== 'function') {
|
|
200
|
+
throw new Error(`${GuardClass.name} does not implement CanActivate interface. ` +
|
|
201
|
+
`The guard must have a canActivate(context: ExecutionContext) method.`);
|
|
202
|
+
}
|
|
203
|
+
// Execute the guard
|
|
204
|
+
const result = await guardInstance.canActivate(context);
|
|
205
|
+
// If guard returns false, deny access
|
|
206
|
+
if (result !== true) {
|
|
207
|
+
throw new exceptions_1.ForbiddenException(`Access denied by ${GuardClass.name}`);
|
|
208
|
+
}
|
|
209
|
+
}
|
|
147
210
|
}
|
|
148
211
|
}
|
|
149
212
|
exports.Router = Router;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"router.js","sourceRoot":"","sources":["../../../src/core/router/router.ts"],"names":[],"mappings":";;;AAAA,4BAA0B;AAG1B,4CAMsB;
|
|
1
|
+
{"version":3,"file":"router.js","sourceRoot":"","sources":["../../../src/core/router/router.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@riktajs/core",
|
|
3
|
-
"version": "0.1
|
|
3
|
+
"version": "0.2.1",
|
|
4
4
|
"description": "A fast and modern TypeScript backend framework with zero-config autowiring, powered by Fastify",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -31,7 +31,8 @@
|
|
|
31
31
|
"dependencies": {
|
|
32
32
|
"fast-glob": "^3.3.2",
|
|
33
33
|
"fastify": "^5.1.0",
|
|
34
|
-
"reflect-metadata": "^0.2.2"
|
|
34
|
+
"reflect-metadata": "^0.2.2",
|
|
35
|
+
"zod": "^3.25.76"
|
|
35
36
|
},
|
|
36
37
|
"devDependencies": {
|
|
37
38
|
"@types/node": "^22.10.2",
|