plug-code 1.1.0 → 1.1.2

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 CHANGED
@@ -1,16 +1,116 @@
1
1
  # Plug&Code
2
2
 
3
- Plug&Code is a multipurpose framework for React, designed for **scalability, reusability, and organized components**.
3
+ Plug&Code is a multipurpose framework for React designed for **scalability, reusability, and modular organization**. It allows you to build complex applications by "plugging in" features without tightly coupling your codebase.
4
4
 
5
5
  ## Usage
6
6
 
7
- You are welcome to use Plug&Code in your projects, **personal or commercial**, as long as you **do not modify or redistribute the framework** without explicit permission from the author.
7
+ You are welcome to use Plug&Code in your projects, **personal or commercial**, as long as you **do not modify or redistribute the framework** without explicit permission from the author.
8
+
9
+ ---
8
10
 
9
11
  ### Installation
10
12
 
11
- You can install the framework via npm or yarn:
13
+ Install the framework via npm or yarn:
12
14
 
13
15
  ```bash
14
16
  npm install plug-code
15
17
  # or
16
18
  yarn add plug-code
19
+
20
+ ```
21
+
22
+ ### Core Concepts
23
+
24
+ Plug&Code is built around the **PLC (Pipeline-Logic-Command)** pattern:
25
+
26
+ * **Slots (UI Pipeline):** Inject components into pre-defined locations from any feature.
27
+ * **Commands (Logic):** Execute and wrap business actions (e.g., `checkout`, `print`, `save`).
28
+ * **Transforms (Data):** Pass data through named channels to be modified by different features.
29
+
30
+ ---
31
+
32
+ ### Quick Start Guide
33
+
34
+ #### 1. Initialize your System
35
+
36
+ Define your system and register features using the fluent API.
37
+
38
+ ```tsx
39
+ import { createPlugAndCode } from 'plug-code';
40
+
41
+ export const { useSystemPlc, SystemPlcRoot } = createPlugAndCode((api) => {
42
+
43
+ // Define a Sales Feature
44
+ api.feature("sales", (api) => {
45
+ // Register a UI component into a slot
46
+ api.register("header.cart", () => <CartIcon />);
47
+
48
+ // Register a business command
49
+ api.registerCommand("sales.checkout", async (items) => {
50
+ console.log("Saving items to database...", items);
51
+ return { success: true };
52
+ });
53
+ });
54
+
55
+ // Define a Logger Feature that wraps existing logic
56
+ api.feature("logger", (api) => {
57
+ api.wrapCommand("sales.checkout", (next) => async (items) => {
58
+ console.log("Checkout started...");
59
+ const result = await next(items);
60
+ console.log("Checkout finished:", result);
61
+ return result;
62
+ });
63
+ });
64
+ });
65
+
66
+ ```
67
+
68
+ #### 2. Wrap your Application
69
+
70
+ Use the `useSystemPlc` hook to manage the state and `SystemPlcRoot` to provide the context.
71
+
72
+ ```tsx
73
+ function App() {
74
+ // Initialize state with initial properties
75
+ const { api, useSelector } = useSystemPlc({ shopName: "My Store" });
76
+
77
+ return (
78
+ <SystemPlcRoot api={api}>
79
+ <nav>
80
+ {/* Render slots from any feature */}
81
+ {api.render("header.cart")}
82
+ </nav>
83
+ <main>
84
+ <h1>Welcome to {useSelector(s => s.root.shopName)}</h1>
85
+ </main>
86
+ </SystemPlcRoot>
87
+ );
88
+ }
89
+
90
+ ```
91
+
92
+ ---
93
+
94
+ ### API Reference
95
+
96
+ #### **UI Management (Slots)**
97
+
98
+ * `api.register(slotName, component)`: Adds a UI component to a slot.
99
+ * `api.render(slotName)`: Renders all components registered in that slot.
100
+ * `api.wrap(slot, wrapper)`: Wraps a slot's content with higher-order components.
101
+
102
+ #### **Business Logic (Commands)**
103
+
104
+ * `api.registerCommand(id, fn)`: Registers an executable action.
105
+ * `api.execute(id, payload)`: Runs a command and returns a Promise.
106
+ * `api.wrapCommand(id, (next) => ...)`: Intercepts a command to add side-effects or validations.
107
+
108
+ #### **Data Processing (Transforms)**
109
+
110
+ * `api.send(channel, id, fn, priority)`: Adds a data transformer to a specific channel.
111
+ * `api.receive(channel, initialData)`: Pipes data through all transformers in the channel.
112
+
113
+ #### **State Management**
114
+
115
+ * `useSelector(selector)`: Reactively listen to state changes.
116
+ * `api.update(key, updater)`: Update store data using Immer-powered drafts.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "plug-code",
3
- "version": "1.1.0",
3
+ "version": "1.1.2",
4
4
  "description": "",
5
5
  "main": "src/plug-code.tsx",
6
6
  "types": "types/plug-code.d.ts",
@@ -37,7 +37,7 @@ export class PlcAPI<S extends ObjectType> {
37
37
 
38
38
  createFeature(name: string, setupFn: (api: PlcAPI<S>) => void): PlcAPI<S> {
39
39
  if (this.installedFeatures.has(name)) {
40
- console.warn(`[PlcFramework] La feature '${name}' ya fue registrada. Se omitirá para evitar conflictos.`);
40
+ console.warn(`[PlcFramework] Feature '${name}' is already registered. It will be skipped to avoid conflicts.`);
41
41
  return this;
42
42
  }
43
43
 
@@ -45,7 +45,7 @@ export class PlcAPI<S extends ObjectType> {
45
45
  setupFn(this);
46
46
  this.installedFeatures.add(name);
47
47
  } catch (error) {
48
- console.error(`[PlcFramework] 💥 Error crítico inicializando la feature '${name}':`, error);
48
+ console.error(`[PlcFramework] 💥 Critical error initializing feature '${name}':`, error);
49
49
  }
50
50
 
51
51
  return this;
@@ -187,7 +187,7 @@ export class PlcAPI<S extends ObjectType> {
187
187
  try {
188
188
  currentData = transformer.fn(currentData, context);
189
189
  } catch (error) {
190
- console.error(`[PlcAPI] Error en transform '${channel as string}/${transformer.id}':`, error);
190
+ console.error(`[PlcAPI] Error in transform '${channel as string}/${transformer.id}':`, error);
191
191
  }
192
192
  }
193
193
 
@@ -199,7 +199,7 @@ export class PlcAPI<S extends ObjectType> {
199
199
  fn: CommandFn<CommandPayload<K>, CommandResult<K>>
200
200
  ) {
201
201
  if (this.commands.has(id as string)) {
202
- console.warn(`[PlcAPI] Sobrescribiendo comando '${id as string}'`);
202
+ console.warn(`[PlcAPI] Overwriting command '${id as string}'`);
203
203
  }
204
204
  this.commands.set(id as string, fn as any);
205
205
  }
@@ -210,7 +210,7 @@ export class PlcAPI<S extends ObjectType> {
210
210
  ) {
211
211
  const currentFn = this.commands.get(id as string);
212
212
  if (!currentFn) {
213
- console.error(`[PlcAPI] No se puede envolver '${id as string}', comando no existe.`);
213
+ console.error(`[PlcAPI] Cannot wrap '${id as string}', command does not exist.`);
214
214
  return;
215
215
  }
216
216
  this.commands.set(id as string, wrapper(currentFn) as any);
@@ -222,13 +222,13 @@ export class PlcAPI<S extends ObjectType> {
222
222
  ): Promise<CommandResult<K>> {
223
223
  const fn = this.commands.get(id as string);
224
224
  if (!fn) {
225
- throw new Error(`[PlcAPI] Comando '${id as string}' no encontrado.`);
225
+ throw new Error(`[PlcAPI] Command '${id as string}' not found.`);
226
226
  }
227
227
 
228
228
  try {
229
229
  return await fn(payload);
230
230
  } catch (error) {
231
- console.error(`[PlcAPI] Error ejecutando '${id as string}':`, error);
231
+ console.error(`[PlcAPI] Error executing '${id as string}':`, error);
232
232
  throw error;
233
233
  }
234
234
  }