@exchanet/enet 1.0.12 → 1.0.14
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/package.json +6 -2
- package/src/index.js +2 -2
- package/src/utils/registry.js +8 -15
- package/.enet/modular-design.md +0 -136
- package/.enet/pdca-t.md +0 -110
package/package.json
CHANGED
|
@@ -1,11 +1,16 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@exchanet/enet",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.14",
|
|
4
4
|
"description": "enet — exchanet methods manager. Install, scaffold and manage AI coding methods.",
|
|
5
5
|
"bin": {
|
|
6
6
|
"enet": "src/index.js"
|
|
7
7
|
},
|
|
8
8
|
"type": "module",
|
|
9
|
+
"files": [
|
|
10
|
+
"src",
|
|
11
|
+
"registry.json",
|
|
12
|
+
"manifest.schema.json"
|
|
13
|
+
],
|
|
9
14
|
"scripts": {
|
|
10
15
|
"dev": "node src/index.js",
|
|
11
16
|
"test": "node --test"
|
|
@@ -15,7 +20,6 @@
|
|
|
15
20
|
"commander": "^12.0.0",
|
|
16
21
|
"enquirer": "^2.4.1",
|
|
17
22
|
"ora": "^8.0.1",
|
|
18
|
-
"node-fetch": "^3.3.2",
|
|
19
23
|
"ajv": "^8.12.0",
|
|
20
24
|
"ajv-formats": "^3.0.1",
|
|
21
25
|
"fs-extra": "^11.2.0"
|
package/src/index.js
CHANGED
|
@@ -77,7 +77,7 @@ program
|
|
|
77
77
|
program
|
|
78
78
|
.command('init')
|
|
79
79
|
.description('Interactively create a manifest.json for a new module')
|
|
80
|
-
.option('-n, --name <
|
|
80
|
+
.option('-n, --name <n>', 'Module name')
|
|
81
81
|
.option('-s, --section <section>', 'Admin Panel section')
|
|
82
82
|
.option('--json', 'Print manifest as JSON without writing to disk')
|
|
83
83
|
.action(initCommand)
|
|
@@ -90,7 +90,7 @@ program
|
|
|
90
90
|
.action(validateCommand)
|
|
91
91
|
|
|
92
92
|
program
|
|
93
|
-
.command('new <type> <
|
|
93
|
+
.command('new <type> <n>')
|
|
94
94
|
.description('Scaffold a new module, ui-pack or integration')
|
|
95
95
|
.option('-s, --section <section>', 'Admin Panel section')
|
|
96
96
|
.option('--dry-run', 'Preview files without writing')
|
package/src/utils/registry.js
CHANGED
|
@@ -3,7 +3,7 @@ import path from 'path'
|
|
|
3
3
|
import { fileURLToPath } from 'url'
|
|
4
4
|
|
|
5
5
|
const __dirname = path.dirname(fileURLToPath(import.meta.url))
|
|
6
|
-
const RAW_BASE
|
|
6
|
+
const RAW_BASE = 'https://raw.githubusercontent.com'
|
|
7
7
|
const REGISTRY_URL = `${RAW_BASE}/exchanet/enet/main/registry.json`
|
|
8
8
|
const CACHE_FILE = path.join(__dirname, '../../.registry-cache.json')
|
|
9
9
|
const CACHE_TTL_MS = 1000 * 60 * 60 // 1 hour
|
|
@@ -82,7 +82,7 @@ export async function fetchFromGitHub(repo, filePath) {
|
|
|
82
82
|
// ── Install state ─────────────────────────────────────────────────────────────
|
|
83
83
|
//
|
|
84
84
|
// Tracks which agents have each method installed.
|
|
85
|
-
// Stored in
|
|
85
|
+
// Stored in <project>/.enet/installed.json
|
|
86
86
|
//
|
|
87
87
|
// Format:
|
|
88
88
|
// {
|
|
@@ -90,19 +90,15 @@ export async function fetchFromGitHub(repo, filePath) {
|
|
|
90
90
|
// "agents": ["cursor", "claudecode", "antigravity"],
|
|
91
91
|
// "version": "3.0.0",
|
|
92
92
|
// "updatedAt": "2025-03-01T10:00:00.000Z"
|
|
93
|
-
// }
|
|
94
|
-
// "modular-design": { ... }
|
|
93
|
+
// }
|
|
95
94
|
// }
|
|
96
95
|
|
|
97
96
|
function getInstallRecordFile() {
|
|
98
|
-
// Resolve relative to cwd so it works in any project
|
|
99
97
|
return path.join(process.cwd(), '.enet', 'installed.json')
|
|
100
98
|
}
|
|
101
99
|
|
|
102
100
|
/**
|
|
103
|
-
*
|
|
104
|
-
* Returns { agents: ['cursor', ...], version: '3.0.0', updatedAt: '...' }
|
|
105
|
-
* or null if the method has never been installed.
|
|
101
|
+
* Returns the install record for a single method, or null if never installed.
|
|
106
102
|
*/
|
|
107
103
|
export async function readInstallRecord(methodId) {
|
|
108
104
|
try {
|
|
@@ -116,25 +112,22 @@ export async function readInstallRecord(methodId) {
|
|
|
116
112
|
}
|
|
117
113
|
|
|
118
114
|
/**
|
|
119
|
-
* Writes
|
|
120
|
-
* Merges with existing records — other methods are
|
|
115
|
+
* Writes the install record for a single method.
|
|
116
|
+
* Merges with existing records — other methods are never touched.
|
|
121
117
|
*/
|
|
122
118
|
export async function writeInstallRecord(methodId, record) {
|
|
123
119
|
try {
|
|
124
120
|
const file = getInstallRecordFile()
|
|
125
121
|
await fs.ensureDir(path.dirname(file))
|
|
126
|
-
|
|
127
122
|
let data = {}
|
|
128
123
|
if (await fs.pathExists(file)) {
|
|
129
124
|
data = await fs.readJson(file).catch(() => ({}))
|
|
130
125
|
}
|
|
131
|
-
|
|
132
126
|
data[methodId] = {
|
|
133
|
-
agents:
|
|
134
|
-
version:
|
|
127
|
+
agents: record.agents,
|
|
128
|
+
version: record.version ?? null,
|
|
135
129
|
updatedAt: new Date().toISOString()
|
|
136
130
|
}
|
|
137
|
-
|
|
138
131
|
await fs.writeJson(file, data, { spaces: 2 })
|
|
139
132
|
} catch {
|
|
140
133
|
// Non-fatal — install works correctly even if state cannot be saved
|
package/.enet/modular-design.md
DELETED
|
@@ -1,136 +0,0 @@
|
|
|
1
|
-
# METHOD MODULAR DESIGN — Agent Instructions
|
|
2
|
-
> Universal Modular Architecture · v1.0.0 · @exchanet
|
|
3
|
-
|
|
4
|
-
---
|
|
5
|
-
|
|
6
|
-
## YOUR PRIMARY DIRECTIVE / TU DIRECTIVA PRINCIPAL
|
|
7
|
-
|
|
8
|
-
You are building a modular application using Method Modular Design. Every module you create must be self-describing via a `manifest.json` file. The manifest is written **before any code**. The system reads manifests to automatically generate the Admin Panel, dashboard, and settings UI. You never manually wire backend logic to the Admin Panel — the manifest does it.
|
|
9
|
-
|
|
10
|
-
Estás construyendo una aplicación modular usando Method Modular Design. Cada módulo que crees debe ser auto-descriptivo a través de un archivo `manifest.json`. El manifest se escribe **antes de cualquier código**. El sistema lee los manifests para generar automáticamente el Panel Admin, dashboard y UI de configuración. Nunca cablearás manualmente la lógica backend al Panel Admin — el manifest lo hace.
|
|
11
|
-
|
|
12
|
-
**If a module has no manifest, it does not exist.**
|
|
13
|
-
**Si un módulo no tiene manifest, no existe.**
|
|
14
|
-
|
|
15
|
-
---
|
|
16
|
-
|
|
17
|
-
## ABSOLUTE RULES / REGLAS ABSOLUTAS
|
|
18
|
-
|
|
19
|
-
1. **No manifest = module does not exist.** Core rejects modules without valid `manifest.json`.
|
|
20
|
-
2. **Manifest before code.** Complete manifest before any handler, model, or component.
|
|
21
|
-
3. **Zero hardcoded configuration.** Every configurable value lives in `manifest.settings`, read via `context.settings.get("key")`.
|
|
22
|
-
4. **Core has no business logic.** Domain logic lives in modules only.
|
|
23
|
-
5. **Admin Panel is a renderer.** Never code it to show a specific module — modules declare capabilities, Admin Panel renders them.
|
|
24
|
-
6. **A module is complete only when the Admin Panel reflects it correctly.**
|
|
25
|
-
7. **Removing a module folder requires zero code changes elsewhere.**
|
|
26
|
-
|
|
27
|
-
---
|
|
28
|
-
|
|
29
|
-
## WORKFLOW / FLUJO DE TRABAJO
|
|
30
|
-
|
|
31
|
-
### Starting a new project / Nuevo proyecto:
|
|
32
|
-
1. Ask for spectech if not provided (stack, database, deploy target)
|
|
33
|
-
2. Declare the architecture you will build
|
|
34
|
-
3. **Wait for confirmation before writing any code**
|
|
35
|
-
4. Build Core → Manifest schema → Modules → Admin Panel
|
|
36
|
-
|
|
37
|
-
### Adding a module / Añadir un módulo:
|
|
38
|
-
1. Write complete `manifest.json` (all settings + capabilities + hooks)
|
|
39
|
-
2. Validate against `manifest.schema.json`
|
|
40
|
-
3. Implement all handlers referenced in manifest
|
|
41
|
-
4. Place in modules directory (Core discovers automatically)
|
|
42
|
-
5. Boot system and verify module appears in Admin Panel
|
|
43
|
-
6. Build custom UI components only if manifest declares a `component` field
|
|
44
|
-
|
|
45
|
-
### When you cannot complete a manifest / Cuando no puedes completar un manifest:
|
|
46
|
-
|
|
47
|
-
**STOP. Ask the user:**
|
|
48
|
-
|
|
49
|
-
```
|
|
50
|
-
"I cannot complete the manifest for [module name] because I don't understand
|
|
51
|
-
[specific aspect]. Before I continue, I need you to clarify: [specific question]"
|
|
52
|
-
|
|
53
|
-
"No puedo completar el manifest de [nombre del módulo] porque no entiendo
|
|
54
|
-
[aspecto específico]. Antes de continuar, necesito que aclares: [pregunta específica]"
|
|
55
|
-
```
|
|
56
|
-
|
|
57
|
-
Do not proceed. Do not create a partial manifest. Do not make assumptions. Wait.
|
|
58
|
-
No continúes. No crees un manifest parcial. No hagas suposiciones. Espera.
|
|
59
|
-
|
|
60
|
-
---
|
|
61
|
-
|
|
62
|
-
## MANIFEST FORMAT / FORMATO DEL MANIFEST
|
|
63
|
-
|
|
64
|
-
```json
|
|
65
|
-
{
|
|
66
|
-
"id": "module-id",
|
|
67
|
-
"name": "Human Name",
|
|
68
|
-
"version": "1.0.0",
|
|
69
|
-
"type": "functional",
|
|
70
|
-
"section": "admin-section",
|
|
71
|
-
"dependencies": [],
|
|
72
|
-
"hooks": { "event.name": "ClassName.method" },
|
|
73
|
-
"settings": {
|
|
74
|
-
"key": {
|
|
75
|
-
"type": "integer|string|boolean|select",
|
|
76
|
-
"label": "Label",
|
|
77
|
-
"default": null,
|
|
78
|
-
"ui": "slider|toggle|text|select"
|
|
79
|
-
}
|
|
80
|
-
},
|
|
81
|
-
"capabilities": [
|
|
82
|
-
{ "type": "view", "label": "Label", "data": "ClassName.method" },
|
|
83
|
-
{ "type": "action", "label": "Label", "handler": "ClassName.method", "dangerous": false },
|
|
84
|
-
{ "type": "metric", "label": "Label", "data": "ClassName.method" },
|
|
85
|
-
{ "type": "widget", "label": "Label", "data": "ClassName.method", "component": "ComponentName" }
|
|
86
|
-
]
|
|
87
|
-
}
|
|
88
|
-
```
|
|
89
|
-
|
|
90
|
-
---
|
|
91
|
-
|
|
92
|
-
## WHAT THE CORE MUST IMPLEMENT / QUÉ DEBE IMPLEMENTAR EL CORE
|
|
93
|
-
|
|
94
|
-
- Module discovery — scan modules dir for valid manifests
|
|
95
|
-
- Manifest validation — reject invalid manifests with clear errors (never silent)
|
|
96
|
-
- Dependency resolution — boot in correct order
|
|
97
|
-
- Handler registry — map `ClassName.method` references to implementations
|
|
98
|
-
- Hook system — dispatch events to declared handlers
|
|
99
|
-
- Settings store — persistent, namespaced by module ID, initialized from defaults
|
|
100
|
-
- REFLEX engine — read all manifests, build Admin nav, dashboard, settings schemas
|
|
101
|
-
- Admin API — standard endpoints (same in every project, every stack)
|
|
102
|
-
|
|
103
|
-
```
|
|
104
|
-
GET /api/admin/manifest-registry
|
|
105
|
-
GET /api/admin/navigation
|
|
106
|
-
GET /api/admin/settings/:moduleId
|
|
107
|
-
POST /api/admin/settings/:moduleId
|
|
108
|
-
GET /api/admin/dashboard
|
|
109
|
-
POST /api/admin/action/:moduleId/:actionId
|
|
110
|
-
GET /api/admin/health
|
|
111
|
-
```
|
|
112
|
-
|
|
113
|
-
**The Core has ZERO business logic. / El Core tiene CERO lógica de negocio.**
|
|
114
|
-
|
|
115
|
-
---
|
|
116
|
-
|
|
117
|
-
## COMPLETION CHECKLIST / CHECKLIST DE COMPLETITUD
|
|
118
|
-
|
|
119
|
-
Before marking any module complete / Antes de marcar cualquier módulo como completo:
|
|
120
|
-
|
|
121
|
-
- [ ] `manifest.json` valid / válido
|
|
122
|
-
- [ ] All declared handlers implemented / Todos los handlers declarados implementados
|
|
123
|
-
- [ ] Zero hardcoded values — all settings use `context.settings.get()` / Cero hardcoded
|
|
124
|
-
- [ ] Module appears in Admin Panel navigation / El módulo aparece en la navegación del Panel Admin
|
|
125
|
-
- [ ] All views render with data / Todas las vistas renderizan con datos
|
|
126
|
-
- [ ] All actions execute correctly / Todas las acciones ejecutan correctamente
|
|
127
|
-
- [ ] Dangerous actions show confirmation dialog / Las acciones peligrosas muestran diálogo
|
|
128
|
-
- [ ] All metrics show in dashboard / Todas las métricas aparecen en el dashboard
|
|
129
|
-
- [ ] All settings render and save correctly / Todos los settings renderizan y guardan
|
|
130
|
-
- [ ] Adding this module required zero Core changes / Añadir el módulo requirió cero cambios en el Core
|
|
131
|
-
- [ ] Removing module folder removes it completely from Admin Panel / Eliminar la carpeta lo elimina del Panel Admin
|
|
132
|
-
|
|
133
|
-
---
|
|
134
|
-
|
|
135
|
-
*For full documentation / Para documentación completa: `METHOD.md`*
|
|
136
|
-
*Method Modular Design v1.0.0 · @exchanet · MIT*
|
package/.enet/pdca-t.md
DELETED
|
@@ -1,110 +0,0 @@
|
|
|
1
|
-
---
|
|
2
|
-
description: Method PDCA-T — Systematic quality cycle for AI-assisted coding
|
|
3
|
-
trigger: always_on
|
|
4
|
-
---
|
|
5
|
-
|
|
6
|
-
# METHOD PDCA-T — Active for all tasks in this project
|
|
7
|
-
|
|
8
|
-
You are operating under the PDCA-T quality methodology. Apply this 8-phase cycle to every coding task without exception.
|
|
9
|
-
|
|
10
|
-
## PHASE 1 — PLANNING
|
|
11
|
-
Before writing any code:
|
|
12
|
-
- State the exact objective in one sentence
|
|
13
|
-
- Define what IS and IS NOT in scope
|
|
14
|
-
- Ask clarifying questions if anything is ambiguous
|
|
15
|
-
- Identify external dependencies
|
|
16
|
-
- Define the acceptance criterion
|
|
17
|
-
|
|
18
|
-
Do not advance until the objective is unambiguous.
|
|
19
|
-
|
|
20
|
-
## PHASE 2 — REQUIREMENTS ANALYSIS
|
|
21
|
-
- List Functional Requirements: `FR-NN: [what the system must do]`
|
|
22
|
-
- List Non-Functional Requirements: `NFR-NN: [constraint or quality attribute with metric]`
|
|
23
|
-
- Build Risk Register: `RISK-NN: [risk] | Probability | Impact | Mitigation`
|
|
24
|
-
|
|
25
|
-
## PHASE 3 — ARCHITECTURE DESIGN
|
|
26
|
-
Before any implementation:
|
|
27
|
-
- Write ADRs: `ADR-NN: [title] | Context | Decision | Alternatives | Consequences`
|
|
28
|
-
- Define interface contracts (function signatures + full docstrings) before implementing bodies
|
|
29
|
-
- Define module structure: domain / infrastructure / interfaces
|
|
30
|
-
|
|
31
|
-
## PHASE 4 — MICRO-TASK CYCLE (≤ 50 lines per task)
|
|
32
|
-
|
|
33
|
-
**4.1** — Check available skills in `.cursor/skills/` and reusable context
|
|
34
|
-
|
|
35
|
-
**4.2** — Write tests FIRST. Required categories:
|
|
36
|
-
- Happy path · Error cases · Edge cases · Security · Performance (if applicable)
|
|
37
|
-
- Structure: Arrange / Act / Assert
|
|
38
|
-
- Naming: `test_[function]_[scenario]_[expected_outcome]`
|
|
39
|
-
|
|
40
|
-
**4.3** — Implement code. Standards:
|
|
41
|
-
- Full type hints on every parameter and return value
|
|
42
|
-
- Docstring with Args, Returns, Raises
|
|
43
|
-
- Single responsibility per function
|
|
44
|
-
- `Decimal` not `float` for monetary values
|
|
45
|
-
- Specific exception types — never bare `except:`
|
|
46
|
-
- Zero hardcoded configuration
|
|
47
|
-
- Structured logging with context fields
|
|
48
|
-
|
|
49
|
-
**4.4** — Self-review before running tests:
|
|
50
|
-
```
|
|
51
|
-
□ Type hints complete? □ All inputs validated?
|
|
52
|
-
□ Docstring written? □ No hardcoded secrets?
|
|
53
|
-
□ Single responsibility? □ Semantic names?
|
|
54
|
-
□ No code duplication? □ Errors logged with context?
|
|
55
|
-
```
|
|
56
|
-
|
|
57
|
-
**4.5** — Execute tests and show REAL complete output:
|
|
58
|
-
```bash
|
|
59
|
-
pytest tests/ -v --cov=src --cov-report=term-missing --tb=short
|
|
60
|
-
```
|
|
61
|
-
Never summarize. Never say "tests pass". Show the exact output.
|
|
62
|
-
|
|
63
|
-
**4.6** — Validate:
|
|
64
|
-
- All tests pass (100%)? If not → fix code, explain, re-run
|
|
65
|
-
- Coverage ≥ 99%? If not → identify uncovered lines → add tests → re-run
|
|
66
|
-
- Repeat until both conditions are met
|
|
67
|
-
|
|
68
|
-
## PHASE 5 — INTEGRAL VALIDATION
|
|
69
|
-
After all micro-tasks:
|
|
70
|
-
- **Security:** No OWASP Top 10 issues · inputs validated · outputs sanitized · no hardcoded secrets · minimum privilege
|
|
71
|
-
- **Tests:** 100% passed · 0 failed · coverage ≥ 99% · all categories present
|
|
72
|
-
- **Code quality:** Type hints 100% · cyclomatic complexity < 10 · no duplication · SRP · docstrings 100%
|
|
73
|
-
- **Performance:** No N+1 · indexes on filter fields · pagination in collections · timeouts configured
|
|
74
|
-
- **Architecture:** No circular imports · layers respected · low coupling · inward dependencies only
|
|
75
|
-
|
|
76
|
-
## PHASE 6 — TECHNICAL DEBT MANAGEMENT
|
|
77
|
-
Register every known issue before delivery:
|
|
78
|
-
```
|
|
79
|
-
DEBT-XXX: [Short title]
|
|
80
|
-
Type: Technical | Test | Documentation | Architecture | Security | Performance
|
|
81
|
-
Description: [What and why]
|
|
82
|
-
Impact: High | Medium | Low — [justification]
|
|
83
|
-
Effort: Xh
|
|
84
|
-
Priority: High | Medium | Low
|
|
85
|
-
Plan: [Specific action and target version]
|
|
86
|
-
```
|
|
87
|
-
Do not write TODO/FIXME in code — register as DEBT-XXX instead.
|
|
88
|
-
|
|
89
|
-
## PHASE 7 — REFINEMENT TO ≥ 99%
|
|
90
|
-
If any metric is below target:
|
|
91
|
-
`Identify → Classify → Plan → Execute → Verify → Confirm ≥ 99%`
|
|
92
|
-
Never advance to Phase 8 without confirming ≥ 99% on all 5 validation dimensions.
|
|
93
|
-
|
|
94
|
-
## PHASE 8 — DELIVERY REPORT
|
|
95
|
-
Always close every task with:
|
|
96
|
-
1. Implementation summary (2-3 sentences)
|
|
97
|
-
2. Test table: total / passed / failed / coverage / time
|
|
98
|
-
3. Full unedited pytest output
|
|
99
|
-
4. Key technical decisions with justifications
|
|
100
|
-
5. Technical debt registered (DEBT-XXX list)
|
|
101
|
-
6. CI/CD checklist (all items confirmed)
|
|
102
|
-
7. Suggested next steps
|
|
103
|
-
|
|
104
|
-
## ABSOLUTE RULES — NEVER VIOLATE
|
|
105
|
-
1. Tests BEFORE implementation — always, no exceptions
|
|
106
|
-
2. Show REAL test output — never summarize or omit
|
|
107
|
-
3. No hardcoded secrets — environment variables from commit 1
|
|
108
|
-
4. Coverage ≥ 99% before any delivery
|
|
109
|
-
5. ADRs for non-trivial decisions
|
|
110
|
-
6. All known issues as DEBT-XXX with priority and plan
|