@deessejs/collections 0.0.22 → 0.0.24

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.
@@ -1,32 +1,2 @@
1
1
  import { Collection } from "./types";
2
- export declare const collection: <const Slug extends string, const Fields extends Record<string, any>>(config: {
3
- slug: Slug;
4
- name?: string;
5
- admin?: {
6
- title?: string;
7
- group?: string;
8
- };
9
- fields: Fields;
10
- hooks?: Collection["hooks"];
11
- permissions?: {
12
- create?: (ctx: any) => Promise<boolean>;
13
- read?: (ctx: any) => Promise<boolean>;
14
- update?: (ctx: any) => Promise<boolean>;
15
- delete?: (ctx: any) => Promise<boolean>;
16
- };
17
- }) => {
18
- slug: Slug;
19
- name?: string;
20
- admin?: {
21
- title?: string;
22
- group?: string;
23
- };
24
- fields: Fields;
25
- hooks?: Collection["hooks"];
26
- permissions?: {
27
- create?: (ctx: any) => Promise<boolean>;
28
- read?: (ctx: any) => Promise<boolean>;
29
- update?: (ctx: any) => Promise<boolean>;
30
- delete?: (ctx: any) => Promise<boolean>;
31
- };
32
- };
2
+ export declare const collection: <const Slug extends string, const Fields extends Record<string, any>>(config: Collection<Slug, Fields>) => Collection<Slug, Fields>;
@@ -1,16 +1,8 @@
1
- import { Collection } from "../collections/types";
2
- import { Field, FieldTypeFinal } from "../fields/types";
3
- import { Provider } from "../providers/types";
4
- type InferSchema<F extends Record<string, Field>> = {
5
- [K in keyof F]: F[K] extends Field<infer FT> ? FT extends FieldTypeFinal<any, infer TVal> ? TVal : never : never;
6
- };
7
- export declare const defineConfig: <const C extends {
8
- provider: Provider;
9
- collections: readonly Collection[];
10
- }>(config: C) => { [Col in C["collections"][number] as Col["slug"]]: {
1
+ import { InferSchema } from "../fields/types";
2
+ import { Config } from "./types";
3
+ export declare const defineConfig: <const C extends Config>(config: C) => { [Col in C["collections"][number] as Col["slug"]]: {
11
4
  create: (data: InferSchema<Col["fields"]>) => Promise<any>;
12
5
  read: (id: string) => Promise<any>;
13
6
  update: (id: string, data: Partial<InferSchema<Col["fields"]>>) => Promise<any>;
14
7
  delete: (id: string) => Promise<void>;
15
8
  }; };
16
- export {};
@@ -1,15 +1,27 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.defineConfig = void 0;
4
+ const orchestrator_1 = require("./orchestrator");
4
5
  const defineConfig = (config) => {
5
- config.provider.init();
6
+ // 1. Initialisation du Provider (Création tables, connexion DB...)
7
+ // On passe les collections pour qu'il connaisse le schéma
8
+ config.provider.init(config.collections);
6
9
  const db = {};
10
+ // 2. Construction dynamique de l'objet DB
7
11
  for (const col of config.collections) {
8
12
  db[col.slug] = {
9
- create: async (data) => data,
10
- read: async (id) => ({ id }),
11
- update: async (id, data) => ({ id, ...data }),
12
- delete: async (id) => { },
13
+ create: async (data) => {
14
+ return (0, orchestrator_1.runOperation)("create", col, config.provider, { data });
15
+ },
16
+ read: async (id) => {
17
+ return (0, orchestrator_1.runOperation)("read", col, config.provider, { id });
18
+ },
19
+ update: async (id, data) => {
20
+ return (0, orchestrator_1.runOperation)("update", col, config.provider, { id, data });
21
+ },
22
+ delete: async (id) => {
23
+ return (0, orchestrator_1.runOperation)("delete", col, config.provider, { id });
24
+ },
13
25
  };
14
26
  }
15
27
  return db;
@@ -0,0 +1,8 @@
1
+ import { Collection } from "../collections/types";
2
+ import { Provider } from "../providers/types";
3
+ type Action = 'create' | 'read' | 'update' | 'delete';
4
+ export declare const runOperation: (action: Action, collection: Collection, provider: Provider, payload: {
5
+ id?: string;
6
+ data?: any;
7
+ }) => Promise<any>;
8
+ export {};
@@ -0,0 +1,70 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.runOperation = void 0;
4
+ const runOperation = async (action, collection, provider, payload) => {
5
+ const { hooks } = collection;
6
+ let currentData = payload.data;
7
+ const id = payload.id;
8
+ try {
9
+ // 1. Hook Global: beforeOperation
10
+ if (hooks?.beforeOperation) {
11
+ await hooks.beforeOperation({ action, collection: collection.slug, data: currentData, id });
12
+ }
13
+ // 2. Hook Spécifique: before[Action]
14
+ // Note: TypeScript peut être strict ici, on simplifie pour la demo
15
+ if (action === 'create' && hooks?.beforeCreate)
16
+ currentData = await hooks.beforeCreate(currentData);
17
+ if (action === 'update' && hooks?.beforeUpdate)
18
+ currentData = await hooks.beforeUpdate(currentData);
19
+ if (action === 'delete' && hooks?.beforeDelete)
20
+ await hooks.beforeDelete({ id });
21
+ // 3. APPEL AU PROVIDER (Le vrai travail DB)
22
+ let result;
23
+ switch (action) {
24
+ case 'create':
25
+ result = await provider.create(collection.slug, currentData);
26
+ break;
27
+ case 'read':
28
+ if (!id)
29
+ throw new Error("ID required for read");
30
+ result = await provider.read(collection.slug, id);
31
+ break;
32
+ case 'update':
33
+ if (!id)
34
+ throw new Error("ID required for update");
35
+ result = await provider.update(collection.slug, id, currentData);
36
+ break;
37
+ case 'delete':
38
+ if (!id)
39
+ throw new Error("ID required for delete");
40
+ await provider.delete(collection.slug, id);
41
+ result = { success: true, id };
42
+ break;
43
+ }
44
+ // 4. Hook Spécifique: after[Action]
45
+ if (action === 'create' && hooks?.afterCreate)
46
+ result = await hooks.afterCreate(result);
47
+ if (action === 'update' && hooks?.afterUpdate)
48
+ result = await hooks.afterUpdate(result);
49
+ if (action === 'delete' && hooks?.afterDelete)
50
+ result = await hooks.afterDelete(result);
51
+ // 5. Hook Global: afterOperation
52
+ if (hooks?.afterOperation) {
53
+ await hooks.afterOperation({ action, result });
54
+ }
55
+ // 6. Hook Global: afterSuccess (spécifique à ta liste)
56
+ if (hooks?.afterSuccess) {
57
+ await hooks.afterSuccess(result);
58
+ }
59
+ return result;
60
+ }
61
+ catch (error) {
62
+ // Gestion des erreurs via les hooks
63
+ if (hooks?.afterError) {
64
+ // Le hook peut transformer l'erreur ou la logger
65
+ await hooks.afterError(error);
66
+ }
67
+ throw error; // On relance l'erreur pour que l'appelant sache que ça a échoué
68
+ }
69
+ };
70
+ exports.runOperation = runOperation;
@@ -1,7 +1,15 @@
1
1
  import { Collection } from "../collections/types";
2
2
  import { CollectionsCrud } from "../database/types";
3
+ import { Field, FieldTypeFinal } from "../fields";
4
+ import { Plugin } from "../plugins/types";
5
+ import { Provider } from "../providers/types";
3
6
  import { UnionToIntersection } from "../utils/union-intersection";
4
7
  export type Config = {
5
- collections: Collection[];
8
+ provider: Provider;
9
+ readonly collections: Collection[];
10
+ plugins?: Plugin[];
6
11
  };
7
12
  export type DbFromConfig<C extends Config> = UnionToIntersection<CollectionsCrud<C["collections"][number]>>;
13
+ export type InferSchema<F extends Record<string, Field>> = {
14
+ [K in keyof F]: F[K] extends Field<infer FT> ? FT extends FieldTypeFinal<any, infer TVal> ? TVal : never : never;
15
+ };
package/dist/index.d.ts CHANGED
@@ -1,4 +1,5 @@
1
- export * from './config';
2
- export * from './collections';
3
- export * from './fields';
4
- export * from './providers';
1
+ export * from "./config";
2
+ export * from "./collections";
3
+ export * from "./fields";
4
+ export * from "./providers";
5
+ export * from "./plugins";
package/dist/index.js CHANGED
@@ -18,3 +18,4 @@ __exportStar(require("./config"), exports);
18
18
  __exportStar(require("./collections"), exports);
19
19
  __exportStar(require("./fields"), exports);
20
20
  __exportStar(require("./providers"), exports);
21
+ __exportStar(require("./plugins"), exports);
@@ -0,0 +1,2 @@
1
+ import { Plugin } from "./types";
2
+ export declare const plugin: () => Plugin;
@@ -0,0 +1,7 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.plugin = void 0;
4
+ const plugin = () => {
5
+ return {};
6
+ };
7
+ exports.plugin = plugin;
@@ -0,0 +1 @@
1
+ export type Plugin = {};
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -2,9 +2,55 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.inAppProvider = void 0;
4
4
  const inAppProvider = () => {
5
+ // Stockage en mémoire : { "posts": { "id_1": { ...data }, "id_2": { ...data } } }
6
+ const storage = {};
5
7
  return {
6
- init: () => {
8
+ // L'init reçoit maintenant la liste des collections pour préparer le "schéma"
9
+ init: (collections) => {
7
10
  console.log("Initializing in-app provider");
11
+ for (const col of collections) {
12
+ // On initialise un "bucket" vide pour chaque collection si pas déjà fait
13
+ if (!storage[col.slug]) {
14
+ storage[col.slug] = {};
15
+ }
16
+ }
17
+ },
18
+ create: async (collectionSlug, data) => {
19
+ // Simulation d'un ID (dans une vraie DB, c'est géré par le moteur ou UUID)
20
+ const id = Math.random().toString(36).substring(2, 15);
21
+ const record = { ...data, id };
22
+ // Sécurité au cas où on écrit dans une collection non initialisée
23
+ if (!storage[collectionSlug])
24
+ storage[collectionSlug] = {};
25
+ storage[collectionSlug][id] = record;
26
+ return record;
27
+ },
28
+ read: async (collectionSlug, id) => {
29
+ const record = storage[collectionSlug]?.[id];
30
+ if (!record) {
31
+ throw new Error(`Record with ID "${id}" not found in "${collectionSlug}".`);
32
+ }
33
+ return record;
34
+ },
35
+ update: async (collectionSlug, id, data) => {
36
+ const existing = storage[collectionSlug]?.[id];
37
+ if (!existing) {
38
+ throw new Error(`Cannot update: Record with ID "${id}" not found in "${collectionSlug}".`);
39
+ }
40
+ // Fusion des données (Partial update)
41
+ const updated = { ...existing, ...data };
42
+ storage[collectionSlug][id] = updated;
43
+ return updated;
44
+ },
45
+ delete: async (collectionSlug, id) => {
46
+ if (storage[collectionSlug] && storage[collectionSlug][id]) {
47
+ delete storage[collectionSlug][id];
48
+ }
49
+ else {
50
+ // Optionnel : Throw une erreur si l'item n'existe pas,
51
+ // ou juste ignorer comme le ferait une requête SQL "DELETE WHERE ID=..."
52
+ console.warn(`Attempted to delete non-existent record "${id}" in "${collectionSlug}"`);
53
+ }
8
54
  }
9
55
  };
10
56
  };
@@ -1,3 +1,8 @@
1
+ import { Collection } from "../collections/types";
1
2
  export type Provider = {
2
- init: () => void;
3
+ init: (collections: readonly Collection[]) => Promise<void> | void;
4
+ create: (collectionSlug: string, data: any) => Promise<any>;
5
+ read: (collectionSlug: string, id: string) => Promise<any>;
6
+ update: (collectionSlug: string, id: string, data: any) => Promise<any>;
7
+ delete: (collectionSlug: string, id: string) => Promise<void>;
3
8
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@deessejs/collections",
3
- "version": "0.0.22",
3
+ "version": "0.0.24",
4
4
  "description": "",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",