@alleen/core 0.1.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.
Files changed (34) hide show
  1. package/README.md +165 -0
  2. package/dist/alleen.module.d.ts +25 -0
  3. package/dist/alleen.module.d.ts.map +1 -0
  4. package/dist/alleen.module.js +60 -0
  5. package/dist/alleen.module.js.map +1 -0
  6. package/dist/database/database.controller.d.ts +46 -0
  7. package/dist/database/database.controller.d.ts.map +1 -0
  8. package/dist/database/database.controller.js +101 -0
  9. package/dist/database/database.controller.js.map +1 -0
  10. package/dist/database/database.service.d.ts +28 -0
  11. package/dist/database/database.service.d.ts.map +1 -0
  12. package/dist/database/database.service.js +113 -0
  13. package/dist/database/database.service.js.map +1 -0
  14. package/dist/dto/alleen-query.dto.d.ts +12 -0
  15. package/dist/dto/alleen-query.dto.d.ts.map +1 -0
  16. package/dist/dto/alleen-query.dto.js +25 -0
  17. package/dist/dto/alleen-query.dto.js.map +1 -0
  18. package/dist/examples/app.module.example.d.ts +1 -0
  19. package/dist/examples/app.module.example.d.ts.map +1 -0
  20. package/dist/examples/app.module.example.js +61 -0
  21. package/dist/examples/app.module.example.js.map +1 -0
  22. package/dist/index.d.ts +7 -0
  23. package/dist/index.d.ts.map +1 -0
  24. package/dist/index.js +14 -0
  25. package/dist/index.js.map +1 -0
  26. package/dist/interceptors/logger.interceptor.d.ts +16 -0
  27. package/dist/interceptors/logger.interceptor.d.ts.map +1 -0
  28. package/dist/interceptors/logger.interceptor.js +43 -0
  29. package/dist/interceptors/logger.interceptor.js.map +1 -0
  30. package/dist/types.d.ts +42 -0
  31. package/dist/types.d.ts.map +1 -0
  32. package/dist/types.js +4 -0
  33. package/dist/types.js.map +1 -0
  34. package/package.json +39 -0
package/README.md ADDED
@@ -0,0 +1,165 @@
1
+ # @alleen/core
2
+
3
+ > Core NestJS module for **alleen-api** — Dynamic multi-database Prisma registry. No more switch statements.
4
+
5
+ ---
6
+
7
+ ## Installation
8
+
9
+ ```bash
10
+ npm install @alleen/core
11
+ ```
12
+
13
+ ---
14
+
15
+ ## Setup (3 étapes)
16
+
17
+ ### 1. Ajouter tes bases de données via le CLI
18
+ ```bash
19
+ npx alleen db:add --name=phoenix --url=postgresql://...
20
+ npx alleen db:add --name=bulk --url=postgresql://...
21
+ ```
22
+
23
+ ### 2. Brancher dans `app.module.ts`
24
+ ```ts
25
+ import { AlleenModule } from '@alleen/core';
26
+ import { PRISMA_REGISTRY, PRISMA_PROVIDERS } from './prisma/prisma.registry';
27
+
28
+ @Module({
29
+ imports: [
30
+ AlleenModule.forRoot({
31
+ registry: PRISMA_REGISTRY,
32
+ providers: PRISMA_PROVIDERS,
33
+ exposeApi: true,
34
+ }),
35
+ ],
36
+ })
37
+ export class AppModule {}
38
+ ```
39
+
40
+ ### 3. C'est tout ✅
41
+ Ton API est prête.
42
+
43
+ ---
44
+
45
+ ## Endpoints exposés automatiquement
46
+
47
+ ### `POST /alleen/query`
48
+ Effectue n'importe quelle opération Prisma sur n'importe quelle DB enregistrée.
49
+
50
+ ```json
51
+ {
52
+ "database": "phoenix",
53
+ "model": "User",
54
+ "action": "findMany",
55
+ "args": {
56
+ "where": { "active": true },
57
+ "include": { "profile": true },
58
+ "take": 10
59
+ }
60
+ }
61
+ ```
62
+
63
+ **Réponse :**
64
+ ```json
65
+ {
66
+ "success": true,
67
+ "data": [...],
68
+ "meta": {
69
+ "database": "phoenix",
70
+ "model": "User",
71
+ "action": "findMany",
72
+ "duration": 38
73
+ }
74
+ }
75
+ ```
76
+
77
+ ---
78
+
79
+ ### `GET /alleen/databases`
80
+ Liste toutes les DBs enregistrées.
81
+ ```json
82
+ {
83
+ "success": true,
84
+ "databases": ["phoenix", "bulk", "finance"]
85
+ }
86
+ ```
87
+
88
+ ### `GET /alleen/health`
89
+ Health check.
90
+ ```json
91
+ {
92
+ "status": "ok",
93
+ "databases": 3,
94
+ "registered": ["phoenix", "bulk", "finance"],
95
+ "timestamp": "2026-04-05T10:00:00.000Z"
96
+ }
97
+ ```
98
+
99
+ ---
100
+
101
+ ## Actions Prisma supportées
102
+
103
+ | Action | Description |
104
+ |---|---|
105
+ | `findUnique` | Trouver un enregistrement unique |
106
+ | `findFirst` | Premier enregistrement correspondant |
107
+ | `findMany` | Liste d'enregistrements |
108
+ | `create` | Créer un enregistrement |
109
+ | `createMany` | Créer plusieurs enregistrements |
110
+ | `update` | Mettre à jour un enregistrement |
111
+ | `updateMany` | Mettre à jour plusieurs enregistrements |
112
+ | `upsert` | Créer ou mettre à jour |
113
+ | `delete` | Supprimer un enregistrement |
114
+ | `deleteMany` | Supprimer plusieurs enregistrements |
115
+ | `count` | Compter les enregistrements |
116
+ | `aggregate` | Agréger des données |
117
+ | `groupBy` | Grouper des données |
118
+
119
+ ---
120
+
121
+ ## Utiliser `DatabaseService` directement
122
+
123
+ Pour les cas complexes, injecte `DatabaseService` dans tes propres services :
124
+
125
+ ```ts
126
+ import { Injectable } from '@nestjs/common';
127
+ import { DatabaseService } from '@alleen/core';
128
+
129
+ @Injectable()
130
+ export class OrderService {
131
+ constructor(private readonly db: DatabaseService) {}
132
+
133
+ async getActiveOrders() {
134
+ return this.db.execute({
135
+ database: 'phoenix',
136
+ model: 'Order',
137
+ action: 'findMany',
138
+ args: { where: { status: 'ACTIVE' } },
139
+ });
140
+ }
141
+ }
142
+ ```
143
+
144
+ ---
145
+
146
+ ## Logging (optionnel)
147
+
148
+ ```ts
149
+ // main.ts
150
+ import { AlleenLoggerInterceptor } from '@alleen/core';
151
+
152
+ app.useGlobalInterceptors(new AlleenLoggerInterceptor());
153
+ ```
154
+
155
+ ```
156
+ ✅ [phoenix] User.findMany — 42ms
157
+ ✅ [bulk] Order.create — 18ms
158
+ ❌ [finance] Invoice.findUnique — 5ms
159
+ ```
160
+
161
+ ---
162
+
163
+ ## License
164
+
165
+ MIT © olivier adou
@@ -0,0 +1,25 @@
1
+ import { DynamicModule } from '@nestjs/common';
2
+ import { PrismaRegistry } from './types';
3
+ export interface AlleenModuleOptions {
4
+ /** Le registry généré par @alleen/cli — importé depuis prisma.registry.ts */
5
+ registry: PrismaRegistry;
6
+ /** Les providers PrismaService à injecter (PRISMA_PROVIDERS du registry) */
7
+ providers: any[];
8
+ /** Exposer l'endpoint HTTP /alleen ? (default: true) */
9
+ exposeApi?: boolean;
10
+ }
11
+ export declare class AlleenModule {
12
+ /**
13
+ * Usage dans app.module.ts :
14
+ *
15
+ * import { PRISMA_REGISTRY, PRISMA_PROVIDERS } from './prisma/prisma.registry';
16
+ *
17
+ * AlleenModule.forRoot({
18
+ * registry: PRISMA_REGISTRY,
19
+ * providers: PRISMA_PROVIDERS,
20
+ * exposeApi: true,
21
+ * })
22
+ */
23
+ static forRoot(options: AlleenModuleOptions): DynamicModule;
24
+ }
25
+ //# sourceMappingURL=alleen.module.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"alleen.module.d.ts","sourceRoot":"","sources":["../src/alleen.module.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAkB,MAAM,gBAAgB,CAAC;AAG/D,OAAO,EAAE,cAAc,EAAE,MAAqB,SAAS,CAAC;AAExD,MAAM,WAAW,mBAAmB;IAClC,6EAA6E;IAC7E,QAAQ,EAAE,cAAc,CAAC;IACzB,4EAA4E;IAC5E,SAAS,EAAE,GAAG,EAAE,CAAC;IACjB,wDAAwD;IACxD,SAAS,CAAC,EAAE,OAAO,CAAC;CACrB;AAED,qBAEa,YAAY;IACvB;;;;;;;;;;OAUG;IACH,MAAM,CAAC,OAAO,CAAC,OAAO,EAAE,mBAAmB,GAAG,aAAa;CAgC5D"}
@@ -0,0 +1,60 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ var AlleenModule_1;
9
+ Object.defineProperty(exports, "__esModule", { value: true });
10
+ exports.AlleenModule = void 0;
11
+ const common_1 = require("@nestjs/common");
12
+ const database_service_1 = require("./database/database.service");
13
+ const database_controller_1 = require("./database/database.controller");
14
+ let AlleenModule = AlleenModule_1 = class AlleenModule {
15
+ /**
16
+ * Usage dans app.module.ts :
17
+ *
18
+ * import { PRISMA_REGISTRY, PRISMA_PROVIDERS } from './prisma/prisma.registry';
19
+ *
20
+ * AlleenModule.forRoot({
21
+ * registry: PRISMA_REGISTRY,
22
+ * providers: PRISMA_PROVIDERS,
23
+ * exposeApi: true,
24
+ * })
25
+ */
26
+ static forRoot(options) {
27
+ const { registry, providers, exposeApi = true } = options;
28
+ // Token d'injection pour le registry
29
+ const REGISTRY_TOKEN = 'ALLEEN_REGISTRY';
30
+ const registryProvider = {
31
+ provide: REGISTRY_TOKEN,
32
+ useValue: registry,
33
+ };
34
+ const databaseServiceProvider = {
35
+ provide: database_service_1.DatabaseService,
36
+ useFactory: (moduleRef) => new database_service_1.DatabaseService(moduleRef, registry),
37
+ inject: ['ModuleRef'],
38
+ };
39
+ return {
40
+ module: AlleenModule_1,
41
+ imports: [],
42
+ controllers: exposeApi ? [database_controller_1.AlleenController] : [],
43
+ providers: [
44
+ ...providers, // PhoenixPrismaService, BulkPrismaService...
45
+ registryProvider, // ALLEEN_REGISTRY token
46
+ databaseServiceProvider, // DatabaseService avec registry injecté
47
+ ],
48
+ exports: [
49
+ database_service_1.DatabaseService,
50
+ ...providers, // Les PrismaServices accessibles dans toute l'app
51
+ ],
52
+ };
53
+ }
54
+ };
55
+ exports.AlleenModule = AlleenModule;
56
+ exports.AlleenModule = AlleenModule = AlleenModule_1 = __decorate([
57
+ (0, common_1.Global)(),
58
+ (0, common_1.Module)({})
59
+ ], AlleenModule);
60
+ //# sourceMappingURL=alleen.module.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"alleen.module.js","sourceRoot":"","sources":["../src/alleen.module.ts"],"names":[],"mappings":";;;;;;;;;;AAAA,2CAA+D;AAC/D,kEAA4E;AAC5E,wEAA+E;AAcxE,IAAM,YAAY,oBAAlB,MAAM,YAAY;IACvB;;;;;;;;;;OAUG;IACH,MAAM,CAAC,OAAO,CAAC,OAA4B;QACzC,MAAM,EAAE,QAAQ,EAAE,SAAS,EAAE,SAAS,GAAG,IAAI,EAAE,GAAG,OAAO,CAAC;QAE1D,qCAAqC;QACrC,MAAM,cAAc,GAAG,iBAAiB,CAAC;QAEzC,MAAM,gBAAgB,GAAG;YACvB,OAAO,EAAG,cAAc;YACxB,QAAQ,EAAE,QAAQ;SACnB,CAAC;QAEF,MAAM,uBAAuB,GAAG;YAC9B,OAAO,EAAK,kCAAe;YAC3B,UAAU,EAAE,CAAC,SAAc,EAAE,EAAE,CAAC,IAAI,kCAAe,CAAC,SAAS,EAAE,QAAQ,CAAC;YACxE,MAAM,EAAM,CAAC,WAAW,CAAC;SAC1B,CAAC;QAEF,OAAO;YACL,MAAM,EAAO,cAAY;YACzB,OAAO,EAAM,EAAE;YACf,WAAW,EAAE,SAAS,CAAC,CAAC,CAAC,CAAC,sCAAgB,CAAC,CAAC,CAAC,CAAC,EAAE;YAChD,SAAS,EAAE;gBACT,GAAG,SAAS,EAAY,6CAA6C;gBACrE,gBAAgB,EAAQ,wBAAwB;gBAChD,uBAAuB,EAAC,wCAAwC;aACjE;YACD,OAAO,EAAE;gBACP,kCAAe;gBACf,GAAG,SAAS,EAAY,kDAAkD;aAC3E;SACF,CAAC;IACJ,CAAC;CACF,CAAA;AA5CY,oCAAY;uBAAZ,YAAY;IAFxB,IAAA,eAAM,GAAE;IACR,IAAA,eAAM,EAAC,EAAE,CAAC;GACE,YAAY,CA4CxB"}
@@ -0,0 +1,46 @@
1
+ import { DatabaseService } from './database.service';
2
+ import { AlleenQuery } from '../types';
3
+ export declare class AlleenController {
4
+ private readonly databaseService;
5
+ private readonly logger;
6
+ constructor(databaseService: DatabaseService);
7
+ /**
8
+ * POST /alleen/query
9
+ *
10
+ * Endpoint universel pour toutes les opérations CRUD.
11
+ *
12
+ * Body:
13
+ * {
14
+ * "database": "phoenix",
15
+ * "model": "User",
16
+ * "action": "findMany",
17
+ * "args": {
18
+ * "where": { "active": true },
19
+ * "include": { "orders": true }
20
+ * }
21
+ * }
22
+ */
23
+ query(body: AlleenQuery): Promise<import("../types").AlleenResult<any>>;
24
+ /**
25
+ * GET /alleen/databases
26
+ *
27
+ * Liste toutes les bases de données enregistrées.
28
+ * Utile pour le debug et la santé du système.
29
+ */
30
+ getDatabases(): {
31
+ success: boolean;
32
+ databases: string[];
33
+ };
34
+ /**
35
+ * GET /alleen/health
36
+ *
37
+ * Health check rapide.
38
+ */
39
+ health(): {
40
+ status: string;
41
+ databases: number;
42
+ registered: string[];
43
+ timestamp: string;
44
+ };
45
+ }
46
+ //# sourceMappingURL=database.controller.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"database.controller.d.ts","sourceRoot":"","sources":["../../src/database/database.controller.ts"],"names":[],"mappings":"AAUA,OAAO,EAAE,eAAe,EAAE,MAAQ,oBAAoB,CAAC;AAEvD,OAAO,EAAE,WAAW,EAAE,MAAY,UAAU,CAAC;AAE7C,qBACa,gBAAgB;IAGf,OAAO,CAAC,QAAQ,CAAC,eAAe;IAF5C,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAqC;gBAE/B,eAAe,EAAE,eAAe;IAE7D;;;;;;;;;;;;;;;OAeG;IAGG,KAAK,CAAS,IAAI,EAAE,WAAW;IAUrC;;;;;OAKG;IAEH,YAAY;;;;IAOZ;;;;OAIG;IAEH,MAAM;;;;;;CASP"}
@@ -0,0 +1,101 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ var __metadata = (this && this.__metadata) || function (k, v) {
9
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
+ };
11
+ var __param = (this && this.__param) || function (paramIndex, decorator) {
12
+ return function (target, key) { decorator(target, key, paramIndex); }
13
+ };
14
+ var AlleenController_1;
15
+ Object.defineProperty(exports, "__esModule", { value: true });
16
+ exports.AlleenController = void 0;
17
+ const common_1 = require("@nestjs/common");
18
+ const database_service_1 = require("./database.service");
19
+ const alleen_query_dto_1 = require("../dto/alleen-query.dto");
20
+ let AlleenController = AlleenController_1 = class AlleenController {
21
+ constructor(databaseService) {
22
+ this.databaseService = databaseService;
23
+ this.logger = new common_1.Logger(AlleenController_1.name);
24
+ }
25
+ /**
26
+ * POST /alleen/query
27
+ *
28
+ * Endpoint universel pour toutes les opérations CRUD.
29
+ *
30
+ * Body:
31
+ * {
32
+ * "database": "phoenix",
33
+ * "model": "User",
34
+ * "action": "findMany",
35
+ * "args": {
36
+ * "where": { "active": true },
37
+ * "include": { "orders": true }
38
+ * }
39
+ * }
40
+ */
41
+ async query(body) {
42
+ // Validation
43
+ const { valid, errors } = alleen_query_dto_1.AlleenQueryDto.validate(body);
44
+ if (!valid) {
45
+ throw new common_1.BadRequestException({ errors });
46
+ }
47
+ return this.databaseService.execute(body);
48
+ }
49
+ /**
50
+ * GET /alleen/databases
51
+ *
52
+ * Liste toutes les bases de données enregistrées.
53
+ * Utile pour le debug et la santé du système.
54
+ */
55
+ getDatabases() {
56
+ return {
57
+ success: true,
58
+ databases: this.databaseService.getRegisteredDatabases(),
59
+ };
60
+ }
61
+ /**
62
+ * GET /alleen/health
63
+ *
64
+ * Health check rapide.
65
+ */
66
+ health() {
67
+ const databases = this.databaseService.getRegisteredDatabases();
68
+ return {
69
+ status: 'ok',
70
+ databases: databases.length,
71
+ registered: databases,
72
+ timestamp: new Date().toISOString(),
73
+ };
74
+ }
75
+ };
76
+ exports.AlleenController = AlleenController;
77
+ __decorate([
78
+ (0, common_1.Post)('dbinstance'),
79
+ (0, common_1.HttpCode)(common_1.HttpStatus.OK),
80
+ __param(0, (0, common_1.Body)()),
81
+ __metadata("design:type", Function),
82
+ __metadata("design:paramtypes", [Object]),
83
+ __metadata("design:returntype", Promise)
84
+ ], AlleenController.prototype, "query", null);
85
+ __decorate([
86
+ (0, common_1.Get)('databases'),
87
+ __metadata("design:type", Function),
88
+ __metadata("design:paramtypes", []),
89
+ __metadata("design:returntype", void 0)
90
+ ], AlleenController.prototype, "getDatabases", null);
91
+ __decorate([
92
+ (0, common_1.Get)('health'),
93
+ __metadata("design:type", Function),
94
+ __metadata("design:paramtypes", []),
95
+ __metadata("design:returntype", void 0)
96
+ ], AlleenController.prototype, "health", null);
97
+ exports.AlleenController = AlleenController = AlleenController_1 = __decorate([
98
+ (0, common_1.Controller)('alleen'),
99
+ __metadata("design:paramtypes", [database_service_1.DatabaseService])
100
+ ], AlleenController);
101
+ //# sourceMappingURL=database.controller.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"database.controller.js","sourceRoot":"","sources":["../../src/database/database.controller.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;AAAA,2CASwB;AACxB,yDAAuD;AACvD,8DAA4D;AAIrD,IAAM,gBAAgB,wBAAtB,MAAM,gBAAgB;IAG3B,YAA6B,eAAgC;QAAhC,oBAAe,GAAf,eAAe,CAAiB;QAF5C,WAAM,GAAG,IAAI,eAAM,CAAC,kBAAgB,CAAC,IAAI,CAAC,CAAC;IAEI,CAAC;IAEjE;;;;;;;;;;;;;;;OAeG;IAGG,AAAN,KAAK,CAAC,KAAK,CAAS,IAAiB;QACnC,aAAa;QACb,MAAM,EAAE,KAAK,EAAE,MAAM,EAAE,GAAG,iCAAc,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QACxD,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,MAAM,IAAI,4BAAmB,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC;QAC5C,CAAC;QAED,OAAO,IAAI,CAAC,eAAe,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IAC5C,CAAC;IAED;;;;;OAKG;IAEH,YAAY;QACV,OAAO;YACL,OAAO,EAAI,IAAI;YACf,SAAS,EAAE,IAAI,CAAC,eAAe,CAAC,sBAAsB,EAAE;SACzD,CAAC;IACJ,CAAC;IAED;;;;OAIG;IAEH,MAAM;QACJ,MAAM,SAAS,GAAG,IAAI,CAAC,eAAe,CAAC,sBAAsB,EAAE,CAAC;QAChE,OAAO;YACL,MAAM,EAAK,IAAI;YACf,SAAS,EAAE,SAAS,CAAC,MAAM;YAC3B,UAAU,EAAE,SAAS;YACrB,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;SACpC,CAAC;IACJ,CAAC;CACF,CAAA;AA9DY,4CAAgB;AAuBrB;IAFL,IAAA,aAAI,EAAC,YAAY,CAAC;IAClB,IAAA,iBAAQ,EAAC,mBAAU,CAAC,EAAE,CAAC;IACX,WAAA,IAAA,aAAI,GAAE,CAAA;;;;6CAQlB;AASD;IADC,IAAA,YAAG,EAAC,WAAW,CAAC;;;;oDAMhB;AAQD;IADC,IAAA,YAAG,EAAC,QAAQ,CAAC;;;;8CASb;2BA7DU,gBAAgB;IAD5B,IAAA,mBAAU,EAAC,QAAQ,CAAC;qCAI2B,kCAAe;GAHlD,gBAAgB,CA8D5B"}
@@ -0,0 +1,28 @@
1
+ import { ModuleRef } from '@nestjs/core';
2
+ import { AlleenQuery, AlleenResult, PrismaRegistry } from '../types';
3
+ export declare class DatabaseService {
4
+ private readonly moduleRef;
5
+ private readonly registry;
6
+ private readonly logger;
7
+ constructor(moduleRef: ModuleRef, registry: PrismaRegistry);
8
+ execute<T = any>(query: AlleenQuery): Promise<AlleenResult<T>>;
9
+ /**
10
+ * Résout l'instance PrismaService depuis le registry.
11
+ * Remplace entièrement le switch manuel.
12
+ */
13
+ private resolveDatabase;
14
+ /**
15
+ * Résout le model Prisma sur l'instance DB.
16
+ * ex: dbInstance["user"] pour le model "User"
17
+ */
18
+ private resolveModel;
19
+ /**
20
+ * Vérifie que l'action demandée est une action Prisma valide.
21
+ */
22
+ private validateAction;
23
+ /** Liste toutes les bases de données enregistrées */
24
+ getRegisteredDatabases(): string[];
25
+ /** Vérifie si une DB est enregistrée */
26
+ hasDatabase(database: string): boolean;
27
+ }
28
+ //# sourceMappingURL=database.service.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"database.service.d.ts","sourceRoot":"","sources":["../../src/database/database.service.ts"],"names":[],"mappings":"AAMA,OAAO,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AACzC,OAAO,EAAE,WAAW,EAAE,YAAY,EAAgB,cAAc,EAAE,MAAM,UAAU,CAAC;AAEnF,qBACa,eAAe;IAIxB,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,QAAQ;IAJ3B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAoC;gBAGxC,SAAS,EAAE,SAAS,EACpB,QAAQ,EAAE,cAAc;IAIrC,OAAO,CAAC,CAAC,GAAG,GAAG,EAAE,KAAK,EAAE,WAAW,GAAG,OAAO,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC;IAqCpE;;;OAGG;IACH,OAAO,CAAC,eAAe;IAevB;;;OAGG;IACH,OAAO,CAAC,YAAY;IAepB;;OAEG;IACH,OAAO,CAAC,cAAc;IAoBtB,qDAAqD;IACrD,sBAAsB,IAAI,MAAM,EAAE;IAIlC,wCAAwC;IACxC,WAAW,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO;CAGvC"}
@@ -0,0 +1,113 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ var __metadata = (this && this.__metadata) || function (k, v) {
9
+ if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
10
+ };
11
+ var DatabaseService_1;
12
+ Object.defineProperty(exports, "__esModule", { value: true });
13
+ exports.DatabaseService = void 0;
14
+ const common_1 = require("@nestjs/common");
15
+ const core_1 = require("@nestjs/core");
16
+ let DatabaseService = DatabaseService_1 = class DatabaseService {
17
+ constructor(moduleRef, registry) {
18
+ this.moduleRef = moduleRef;
19
+ this.registry = registry;
20
+ this.logger = new common_1.Logger(DatabaseService_1.name);
21
+ }
22
+ // ─── Point d'entrée principal ────────────────────────────────────
23
+ async execute(query) {
24
+ const start = Date.now();
25
+ const { database, model, action, args = {} } = query;
26
+ // 1. Résoudre l'instance Prisma pour cette DB
27
+ const dbInstance = this.resolveDatabase(database);
28
+ // 2. Résoudre le model sur l'instance
29
+ const prismaModel = this.resolveModel(dbInstance, model, database);
30
+ // 3. Valider l'action
31
+ this.validateAction(action);
32
+ // 4. Exécuter
33
+ try {
34
+ this.logger.debug(`[${database}] ${model}.${action}(${JSON.stringify(args)})`);
35
+ const data = await prismaModel[action](args);
36
+ const duration = Date.now() - start;
37
+ return {
38
+ success: true,
39
+ data,
40
+ meta: { database, model, action, duration },
41
+ };
42
+ }
43
+ catch (err) {
44
+ this.logger.error(`[${database}] ${model}.${action} failed — ${err.message}`);
45
+ throw new common_1.BadRequestException({
46
+ success: false,
47
+ error: err.message,
48
+ meta: { database, model, action },
49
+ });
50
+ }
51
+ }
52
+ // ─── Helpers ─────────────────────────────────────────────────────
53
+ /**
54
+ * Résout l'instance PrismaService depuis le registry.
55
+ * Remplace entièrement le switch manuel.
56
+ */
57
+ resolveDatabase(database) {
58
+ const ServiceClass = this.registry[database];
59
+ if (!ServiceClass) {
60
+ const available = Object.keys(this.registry).join(', ');
61
+ throw new common_1.NotFoundException(`Database "${database}" is not registered. ` +
62
+ `Available: [${available}]. ` +
63
+ `Run: alleen db:add --name=${database} --url=<url>`);
64
+ }
65
+ return this.moduleRef.get(ServiceClass, { strict: false });
66
+ }
67
+ /**
68
+ * Résout le model Prisma sur l'instance DB.
69
+ * ex: dbInstance["user"] pour le model "User"
70
+ */
71
+ resolveModel(dbInstance, model, database) {
72
+ // Prisma expose les models en camelCase lowercase
73
+ const modelKey = model.charAt(0).toLowerCase() + model.slice(1);
74
+ const prismaModel = dbInstance[modelKey];
75
+ if (!prismaModel) {
76
+ throw new common_1.NotFoundException(`Model "${model}" not found in database "${database}". ` +
77
+ `Check your prisma/${database}/schema.prisma file.`);
78
+ }
79
+ return prismaModel;
80
+ }
81
+ /**
82
+ * Vérifie que l'action demandée est une action Prisma valide.
83
+ */
84
+ validateAction(action) {
85
+ const validActions = [
86
+ 'findUnique', 'findFirst', 'findMany',
87
+ 'create', 'createMany',
88
+ 'update', 'updateMany',
89
+ 'upsert',
90
+ 'delete', 'deleteMany',
91
+ 'count', 'aggregate', 'groupBy',
92
+ ];
93
+ if (!validActions.includes(action)) {
94
+ throw new common_1.BadRequestException(`Action "${action}" is not a valid Prisma action. ` +
95
+ `Valid actions: ${validActions.join(', ')}`);
96
+ }
97
+ }
98
+ // ─── Méthodes utilitaires publiques ───────────────────────────────
99
+ /** Liste toutes les bases de données enregistrées */
100
+ getRegisteredDatabases() {
101
+ return Object.keys(this.registry);
102
+ }
103
+ /** Vérifie si une DB est enregistrée */
104
+ hasDatabase(database) {
105
+ return database in this.registry;
106
+ }
107
+ };
108
+ exports.DatabaseService = DatabaseService;
109
+ exports.DatabaseService = DatabaseService = DatabaseService_1 = __decorate([
110
+ (0, common_1.Injectable)(),
111
+ __metadata("design:paramtypes", [core_1.ModuleRef, Object])
112
+ ], DatabaseService);
113
+ //# sourceMappingURL=database.service.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"database.service.js","sourceRoot":"","sources":["../../src/database/database.service.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,12 @@
1
+ import { PrismaAction } from '../types';
2
+ export declare class AlleenQueryDto {
3
+ database: string;
4
+ model: string;
5
+ action: PrismaAction;
6
+ args?: Record<string, any>;
7
+ static validate(body: any): {
8
+ valid: boolean;
9
+ errors: string[];
10
+ };
11
+ }
12
+ //# sourceMappingURL=alleen-query.dto.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"alleen-query.dto.d.ts","sourceRoot":"","sources":["../../src/dto/alleen-query.dto.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAKxC,qBAAa,cAAc;IACzB,QAAQ,EAAG,MAAM,CAAC;IAClB,KAAK,EAAM,MAAM,CAAC;IAClB,MAAM,EAAK,YAAY,CAAC;IACxB,IAAI,CAAC,EAAM,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAE/B,MAAM,CAAC,QAAQ,CAAC,IAAI,EAAE,GAAG,GAAG;QAAE,KAAK,EAAE,OAAO,CAAC;QAAC,MAAM,EAAE,MAAM,EAAE,CAAA;KAAE;CAqBjE"}
@@ -0,0 +1,25 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.AlleenQueryDto = void 0;
4
+ // ─── Validation manuelle (sans class-validator pour garder 0 dépendances) ──
5
+ // Si le projet utilise class-validator, vous pouvez ajouter les décorateurs.
6
+ class AlleenQueryDto {
7
+ static validate(body) {
8
+ const errors = [];
9
+ if (!body.database || typeof body.database !== 'string') {
10
+ errors.push('"database" is required and must be a string');
11
+ }
12
+ if (!body.model || typeof body.model !== 'string') {
13
+ errors.push('"model" is required and must be a string');
14
+ }
15
+ if (!body.action || typeof body.action !== 'string') {
16
+ errors.push('"action" is required and must be a string');
17
+ }
18
+ if (body.args !== undefined && typeof body.args !== 'object') {
19
+ errors.push('"args" must be an object if provided');
20
+ }
21
+ return { valid: errors.length === 0, errors };
22
+ }
23
+ }
24
+ exports.AlleenQueryDto = AlleenQueryDto;
25
+ //# sourceMappingURL=alleen-query.dto.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"alleen-query.dto.js","sourceRoot":"","sources":["../../src/dto/alleen-query.dto.ts"],"names":[],"mappings":";;;AAEA,8EAA8E;AAC9E,6EAA6E;AAE7E,MAAa,cAAc;IAMzB,MAAM,CAAC,QAAQ,CAAC,IAAS;QACvB,MAAM,MAAM,GAAa,EAAE,CAAC;QAE5B,IAAI,CAAC,IAAI,CAAC,QAAQ,IAAI,OAAO,IAAI,CAAC,QAAQ,KAAK,QAAQ,EAAE,CAAC;YACxD,MAAM,CAAC,IAAI,CAAC,6CAA6C,CAAC,CAAC;QAC7D,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,KAAK,IAAI,OAAO,IAAI,CAAC,KAAK,KAAK,QAAQ,EAAE,CAAC;YAClD,MAAM,CAAC,IAAI,CAAC,0CAA0C,CAAC,CAAC;QAC1D,CAAC;QAED,IAAI,CAAC,IAAI,CAAC,MAAM,IAAI,OAAO,IAAI,CAAC,MAAM,KAAK,QAAQ,EAAE,CAAC;YACpD,MAAM,CAAC,IAAI,CAAC,2CAA2C,CAAC,CAAC;QAC3D,CAAC;QAED,IAAI,IAAI,CAAC,IAAI,KAAK,SAAS,IAAI,OAAO,IAAI,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;YAC7D,MAAM,CAAC,IAAI,CAAC,sCAAsC,CAAC,CAAC;QACtD,CAAC;QAED,OAAO,EAAE,KAAK,EAAE,MAAM,CAAC,MAAM,KAAK,CAAC,EAAE,MAAM,EAAE,CAAC;IAChD,CAAC;CACF;AA3BD,wCA2BC"}
@@ -0,0 +1 @@
1
+ //# sourceMappingURL=app.module.example.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"app.module.example.d.ts","sourceRoot":"","sources":["../../src/examples/app.module.example.ts"],"names":[],"mappings":""}
@@ -0,0 +1,61 @@
1
+ "use strict";
2
+ // /**
3
+ // * Exemple — app.module.ts du projet alleen-api (starter)
4
+ // *
5
+ // * Après avoir lancé :
6
+ // * alleen db:add --name=phoenix --url=postgresql://...
7
+ // * alleen db:add --name=bulk --url=postgresql://...
8
+ // *
9
+ // * Ce fichier N'EST JAMAIS modifié manuellement pour les DBs.
10
+ // * Seul prisma.registry.ts change automatiquement.
11
+ // */
12
+ // import { Module } from '@nestjs/common';
13
+ // import { ConfigModule } from '@nestjs/config';
14
+ // import { AlleenModule } from '@alleen/core';
15
+ // import { PRISMA_REGISTRY, PRISMA_PROVIDERS } from './prisma/prisma.registry';
16
+ // @Module({
17
+ // imports: [
18
+ // // Config globale (.env)
19
+ // ConfigModule.forRoot({ isGlobal: true }),
20
+ // AlleenModule.forRoot({
21
+ // registry: PRISMA_REGISTRY, // { phoenix: PhoenixPrismaService, ... }
22
+ // providers: PRISMA_PROVIDERS, // [PhoenixPrismaService, BulkPrismaService, ...]
23
+ // exposeApi: true, // Active POST /alleen/query automatiquement
24
+ // }),
25
+ // ],
26
+ // })
27
+ // export class AppModule {}
28
+ // /**
29
+ // * Endpoints disponibles automatiquement après forRoot() :
30
+ // *
31
+ // * POST /alleen/query ← toutes tes opérations CRUD
32
+ // * GET /alleen/databases ← liste les DBs enregistrées
33
+ // * GET /alleen/health ← health check
34
+ // *
35
+ // * ─── Exemple de requête ───────────────────────────────────────────
36
+ // *
37
+ // * POST /alleen/query
38
+ // * {
39
+ // * "database": "phoenix",
40
+ // * "model": "User",
41
+ // * "action": "findMany",
42
+ // * "args": {
43
+ // * "where": { "active": true },
44
+ // * "include": { "profile": true },
45
+ // * "take": 10
46
+ // * }
47
+ // * }
48
+ // *
49
+ // * ─── Réponse ─────────────────────────────────────────────────────
50
+ // * {
51
+ // * "success": true,
52
+ // * "data": [...],
53
+ // * "meta": {
54
+ // * "database": "phoenix",
55
+ // * "model": "User",
56
+ // * "action": "findMany",
57
+ // * "duration": 42
58
+ // * }
59
+ // * }
60
+ // */
61
+ //# sourceMappingURL=app.module.example.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"app.module.example.js","sourceRoot":"","sources":["../../src/examples/app.module.example.ts"],"names":[],"mappings":";AAAA,MAAM;AACN,4DAA4D;AAC5D,KAAK;AACL,yBAAyB;AACzB,2DAA2D;AAC3D,2DAA2D;AAC3D,KAAK;AACL,gEAAgE;AAChE,qDAAqD;AACrD,MAAM;AAEN,iDAAiD;AACjD,iDAAiD;AAEjD,+CAA+C;AAE/C,gFAAgF;AAEhF,YAAY;AACZ,eAAe;AACf,+BAA+B;AAC/B,gDAAgD;AAEhD,6BAA6B;AAC7B,gFAAgF;AAChF,wFAAwF;AACxF,mFAAmF;AACnF,UAAU;AACV,OAAO;AACP,KAAK;AACL,4BAA4B;AAE5B,MAAM;AACN,6DAA6D;AAC7D,KAAK;AACL,0DAA0D;AAC1D,0DAA0D;AAC1D,4CAA4C;AAC5C,KAAK;AACL,wEAAwE;AACxE,KAAK;AACL,wBAAwB;AACxB,OAAO;AACP,8BAA8B;AAC9B,2BAA2B;AAC3B,+BAA+B;AAC/B,iBAAiB;AACjB,wCAAwC;AACxC,yCAAyC;AACzC,uBAAuB;AACvB,SAAS;AACT,OAAO;AACP,KAAK;AACL,uEAAuE;AACvE,OAAO;AACP,wBAAwB;AACxB,sBAAsB;AACtB,iBAAiB;AACjB,gCAAgC;AAChC,6BAA6B;AAC7B,iCAAiC;AACjC,wBAAwB;AACxB,SAAS;AACT,OAAO;AACP,MAAM"}
@@ -0,0 +1,7 @@
1
+ export { AlleenLoggerInterceptor } from './interceptors/logger.interceptor';
2
+ export { AlleenModule } from './alleen.module';
3
+ export { DatabaseService } from './database/database.service';
4
+ export { AlleenController } from './database/database.controller';
5
+ export type { AlleenQuery, AlleenResult, AlleenConfig, DatabaseConfig, PrismaAction, PrismaRegistry, } from './types';
6
+ export { AlleenQueryDto } from './dto/alleen-query.dto';
7
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,uBAAuB,EAAE,MAAM,mCAAmC,CAAC;AAE5E,OAAO,EAAE,YAAY,EAAE,MAAkB,iBAAiB,CAAC;AAE3D,OAAO,EAAE,eAAe,EAAE,MAAe,6BAA6B,CAAC;AAEvE,OAAO,EAAE,gBAAgB,EAAE,MAAc,gCAAgC,CAAC;AAE1E,YAAY,EACV,WAAW,EACX,YAAY,EACZ,YAAY,EACZ,cAAc,EACd,YAAY,EACZ,cAAc,GACf,MAAM,SAAS,CAAC;AAEjB,OAAO,EAAE,cAAc,EAAE,MAAgB,wBAAwB,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,14 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.AlleenQueryDto = exports.AlleenController = exports.DatabaseService = exports.AlleenModule = exports.AlleenLoggerInterceptor = void 0;
4
+ var logger_interceptor_1 = require("./interceptors/logger.interceptor");
5
+ Object.defineProperty(exports, "AlleenLoggerInterceptor", { enumerable: true, get: function () { return logger_interceptor_1.AlleenLoggerInterceptor; } });
6
+ var alleen_module_1 = require("./alleen.module");
7
+ Object.defineProperty(exports, "AlleenModule", { enumerable: true, get: function () { return alleen_module_1.AlleenModule; } });
8
+ var database_service_1 = require("./database/database.service");
9
+ Object.defineProperty(exports, "DatabaseService", { enumerable: true, get: function () { return database_service_1.DatabaseService; } });
10
+ var database_controller_1 = require("./database/database.controller");
11
+ Object.defineProperty(exports, "AlleenController", { enumerable: true, get: function () { return database_controller_1.AlleenController; } });
12
+ var alleen_query_dto_1 = require("./dto/alleen-query.dto");
13
+ Object.defineProperty(exports, "AlleenQueryDto", { enumerable: true, get: function () { return alleen_query_dto_1.AlleenQueryDto; } });
14
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;AAAA,wEAA4E;AAAnE,6HAAA,uBAAuB,OAAA;AAEhC,iDAA2D;AAAlD,6GAAA,YAAY,OAAA;AAErB,gEAAuE;AAA9D,mHAAA,eAAe,OAAA;AAExB,sEAA0E;AAAjE,uHAAA,gBAAgB,OAAA;AAWzB,2DAAkE;AAAzD,kHAAA,cAAc,OAAA"}
@@ -0,0 +1,16 @@
1
+ import { NestInterceptor, ExecutionContext, CallHandler } from '@nestjs/common';
2
+ import { Observable } from 'rxjs';
3
+ /**
4
+ * AlleenLoggerInterceptor
5
+ *
6
+ * Log chaque requête avec sa durée et son résultat.
7
+ * Optionnel — à activer dans app.module.ts si souhaité.
8
+ *
9
+ * Usage:
10
+ * app.useGlobalInterceptors(new AlleenLoggerInterceptor());
11
+ */
12
+ export declare class AlleenLoggerInterceptor implements NestInterceptor {
13
+ private readonly logger;
14
+ intercept(context: ExecutionContext, next: CallHandler): Observable<any>;
15
+ }
16
+ //# sourceMappingURL=logger.interceptor.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.interceptor.d.ts","sourceRoot":"","sources":["../../src/interceptors/logger.interceptor.ts"],"names":[],"mappings":"AAAA,OAAO,EAEL,eAAe,EACf,gBAAgB,EAChB,WAAW,EAEZ,MAAM,gBAAgB,CAAC;AACxB,OAAO,EAAE,UAAU,EAAO,MAAM,MAAM,CAAC;AAEvC;;;;;;;;GAQG;AACH,qBACa,uBAAwB,YAAW,eAAe;IAC7D,OAAO,CAAC,QAAQ,CAAC,MAAM,CAA6B;IAEpD,SAAS,CAAC,OAAO,EAAE,gBAAgB,EAAE,IAAI,EAAE,WAAW,GAAG,UAAU,CAAC,GAAG,CAAC;CAkBzE"}
@@ -0,0 +1,43 @@
1
+ "use strict";
2
+ var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
3
+ var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
4
+ if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
5
+ else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
6
+ return c > 3 && r && Object.defineProperty(target, key, r), r;
7
+ };
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.AlleenLoggerInterceptor = void 0;
10
+ const common_1 = require("@nestjs/common");
11
+ const rxjs_1 = require("rxjs");
12
+ /**
13
+ * AlleenLoggerInterceptor
14
+ *
15
+ * Log chaque requête avec sa durée et son résultat.
16
+ * Optionnel — à activer dans app.module.ts si souhaité.
17
+ *
18
+ * Usage:
19
+ * app.useGlobalInterceptors(new AlleenLoggerInterceptor());
20
+ */
21
+ let AlleenLoggerInterceptor = class AlleenLoggerInterceptor {
22
+ constructor() {
23
+ this.logger = new common_1.Logger('AlleenQuery');
24
+ }
25
+ intercept(context, next) {
26
+ const request = context.switchToHttp().getRequest();
27
+ const { body } = request;
28
+ const start = Date.now();
29
+ // Seulement logger les requêtes alleen
30
+ if (!body?.database)
31
+ return next.handle();
32
+ return next.handle().pipe((0, rxjs_1.tap)((result) => {
33
+ const duration = Date.now() - start;
34
+ const status = result?.success ? '✅' : '❌';
35
+ this.logger.log(`${status} [${body.database}] ${body.model}.${body.action} — ${duration}ms`);
36
+ }));
37
+ }
38
+ };
39
+ exports.AlleenLoggerInterceptor = AlleenLoggerInterceptor;
40
+ exports.AlleenLoggerInterceptor = AlleenLoggerInterceptor = __decorate([
41
+ (0, common_1.Injectable)()
42
+ ], AlleenLoggerInterceptor);
43
+ //# sourceMappingURL=logger.interceptor.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.interceptor.js","sourceRoot":"","sources":["../../src/interceptors/logger.interceptor.ts"],"names":[],"mappings":";;;;;;;;;AAAA,2CAMwB;AACxB,+BAAuC;AAEvC;;;;;;;;GAQG;AAEI,IAAM,uBAAuB,GAA7B,MAAM,uBAAuB;IAA7B;QACY,WAAM,GAAG,IAAI,eAAM,CAAC,aAAa,CAAC,CAAC;IAoBtD,CAAC;IAlBC,SAAS,CAAC,OAAyB,EAAE,IAAiB;QACpD,MAAM,OAAO,GAAG,OAAO,CAAC,YAAY,EAAE,CAAC,UAAU,EAAE,CAAC;QACpD,MAAM,EAAE,IAAI,EAAE,GAAI,OAAO,CAAC;QAC1B,MAAM,KAAK,GAAO,IAAI,CAAC,GAAG,EAAE,CAAC;QAE7B,uCAAuC;QACvC,IAAI,CAAC,IAAI,EAAE,QAAQ;YAAE,OAAO,IAAI,CAAC,MAAM,EAAE,CAAC;QAE1C,OAAO,IAAI,CAAC,MAAM,EAAE,CAAC,IAAI,CACvB,IAAA,UAAG,EAAC,CAAC,MAAM,EAAE,EAAE;YACb,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC;YACpC,MAAM,MAAM,GAAK,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,CAAC;YAC7C,IAAI,CAAC,MAAM,CAAC,GAAG,CACb,GAAG,MAAM,KAAK,IAAI,CAAC,QAAQ,KAAK,IAAI,CAAC,KAAK,IAAI,IAAI,CAAC,MAAM,MAAM,QAAQ,IAAI,CAC5E,CAAC;QACJ,CAAC,CAAC,CACH,CAAC;IACJ,CAAC;CACF,CAAA;AArBY,0DAAuB;kCAAvB,uBAAuB;IADnC,IAAA,mBAAU,GAAE;GACA,uBAAuB,CAqBnC"}
@@ -0,0 +1,42 @@
1
+ /** Actions Prisma supportées */
2
+ export type PrismaAction = 'findUnique' | 'findFirst' | 'findMany' | 'create' | 'createMany' | 'update' | 'updateMany' | 'upsert' | 'delete' | 'deleteMany' | 'count' | 'aggregate' | 'groupBy';
3
+ /** Structure d'une requête envoyée à l'endpoint alleen */
4
+ export interface AlleenQuery {
5
+ /** Nom de la base de données cible (ex: "phoenix") */
6
+ database: string;
7
+ /** Nom du model Prisma (ex: "User") */
8
+ model: string;
9
+ /** Action Prisma à exécuter */
10
+ action: PrismaAction;
11
+ /** Arguments passés à l'action Prisma (where, data, include, select...) */
12
+ args?: Record<string, any>;
13
+ }
14
+ /** Résultat d'une requête alleen */
15
+ export interface AlleenResult<T = any> {
16
+ success: boolean;
17
+ data?: T;
18
+ error?: string;
19
+ meta?: {
20
+ database: string;
21
+ model: string;
22
+ action: string;
23
+ duration?: number;
24
+ };
25
+ }
26
+ /** Config d'une base de données dans alleen.config.ts */
27
+ export interface DatabaseConfig {
28
+ name: string;
29
+ url: string;
30
+ provider?: 'postgresql' | 'mysql' | 'sqlite' | 'sqlserver' | 'mongodb';
31
+ }
32
+ /** Config globale du framework alleen */
33
+ export interface AlleenConfig {
34
+ databases: DatabaseConfig[];
35
+ api?: {
36
+ prefix?: string;
37
+ version?: string;
38
+ };
39
+ }
40
+ /** Registry interne — map de nom de DB vers sa classe PrismaService */
41
+ export type PrismaRegistry = Record<string, new (...args: any[]) => any>;
42
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAEA,gCAAgC;AAChC,MAAM,MAAM,YAAY,GACpB,YAAY,GACZ,WAAW,GACX,UAAU,GACV,QAAQ,GACR,YAAY,GACZ,QAAQ,GACR,YAAY,GACZ,QAAQ,GACR,QAAQ,GACR,YAAY,GACZ,OAAO,GACP,WAAW,GACX,SAAS,CAAC;AAEd,0DAA0D;AAC1D,MAAM,WAAW,WAAW;IAC1B,sDAAsD;IACtD,QAAQ,EAAE,MAAM,CAAC;IACjB,uCAAuC;IACvC,KAAK,EAAE,MAAM,CAAC;IACd,+BAA+B;IAC/B,MAAM,EAAE,YAAY,CAAC;IACrB,2EAA2E;IAC3E,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;CAC5B;AAED,oCAAoC;AACpC,MAAM,WAAW,YAAY,CAAC,CAAC,GAAG,GAAG;IACnC,OAAO,EAAE,OAAO,CAAC;IACjB,IAAI,CAAC,EAAE,CAAC,CAAC;IACT,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,IAAI,CAAC,EAAE;QACL,QAAQ,EAAE,MAAM,CAAC;QACjB,KAAK,EAAE,MAAM,CAAC;QACd,MAAM,EAAE,MAAM,CAAC;QACf,QAAQ,CAAC,EAAE,MAAM,CAAC;KACnB,CAAC;CACH;AAED,yDAAyD;AACzD,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,MAAM,CAAC;IACb,GAAG,EAAE,MAAM,CAAC;IACZ,QAAQ,CAAC,EAAE,YAAY,GAAG,OAAO,GAAG,QAAQ,GAAG,WAAW,GAAG,SAAS,CAAC;CACxE;AAED,yCAAyC;AACzC,MAAM,WAAW,YAAY;IAC3B,SAAS,EAAE,cAAc,EAAE,CAAC;IAC5B,GAAG,CAAC,EAAE;QACJ,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,OAAO,CAAC,EAAE,MAAM,CAAC;KAClB,CAAC;CACH;AAED,uEAAuE;AACvE,MAAM,MAAM,cAAc,GAAG,MAAM,CAAC,MAAM,EAAE,KAAK,GAAG,IAAI,EAAE,GAAG,EAAE,KAAK,GAAG,CAAC,CAAC"}
package/dist/types.js ADDED
@@ -0,0 +1,4 @@
1
+ "use strict";
2
+ // ─── Types de base ────────────────────────────────────────────────
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":";AAAA,qEAAqE"}
package/package.json ADDED
@@ -0,0 +1,39 @@
1
+ {
2
+ "name": "@alleen/core",
3
+ "version": "0.1.0",
4
+ "description": "Core NestJS module for alleen-api — dynamic multi-database Prisma registry",
5
+ "publishConfig": {
6
+ "access": "public"
7
+ },
8
+ "files": [
9
+ "dist",
10
+ "README.md"
11
+ ],
12
+ "main": "./dist/index.js",
13
+ "types": "./dist/index.d.ts",
14
+ "scripts": {
15
+ "build": "tsc",
16
+ "dev": "ts-node src/index.ts"
17
+ },
18
+ "peerDependencies": {
19
+ "@nestjs/common": "^10.0.0",
20
+ "@nestjs/core": "^10.0.0",
21
+ "reflect-metadata": "^0.1.13"
22
+ },
23
+ "devDependencies": {
24
+ "@nestjs/common": "^10.0.0",
25
+ "@nestjs/core": "^10.0.0",
26
+ "@types/node": "^20.0.0",
27
+ "reflect-metadata": "^0.1.13",
28
+ "ts-node": "^10.9.2",
29
+ "typescript": "^5.4.0"
30
+ },
31
+ "engines": {
32
+ "node": ">=18.0.0"
33
+ },
34
+ "dependencies": {
35
+ "rxjs": "^7.8.2"
36
+ },
37
+ "author": "OLIVIER ADOU",
38
+ "license": "ISC"
39
+ }