@asterflow/plugin 1.0.1 → 1.0.3

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,88 +1,121 @@
1
1
  "use strict";
2
2
  var r = Object.defineProperty;
3
- var f = Object.getOwnPropertyDescriptor;
4
- var u = Object.getOwnPropertyNames;
5
- var d = Object.prototype.hasOwnProperty;
6
- var g = (t, e) => {
7
- for (var o in e)
8
- r(t, o, { get: e[o], enumerable: !0 });
9
- }, C = (t, e, o, n) => {
3
+ var h = Object.getOwnPropertyDescriptor;
4
+ var d = Object.getOwnPropertyNames;
5
+ var c = Object.prototype.hasOwnProperty;
6
+ var f = (t, e) => {
7
+ for (var n in e)
8
+ r(t, n, { get: e[n], enumerable: !0 });
9
+ }, u = (t, e, n, s) => {
10
10
  if (e && typeof e == "object" || typeof e == "function")
11
- for (let s of u(e))
12
- !d.call(t, s) && s !== o && r(t, s, { get: () => e[s], enumerable: !(n = f(e, s)) || n.enumerable });
11
+ for (let o of d(e))
12
+ !c.call(t, o) && o !== n && r(t, o, { get: () => e[o], enumerable: !(s = h(e, o)) || s.enumerable });
13
13
  return t;
14
14
  };
15
- var x = (t) => C(r({}, "__esModule", { value: !0 }), t);
15
+ var g = (t) => u(r({}, "__esModule", { value: !0 }), t);
16
16
  // packages/plugin/src/index.ts
17
- var y = {};
18
- g(y, {
17
+ var C = {};
18
+ f(C, {
19
19
  Plugin: () => a
20
20
  });
21
- module.exports = x(y);
21
+ module.exports = g(C);
22
22
  // packages/plugin/src/controllers/Plugin.ts
23
23
  var a = class t {
24
24
  name;
25
25
  resolvers;
26
26
  defaultConfig;
27
27
  hooks;
28
- constructor(e, o, n, s) {
29
- this.name = e, this.resolvers = o, this.hooks = n, this.defaultConfig = s;
28
+ instance;
29
+ _extensionFn;
30
+ constructor(e, n, s, o, i) {
31
+ this.name = e, this.resolvers = n, this.hooks = s, this.defaultConfig = o, this._extensionFn = i;
30
32
  }
31
- withConfig(e) {
33
+ config(e) {
32
34
  return new t(
33
35
  this.name,
34
36
  this.resolvers,
35
37
  this.hooks,
36
- e
38
+ e,
39
+ this._extensionFn
37
40
  );
38
41
  }
39
- decorate(e, o) {
40
- let n = (s, i) => ({
42
+ defineInstance(e) {
43
+ return this.instance = e, this;
44
+ }
45
+ decorate(e, n) {
46
+ let s = async (o, i) => ({
41
47
  ...i,
42
- [e]: o
48
+ [e]: n
43
49
  });
44
50
  return new t(
45
51
  this.name,
46
- [...this.resolvers, n],
52
+ [...this.resolvers, s],
47
53
  this.hooks,
48
- this.defaultConfig
54
+ this.defaultConfig,
55
+ this._extensionFn
49
56
  );
50
57
  }
51
- derive(e, o) {
52
- let n = (s, i) => {
53
- let l = { ...i, ...s }, h = o(l);
58
+ derive(e, n) {
59
+ let s = async (o, i) => {
60
+ let l = { ...i, ...o }, x = await n(l);
54
61
  return {
55
62
  ...i,
56
- [e]: h
63
+ [e]: x
57
64
  };
58
65
  };
59
66
  return new t(
60
67
  this.name,
61
- [...this.resolvers, n],
68
+ [...this.resolvers, s],
62
69
  this.hooks,
63
- this.defaultConfig
70
+ this.defaultConfig,
71
+ this._extensionFn
64
72
  );
65
73
  }
66
- on(e, o) {
67
- return this.hooks[e] || (this.hooks[e] = []), this.hooks[e].push(o), new t(
74
+ on(e, n) {
75
+ let s = this.hooks[e] || [], o = {
76
+ ...this.hooks,
77
+ [e]: [...s, n]
78
+ };
79
+ return new t(
80
+ this.name,
81
+ this.resolvers,
82
+ o,
83
+ this.defaultConfig,
84
+ this._extensionFn
85
+ );
86
+ }
87
+ extends(e) {
88
+ return new t(
68
89
  this.name,
69
90
  this.resolvers,
70
91
  this.hooks,
71
- this.defaultConfig
92
+ this.defaultConfig,
93
+ (n, s) => ({ ...this._extensionFn ? this._extensionFn(n, s) : {}, ...e(n, s) })
72
94
  );
73
95
  }
74
96
  _build(e) {
75
- let o = { ...this.defaultConfig, ...e }, n = {};
76
- for (let s of this.resolvers)
77
- n = s(o, n);
97
+ let n = { ...this.defaultConfig, ...e };
78
98
  return {
79
99
  name: this.name,
80
- context: n,
81
- hooks: this.hooks
100
+ context: { ...n },
101
+ hooks: this.hooks,
102
+ _extensionFn: this._extensionFn,
103
+ resolvers: this.resolvers
82
104
  };
83
105
  }
84
106
  static create(e) {
85
- return new t(e.name, [], {}, {});
107
+ return new t(e.name, [], {}, {}, void 0);
108
+ }
109
+ static instance() {
110
+ return {
111
+ create: (e) => new t(
112
+ e.name,
113
+ [],
114
+ {},
115
+ {},
116
+ void 0
117
+ )
118
+ };
86
119
  }
87
120
  };
88
121
  0 && (module.exports = {
package/dist/mjs/index.js CHANGED
@@ -4,32 +4,39 @@ var r = class s {
4
4
  resolvers;
5
5
  defaultConfig;
6
6
  hooks;
7
- constructor(e, o, t, n) {
8
- this.name = e, this.resolvers = o, this.hooks = t, this.defaultConfig = n;
7
+ instance;
8
+ _extensionFn;
9
+ constructor(e, n, t, o, i) {
10
+ this.name = e, this.resolvers = n, this.hooks = t, this.defaultConfig = o, this._extensionFn = i;
9
11
  }
10
- withConfig(e) {
12
+ config(e) {
11
13
  return new s(
12
14
  this.name,
13
15
  this.resolvers,
14
16
  this.hooks,
15
- e
17
+ e,
18
+ this._extensionFn
16
19
  );
17
20
  }
18
- decorate(e, o) {
19
- let t = (n, i) => ({
21
+ defineInstance(e) {
22
+ return this.instance = e, this;
23
+ }
24
+ decorate(e, n) {
25
+ let t = async (o, i) => ({
20
26
  ...i,
21
- [e]: o
27
+ [e]: n
22
28
  });
23
29
  return new s(
24
30
  this.name,
25
31
  [...this.resolvers, t],
26
32
  this.hooks,
27
- this.defaultConfig
33
+ this.defaultConfig,
34
+ this._extensionFn
28
35
  );
29
36
  }
30
- derive(e, o) {
31
- let t = (n, i) => {
32
- let a = { ...i, ...n }, l = o(a);
37
+ derive(e, n) {
38
+ let t = async (o, i) => {
39
+ let a = { ...i, ...o }, l = await n(a);
33
40
  return {
34
41
  ...i,
35
42
  [e]: l
@@ -39,29 +46,55 @@ var r = class s {
39
46
  this.name,
40
47
  [...this.resolvers, t],
41
48
  this.hooks,
42
- this.defaultConfig
49
+ this.defaultConfig,
50
+ this._extensionFn
43
51
  );
44
52
  }
45
- on(e, o) {
46
- return this.hooks[e] || (this.hooks[e] = []), this.hooks[e].push(o), new s(
53
+ on(e, n) {
54
+ let t = this.hooks[e] || [], o = {
55
+ ...this.hooks,
56
+ [e]: [...t, n]
57
+ };
58
+ return new s(
59
+ this.name,
60
+ this.resolvers,
61
+ o,
62
+ this.defaultConfig,
63
+ this._extensionFn
64
+ );
65
+ }
66
+ extends(e) {
67
+ return new s(
47
68
  this.name,
48
69
  this.resolvers,
49
70
  this.hooks,
50
- this.defaultConfig
71
+ this.defaultConfig,
72
+ (n, t) => ({ ...this._extensionFn ? this._extensionFn(n, t) : {}, ...e(n, t) })
51
73
  );
52
74
  }
53
75
  _build(e) {
54
- let o = { ...this.defaultConfig, ...e }, t = {};
55
- for (let n of this.resolvers)
56
- t = n(o, t);
76
+ let n = { ...this.defaultConfig, ...e };
57
77
  return {
58
78
  name: this.name,
59
- context: t,
60
- hooks: this.hooks
79
+ context: { ...n },
80
+ hooks: this.hooks,
81
+ _extensionFn: this._extensionFn,
82
+ resolvers: this.resolvers
61
83
  };
62
84
  }
63
85
  static create(e) {
64
- return new s(e.name, [], {}, {});
86
+ return new s(e.name, [], {}, {}, void 0);
87
+ }
88
+ static instance() {
89
+ return {
90
+ create: (e) => new s(
91
+ e.name,
92
+ [],
93
+ {},
94
+ {},
95
+ void 0
96
+ )
97
+ };
65
98
  }
66
99
  };
67
100
  export {
@@ -1,28 +1,36 @@
1
- import type { AnyPluginHooks } from '../types/plugin';
1
+ import type { AnyAsterflow, ExtendedAsterflow } from '@asterflow/core';
2
+ import type { PluginHooks, Resolver } from '../types/plugin';
2
3
  /**
3
4
  * A factory for creating plugins that can be configured and attached to AsterFlow.
4
5
  * Plugins are defined with a series of resolvers (`decorate`, `derive`) and lifecycle
5
6
  * hooks (`on`) that build up its context and runtime behavior.
6
7
  */
7
- export declare class Plugin<Path extends string, Config extends Record<string, any> = {}, Context extends Record<string, any> = {}, THooks extends AnyPluginHooks = {}> {
8
+ export declare class Plugin<Path extends string, Instance extends AnyAsterflow, Config extends Record<string, any> = {}, Context extends Record<string, any> = {}, Hooks extends PluginHooks<any, Context[], any> = {}, Extension extends Record<string, any> = {}> {
8
9
  readonly name: Path;
9
10
  private readonly resolvers;
10
11
  readonly defaultConfig: Partial<Config>;
11
- readonly hooks: THooks;
12
+ readonly hooks: Hooks;
13
+ instance: Instance;
14
+ private readonly _extensionFn?;
12
15
  private constructor();
13
16
  /**
14
17
  * Defines the shape of the configuration and its default values for this plugin.
15
18
  */
16
- withConfig<C extends Record<string, any>>(defaultConfig: C): Plugin<Path, C, Context, THooks>;
19
+ config<C extends Record<string, any>>(defaultConfig: C): Plugin<Path, Instance, C, Context, Hooks, Extension>;
20
+ /**
21
+ * O `defineInstance` agora é mais simples. Ele não precisa mais re-tipar
22
+ * a classe inteira. Ele só serve para passar o `this` para o `_build`.
23
+ */
24
+ defineInstance<Instanced extends AnyAsterflow>(instance: Instanced): this;
17
25
  /**
18
26
  * Adds a new static value to the plugin's context (decoration).
19
27
  */
20
- decorate<Key extends string, Value>(key: Key, value: Value): Plugin<Path, Config, Context & { [K in Key]: Value; }, THooks>;
28
+ decorate<Key extends string, Value>(key: Key, value: Value): Plugin<Path, Instance, Config, Context & { [K in Key]: Value; }, Hooks, Extension>;
21
29
  /**
22
30
  * Adds a new property to the context that is derived from the configuration and the existing context.
23
31
  * The resolver function is executed lazily when the plugin is registered via `app.use()`.
24
32
  */
25
- derive<Key extends string, Value>(key: Key, resolverFn: (context: Context & Config) => Value): Plugin<Path, Config, Context & { [K in Key]: Value; }, THooks>;
33
+ derive<Key extends string, Value>(key: Key, resolverFn: (context: Context & Config) => Value | Promise<Value>): Plugin<Path, Instance, Config, Context & { [K in Key]: Awaited<Value>; }, Hooks, Extension>;
26
34
  /**
27
35
  * Registers a handler for a specific lifecycle event.
28
36
  * Adding a hook makes the plugin "runtime-aware". AsterFlow can optimize by only
@@ -30,25 +38,35 @@ export declare class Plugin<Path extends string, Config extends Record<string, a
30
38
  *
31
39
  * @example
32
40
  * const routingPlugin = Plugin.create({ name: 'dynamic-routes' })
33
- * .on('beforeInitialize', (app, context) => {
34
- * // `app` is the AsterFlow instance
35
- * const dynamicRouter = createDynamicRouter();
36
- * app.controller(dynamicRouter);
37
- * });
41
+ * .on('beforeInitialize', (app, context) => { })
42
+ * .on('beforeInitialize', (app, context) => { });
38
43
  */
39
- on<Event extends keyof AnyPluginHooks, Handler extends NonNullable<AnyPluginHooks[Event]> extends (infer F)[] ? F : never>(event: Event, handler: Handler): Plugin<Path, Config, Context, THooks>;
44
+ on<Event extends keyof PluginHooks<ExtendedAsterflow<Instance>, Context & Config, Extension>, Handler extends NonNullable<PluginHooks<ExtendedAsterflow<Instance>, Context & Config, Extension>[Event]> extends (infer F)[] ? F : never>(event: Event, handler: Handler): Plugin<Path, Instance, Config, Context, Omit<Hooks, Event> & { [K in Event]: [...Hooks extends { [k in Event]: any[]; } ? Hooks[K] : [], Handler]; }, Extension>;
45
+ /**
46
+ * Defines new properties or methods to be added to the AsterFlow instance.
47
+ * A função recebe a instância do app e o contexto do plugin, e deve retornar um objeto
48
+ * com as novas propriedades.
49
+ */
50
+ extends<E extends Record<string, any>>(extensionFn: (app: Instance, context: Context) => E): Plugin<Path, Instance, Config, Context, Hooks, Extension & E>;
40
51
  /**
41
52
  * Builds the final context and hooks from the provided configuration.
42
53
  */
43
54
  _build(config: any): {
44
55
  name: Path;
45
- context: Context;
46
- hooks: THooks;
56
+ context: Config & Context;
57
+ hooks: Hooks;
58
+ _extensionFn: ((app: Instance, context: Context) => Extension) | undefined;
59
+ resolvers: Resolver[];
47
60
  };
48
61
  /**
49
62
  * Creates a new Plugin instance. This is the entry point for building a plugin.
50
63
  */
51
- static create<Path extends string>(options: {
64
+ static create<Path extends string, Asterflow extends AnyAsterflow>(options: {
52
65
  name: Path;
53
- }): Plugin<Path, {}, {}, {}>;
66
+ }): Plugin<Path, Asterflow, {}, {}, {}>;
67
+ static instance<T extends AnyAsterflow>(): {
68
+ create: <Path extends string>(options: {
69
+ name: Path;
70
+ }) => Plugin<Path, T, {}, {}, {}, {}>;
71
+ };
54
72
  }
@@ -1,29 +1,34 @@
1
- import type { AsterFlow } from '@asterflow/core';
1
+ import type { AnyAsterflow, ExtendedAsterflow } from '@asterflow/core';
2
2
  import type { Request } from '@asterflow/request';
3
3
  import type { Response } from '@asterflow/response';
4
4
  import type { Plugin } from '../controllers/Plugin';
5
- export type AnyPlugin = Plugin<string>;
6
- export type AnyPluginHooks = PluginHooks<any, any, any, any>;
5
+ export type AnyPlugin = Plugin<string, any, any, any, any, any>;
6
+ export type AnyPlugins = Record<string, ResolvedPlugin<AnyPlugin>>;
7
+ export type AnyPluginHooks = PluginHooks<any, any>;
8
+ export type InferPluginExtension<P> = P extends Plugin<any, any, any, any, any, infer Ext> ? Ext : {};
9
+ export type ResolvedPlugin<P extends AnyPlugin> = P extends Plugin<infer Path, any, any, infer Ctx, any, infer Ext> ? {
10
+ name: Path;
11
+ context: Ctx;
12
+ hooks: PluginHooks<any, Ctx, Ext>;
13
+ _extensionFn?: (app: any, context: Ctx) => Ext;
14
+ resolvers: Resolver[];
15
+ } : never;
7
16
  /**
8
17
  * Tipo para extrair o objeto de configuração de um plugin.
9
18
  * Ele torna as propriedades com valores padrão opcionais.
10
19
  */
11
- export type ConfigArgument<P extends AnyPlugin> = P extends Plugin<any, any, any, infer C> ? Omit<C, keyof P['defaultConfig']> & Partial<Pick<C, keyof P['defaultConfig'] & keyof C>> : never;
12
- /**
13
- * Tipo para o plugin após seu contexto ter sido construído.
14
- */
15
- export type ResolvedPlugin<P extends AnyPlugin> = ReturnType<P['_build']>;
20
+ export type ConfigArgument<P extends AnyPlugin> = P extends Plugin<any, any, infer C, any, any> ? Omit<C, keyof P['defaultConfig']> & Partial<Pick<C, keyof P['defaultConfig'] & keyof C>> : never;
16
21
  /**
17
22
  * Defines the available lifecycle hooks a plugin can register.
18
23
  */
19
- export type PluginHooks<Instance extends AsterFlow<any>, Context extends Record<string, any>, Responser extends Response, Requester extends Request<unknown>> = {
20
- beforeInitialize?: ((app: Instance, context: Context) => void | Promise<void>)[];
21
- afterInitialize?: ((app: Instance, context: Context) => void | Promise<void>)[];
22
- onRequest?: ((request: Requester, response: Responser, context: Context) => void | Promise<void>)[];
23
- onResponse?: ((request: Requester, response: Responser, context: Context) => void | Promise<void>)[];
24
+ export type PluginHooks<Instance extends AnyAsterflow, Context extends Record<string, any>, Extension extends Record<string, any> = {}> = {
25
+ beforeInitialize?: ((app: ExtendedAsterflow<Instance> & Extension, context: Context) => void | Promise<void>)[];
26
+ afterInitialize?: ((app: ExtendedAsterflow<Instance> & Extension, context: Context) => void | Promise<void>)[];
27
+ onRequest?: ((request: Request<unknown>, response: Response, context: Context) => void | Promise<void>)[];
28
+ onResponse?: ((request: Request<unknown>, response: Response, context: Context) => void | Promise<void>)[];
24
29
  };
25
30
  /**
26
31
  * Represents a function that resolves a part of the plugin's context.
27
32
  * @internal
28
33
  */
29
- export type Resolver = (config: any, context: any) => Record<string, any>;
34
+ export type Resolver = (config: any, context: any) => Promise<Record<string, any>>;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@asterflow/plugin",
3
- "version": "1.0.1",
3
+ "version": "1.0.3",
4
4
  "main": "dist/cjs/index.cjs",
5
5
  "module": "dist/mjs/index.js",
6
6
  "types": "dist/types/index.d.ts",
@@ -18,9 +18,9 @@
18
18
  "node": ">=20"
19
19
  },
20
20
  "devDependencies": {
21
- "@asterflow/core": "1.0.5",
22
- "@asterflow/response": "1.0.2",
23
- "@asterflow/request": "1.0.5"
21
+ "@asterflow/core": "1.0.7",
22
+ "@asterflow/response": "1.0.4",
23
+ "@asterflow/request": "1.0.7"
24
24
  },
25
25
  "peerDependencies": {
26
26
  "typescript": "^5.8.3"