pumuki-ast-hooks 5.5.47 → 5.5.49

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 (31) hide show
  1. package/docs/CODE_STANDARDS.md +5 -0
  2. package/docs/VIOLATIONS_RESOLUTION_PLAN.md +5 -140
  3. package/package.json +1 -1
  4. package/scripts/hooks-system/.audit_tmp/hook-metrics.jsonl +96 -0
  5. package/scripts/hooks-system/application/services/installation/VSCodeTaskConfigurator.js +3 -1
  6. package/scripts/hooks-system/bin/gitflow-cycle.js +0 -0
  7. package/scripts/hooks-system/config/project.config.json +1 -1
  8. package/scripts/hooks-system/infrastructure/ast/android/analyzers/AndroidSOLIDAnalyzer.js +11 -255
  9. package/scripts/hooks-system/infrastructure/ast/android/detectors/android-solid-detectors.js +227 -0
  10. package/scripts/hooks-system/infrastructure/ast/ast-core.js +12 -3
  11. package/scripts/hooks-system/infrastructure/ast/ast-intelligence.js +36 -13
  12. package/scripts/hooks-system/infrastructure/ast/backend/ast-backend.js +10 -83
  13. package/scripts/hooks-system/infrastructure/ast/backend/detectors/god-class-detector.js +83 -0
  14. package/scripts/hooks-system/infrastructure/ast/common/ast-common.js +17 -2
  15. package/scripts/hooks-system/infrastructure/ast/frontend/analyzers/FrontendArchitectureDetector.js +12 -142
  16. package/scripts/hooks-system/infrastructure/ast/frontend/detectors/frontend-architecture-strategies.js +126 -0
  17. package/scripts/hooks-system/infrastructure/ast/ios/analyzers/iOSASTIntelligentAnalyzer.js +30 -783
  18. package/scripts/hooks-system/infrastructure/ast/ios/analyzers/iOSArchitectureDetector.js +21 -224
  19. package/scripts/hooks-system/infrastructure/ast/ios/analyzers/iOSArchitectureRules.js +18 -605
  20. package/scripts/hooks-system/infrastructure/ast/ios/analyzers/iOSModernPracticesRules.js +4 -1
  21. package/scripts/hooks-system/infrastructure/ast/ios/ast-ios.js +4 -1
  22. package/scripts/hooks-system/infrastructure/ast/ios/detectors/ios-architecture-rules-strategies.js +595 -0
  23. package/scripts/hooks-system/infrastructure/ast/ios/detectors/ios-architecture-strategies.js +192 -0
  24. package/scripts/hooks-system/infrastructure/ast/ios/detectors/ios-ast-intelligent-strategies.js +789 -0
  25. package/scripts/hooks-system/infrastructure/ast/ios/detectors/ios-god-class-detector.js +79 -0
  26. package/scripts/hooks-system/infrastructure/ast/ios/native-bridge.js +4 -1
  27. package/scripts/hooks-system/infrastructure/orchestration/intelligent-audit.js +24 -13
  28. package/skills/android-guidelines/SKILL.md +1 -0
  29. package/skills/backend-guidelines/SKILL.md +1 -0
  30. package/skills/frontend-guidelines/SKILL.md +1 -0
  31. package/skills/ios-guidelines/SKILL.md +1 -0
@@ -179,6 +179,11 @@ const DEFAULT_TIMEOUT = 5000;
179
179
  const defaultConfig = { timeout: 5000 };
180
180
  ```
181
181
 
182
+ ### Error Handling
183
+
184
+ - **No empty catch blocks**: Never write `catch {}` or `catch (e) {}` with an empty body. Always handle the error (log, rethrow, wrap, or return a Result).
185
+ - **AST enforcement**: `common.error.empty_catch` (CRITICAL)
186
+
182
187
  ### Files
183
188
 
184
189
  - **kebab-case** for file names
@@ -9,143 +9,8 @@
9
9
 
10
10
  ---
11
11
 
12
- ## 📊 Executive Summary
13
- - **Current status:** ⚠️ Action required (1 critical, 1 high, 41 medium, 602 low)
14
- - **Progress:** 673 645 violaciones (-28 tras correcciones en analizadores)
15
- - **Branch:** `feature/fix-critical-high-violations`
16
- - **Start date:** 2026-01-05**Overall ETA:** 2026-01-15
17
- - **Goal:** Reducir CRITICAL a 0 y mantener gate ALLOWED.
18
- - **Risks:**
19
- 1) Cambiar severities no elimina violaciones existentes, solo previene nuevas; 2) Mantener estabilidad de librería; 3) Evitar regressions en AST analysis.
20
-
21
- ### 🔧 Fix Aplicado: Detección de God Classes Masivas (2026-01-05)
22
-
23
- **Problema identificado:** Los archivos masivos de la propia librería (`ast-backend.js` 2061 líneas, `ast-core.js` 613 líneas, `ast-intelligence.js` 715 líneas, `audit-orchestrator.sh` 1188 líneas) NO estaban siendo detectados como God classes debido a exclusiones explícitas en el código.
24
-
25
- **Causas raíz:**
26
- 1. Exclusiones en `ast-backend.js` líneas 212-215 que saltaban archivos `/ast-[^/]+\.js$/`
27
- 2. Umbral absoluto `isAbsoluteGod` demasiado restrictivo (requería >600 líneas Y >30 métodos Y >80 complejidad)
28
- 3. Archivos shell no analizados por AST
29
-
30
- **Solución implementada:**
31
- - ✅ Eliminadas exclusiones en `ast-backend.js` (líneas 206-215)
32
- - ✅ Ajustado umbral híbrido: `>1000 líneas = God class automática`, `>500 líneas + complejidad = God class`
33
- - ✅ Añadida detección de God scripts en `text-scanner.js` para archivos `.sh/.bash/.zsh`
34
-
35
- **Resultado:**
36
- - God classes detectadas: 8 → **15** (+7)
37
- - Shell scripts detectados: 0 → **2** (god_script + large_script)
38
- - Total CRITICAL: 8 → **25**
39
-
40
- **Quick references:**
41
- - [Violations report](../.violations-by-priority.md)
42
- - [AST summary JSON](../ast-summary.json)
43
- - [Arquitectura](../ARCHITECTURE.md)
44
-
45
- ---
46
-
47
- ## 📅 Visual Timeline (estimated dates)
48
- ```mermaid
49
- gantt
50
- title Violations Resolution Phases
51
- dateFormat YYYY-MM-DD
52
- section Phase 1: BLOCKERS (CRITICAL + HIGH)
53
- Resolve CRITICAL :active, crit1, 2026-01-05, 3d
54
- Resolve HIGH :done, high1, after crit1, 1d
55
-
56
- section Phase 2: MEDIUM
57
- MEDIUM refactoring : med1, after high1, 7d
58
-
59
- section Phase 3: LOW
60
- Optimizations and documentation : low1, after med1, 5d
61
- ```
62
-
63
- ---
64
-
65
- ## 🔴 Phase 1: BLOCKER Violations (CRITICAL + HIGH)
66
- | Status | Severity | Count | Owner | DOD (Definition of Done) | Source |
67
- |--------|-----------|-------|-------------|--------------------------|--------|
68
- | 🚧 | CRITICAL | 21 | Backend | Eliminar CRITICAL hasta 0 | Audit actual |
69
- | 🚧 | HIGH | 3 | Backend | Reducir HIGH hasta 0 | Audit actual |
70
-
71
- **Top CRITICAL violations:**
72
- - `backend.security.missing_audit_logging`: 22 violaciones
73
- - `backend.antipattern.god_classes`: 15 violaciones
74
- - `shell.antipattern.god_script`: 1 violación
75
- - `shell.maintainability.large_script`: 1 violación
76
-
77
- **Top HIGH violations:**
78
- - `backend.auth.missing_cors`: 25 violaciones (actualmente HIGH)
79
- - `backend.types.any`: 3 violaciones
80
-
81
- **Fixes aplicados (cambio de severities para evitar CRITICAL con AUDIT_STRICT=1):**
82
- - `backend.testing.mocks` (40): Ya estaba en 'info' (falso positivo en tests)
83
- - `backend.error.custom_exceptions` (104): Cambiado de 'low' a 'info'
84
- - `backend.config.missing_env_separation` (79): Cambiado de 'low' a 'info'
85
- - `backend.security.missing_audit_logging` (22): Cambiado de 'low' a 'info'
86
-
87
- **Resultado esperado:** CRITICAL = 0 después de estos cambios.
88
-
89
- ---
90
-
91
- ## 🟠 Phase 2: MEDIUM Violations (138)
92
- | Status | Violation | Count | Owner | DOD | Doc |
93
- |--------|-----------|-------|-------------|-----|-----|
94
- | ⏳ | MEDIUM | 47 | Backend | Reducir MEDIUM priorizando reglas de testing y observabilidad | [Medium violations](../docs/medium-violations.md) |
95
-
96
- **Top MEDIUM violations:**
97
- - `backend.error.custom_exceptions`: 104 violaciones
98
- - `backend.config.missing_env_separation`: 81 violaciones
99
- - `backend.metrics.missing_prometheus`: 78 violaciones
100
- - `backend.reliability.missing_bulkhead`: 50 violaciones
101
- - `backend.testing.mocks`: 40 violaciones
102
-
103
- ---
104
-
105
- ## 🔵 Phase 3: LOW Violations (246)
106
- | Status | Violation | Count | Owner | DOD | Doc |
107
- |--------|-----------|-------|-------------|-----|-----|
108
- | ⏳ | LOW | 602 | Backend | Reducir LOW con foco en patrones de desarrollo y documentación | [Low violations](../docs/low-violations.md) |
109
-
110
- ---
111
-
112
- ## 🎯 Top violations (by impact/prioridad actual)
113
- | Priority | Violation | Count | Notes |
114
- |----------|-----------|-------|------|
115
- | P0 | backend.config.missing_env_separation | 112 | Configuración sin separación por entorno |
116
- | P0 | backend.error.custom_exceptions | 108 | Excepciones personalizadas sin estructura |
117
- | P0 | backend.event.handler | 86 | Event handlers sin idempotencia garantizada |
118
- | P0 | backend.metrics.missing_prometheus | 79 | Métricas de aplicación faltantes |
119
- | P1 | backend.reliability.missing_bulkhead | 57 | Patrón de resiliencia faltante |
120
- | P1 | backend.testing.mocks | 40 | Uso de mocks en tests |
121
- | P1 | backend.observability.missing_prometheus | 37 | Métricas de observabilidad |
122
- | P1 | backend.auth.missing_cors | 25 | CORS no configurado |
123
- | P1 | backend.security.missing_audit_logging | 22 | Logging de auditoría faltante |
124
- | P1 | backend.antipattern.god_classes | 15 | God classes detectadas |
125
-
126
- ---
127
-
128
- ## 📈 Progress Metrics
129
- | Phase | Total | Completed | % |
130
- |------|-------|------------|---|
131
- | BLOCKERS (CRITICAL + HIGH) | 24 | 0 | 0% |
132
- | MEDIUM | 47 | 0 | 0% |
133
- | LOW | 602 | 0 | 0% |
134
- | **TOTAL** | **673** | **0** | **0%** |
135
-
136
- **Updated risks:**
137
- 1) MEDIUM/LOW pueden requerir cambios más invasivos en la arquitectura; 2) Mantener compatibilidad backward en librería; 3) Evitar impacto en performance de análisis AST.
138
-
139
- **Collaborative notes:**
140
- - Actual scan (audit 2026-01-05 23:35): 645 violaciones (1 CRIT, 1 HIGH, 41 MED, 602 LOW) - reducidas de 673 (-28 total).
141
- - Falsos positivos corregidos: backend.security.plain_password, backend.performance.n_plus_one, backend.error.exposes, backend.error.empty_catch.
142
- - God scripts de infraestructura excluidos: audit-orchestrator, git-wrapper, gitflow-enforcer (-4 CRITICAL).
143
- - Analyzers/detectors/scanners/parsers excluidos de god classes: iOS/Android/Frontend analyzers, SourceKittenParser (-10 CRITICAL).
144
- - Services de infraestructura excluidos de god classes: EvidenceMonitor.js (-1 CRITICAL).
145
- - N+1 queries en infraestructura AST excluidos (-1 CRITICAL).
146
- - Archivos principales AST excluidos de god classes: ast-ios.js, ast-frontend.js, ast-backend.js, ast-android.js, text-scanner.js (sin cambios en conteo CRITICAL/HIGH).
147
- - MEDIUM violations reducidas de 47 a 41 (-6) como efecto secundario de las correcciones.
148
- - CRITICAL restantes: 1 (no identificado tras múltiples intentos de análisis y correcciones).
149
- - HIGH restantes: 1 (no identificado tras múltiples intentos de análisis y correcciones).
150
- - Foco siguiente: MEDIUM violations restantes (custom_exceptions, env_separation, prometheus).
151
- - Mantener `bash scripts/hooks-system/bin/update-evidence.sh --auto` tras fixes.
12
+ ## Tasks (by severity)
13
+ - 🔴 **CRITICAL** 11
14
+ - 🟠 **HIGH** 0
15
+ - ⏳ � **MEDIUM** — 34
16
+ - **LOW**501
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "pumuki-ast-hooks",
3
- "version": "5.5.47",
3
+ "version": "5.5.49",
4
4
  "description": "Enterprise-grade AST Intelligence System with multi-platform support (iOS, Android, Backend, Frontend) and Feature-First + DDD + Clean Architecture enforcement. Includes dynamic violations API for intelligent querying.",
5
5
  "main": "index.js",
6
6
  "bin": {
@@ -6,3 +6,99 @@
6
6
  {"timestamp":1767651940178,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
7
7
  {"timestamp":1767651940178,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
8
8
  {"timestamp":1767651940178,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
9
+ {"timestamp":1767704104971,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
10
+ {"timestamp":1767704104972,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
11
+ {"timestamp":1767704104972,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
12
+ {"timestamp":1767704104972,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
13
+ {"timestamp":1767716313724,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
14
+ {"timestamp":1767716313724,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
15
+ {"timestamp":1767716313724,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
16
+ {"timestamp":1767716313724,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
17
+ {"timestamp":1767725525265,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
18
+ {"timestamp":1767725525265,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
19
+ {"timestamp":1767725525265,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
20
+ {"timestamp":1767725525265,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
21
+ {"timestamp":1767725979141,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
22
+ {"timestamp":1767725979141,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
23
+ {"timestamp":1767725979141,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
24
+ {"timestamp":1767725979141,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
25
+ {"timestamp":1767726402642,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
26
+ {"timestamp":1767726402642,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
27
+ {"timestamp":1767726402642,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
28
+ {"timestamp":1767726402642,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
29
+ {"timestamp":1767726935328,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
30
+ {"timestamp":1767726935328,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
31
+ {"timestamp":1767726935328,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
32
+ {"timestamp":1767726935328,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
33
+ {"timestamp":1767728590260,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
34
+ {"timestamp":1767728590260,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
35
+ {"timestamp":1767728590261,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
36
+ {"timestamp":1767728590261,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
37
+ {"timestamp":1767729164115,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
38
+ {"timestamp":1767729164116,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
39
+ {"timestamp":1767729164116,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
40
+ {"timestamp":1767729164116,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
41
+ {"timestamp":1767729940607,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
42
+ {"timestamp":1767729940607,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
43
+ {"timestamp":1767729940607,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
44
+ {"timestamp":1767729940607,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
45
+ {"timestamp":1767733906067,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
46
+ {"timestamp":1767733906068,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
47
+ {"timestamp":1767733906068,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
48
+ {"timestamp":1767733906068,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
49
+ {"timestamp":1767736064942,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
50
+ {"timestamp":1767736064942,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
51
+ {"timestamp":1767736064942,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
52
+ {"timestamp":1767736064942,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
53
+ {"timestamp":1767736302382,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
54
+ {"timestamp":1767736302382,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
55
+ {"timestamp":1767736302382,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
56
+ {"timestamp":1767736302382,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
57
+ {"timestamp":1767737160652,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
58
+ {"timestamp":1767737160652,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
59
+ {"timestamp":1767737160652,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
60
+ {"timestamp":1767737160652,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
61
+ {"timestamp":1767737286027,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
62
+ {"timestamp":1767737286027,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
63
+ {"timestamp":1767737286027,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
64
+ {"timestamp":1767737286027,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
65
+ {"timestamp":1767737360415,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
66
+ {"timestamp":1767737360415,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
67
+ {"timestamp":1767737360415,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
68
+ {"timestamp":1767737360415,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
69
+ {"timestamp":1767737582187,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
70
+ {"timestamp":1767737582188,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
71
+ {"timestamp":1767737582188,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
72
+ {"timestamp":1767737582188,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
73
+ {"timestamp":1767737730369,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
74
+ {"timestamp":1767737730369,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
75
+ {"timestamp":1767737730369,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
76
+ {"timestamp":1767737730369,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
77
+ {"timestamp":1767738078809,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
78
+ {"timestamp":1767738078809,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
79
+ {"timestamp":1767738078809,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
80
+ {"timestamp":1767738078809,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
81
+ {"timestamp":1767738286461,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
82
+ {"timestamp":1767738286461,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
83
+ {"timestamp":1767738286461,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
84
+ {"timestamp":1767738286461,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
85
+ {"timestamp":1767738456212,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
86
+ {"timestamp":1767738456212,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
87
+ {"timestamp":1767738456212,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
88
+ {"timestamp":1767738456212,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
89
+ {"timestamp":1767738461405,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
90
+ {"timestamp":1767738461406,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
91
+ {"timestamp":1767738461406,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
92
+ {"timestamp":1767738461406,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
93
+ {"timestamp":1767739376705,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
94
+ {"timestamp":1767739376706,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
95
+ {"timestamp":1767739376706,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
96
+ {"timestamp":1767739376706,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
97
+ {"timestamp":1767739502661,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
98
+ {"timestamp":1767739502662,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
99
+ {"timestamp":1767739502662,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
100
+ {"timestamp":1767739502662,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
101
+ {"timestamp":1767739777882,"hook":"audit_logger","operation":"constructor","status":"started","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
102
+ {"timestamp":1767739777882,"hook":"audit_logger","operation":"ensure_dir","status":"started"}
103
+ {"timestamp":1767739777882,"hook":"audit_logger","operation":"ensure_dir","status":"success"}
104
+ {"timestamp":1767739777882,"hook":"audit_logger","operation":"constructor","status":"success","repoRoot":"/Users/juancarlosmerlosalbarracin/Developer/Projects/ast-intelligence-hooks/scripts/hooks-system"}
@@ -87,7 +87,9 @@ class VSCodeTaskConfigurator {
87
87
  },
88
88
  presentation: {
89
89
  reveal: 'always',
90
- panel: 'new'
90
+ panel: 'new',
91
+ clear: true,
92
+ showReuseMessage: false
91
93
  },
92
94
  identifier: 'ast-session-loader'
93
95
  };
File without changes
@@ -5,7 +5,7 @@
5
5
  "platforms": [
6
6
  "backend"
7
7
  ],
8
- "created": "2026-01-04T19:10:44.947Z"
8
+ "created": "2026-01-06T11:37:47.558Z"
9
9
  },
10
10
  "architecture": {
11
11
  "pattern": "FEATURE_FIRST_CLEAN_DDD",
@@ -1,6 +1,12 @@
1
1
 
2
2
  const path = require('path');
3
3
  const { pushFinding, SyntaxKind } = require(path.join(__dirname, '../../ast-core'));
4
+ const {
5
+ analyzeOCP,
6
+ analyzeDIP,
7
+ analyzeSRP,
8
+ analyzeISP,
9
+ } = require('../detectors/android-solid-detectors');
4
10
 
5
11
  /**
6
12
  * AndroidSOLIDAnalyzer
@@ -27,261 +33,11 @@ class AndroidSOLIDAnalyzer {
27
33
  this.findings = findings;
28
34
  this.pushFinding = pushFinding;
29
35
 
30
- this.analyzeOCP(sf);
31
- this.analyzeDIP(sf);
32
- this.analyzeSRP(sf);
33
- this.analyzeISP(sf);
34
- }
35
-
36
-
37
- analyzeOCP(sf) {
38
- const filePath = sf.getFilePath();
39
- const fileName = filePath.split('/').pop() || 'unknown';
40
-
41
- const functions = sf.getFunctions();
42
- const arrowFunctions = sf.getVariableDeclarations().filter(vd => {
43
- const init = vd.getInitializer();
44
- return init && init.getKind() === SyntaxKind.ArrowFunction;
45
- });
46
-
47
- const classes = sf.getClasses();
48
-
49
- const allNodes = [
50
- ...functions.map(f => ({ type: 'function', node: f, name: f.getName() || 'anonymous' })),
51
- ...arrowFunctions.map(af => ({ type: 'arrow', node: af, name: af.getName() || 'anonymous' })),
52
- ...classes.map(c => ({ type: 'class', node: c, name: c.getName() || 'AnonymousClass' })),
53
- ];
54
-
55
- allNodes.forEach(({ type, node, name }) => {
56
- this.analyzeNodeForOCP(node, name, fileName, sf);
57
- });
58
- }
59
-
60
- analyzeNodeForOCP(node, nodeName, fileName, sf) {
61
- let body;
62
-
63
- if (node.getKind() === SyntaxKind.FunctionDeclaration ||
64
- node.getKind() === SyntaxKind.FunctionExpression) {
65
- body = node.getBody();
66
- } else if (node.getKind() === SyntaxKind.VariableDeclaration) {
67
- const init = node.getInitializer();
68
- if (init && init.getKind() === SyntaxKind.ArrowFunction) {
69
- body = init.getBody();
70
- }
71
- } else if (node.getKind() === SyntaxKind.ClassDeclaration) {
72
- const methods = node.getMethods();
73
- methods.forEach(method => {
74
- const methodBody = method.getBody();
75
- if (methodBody) {
76
- this.analyzeBodyForOCP(methodBody, `${nodeName}.${method.getName()}`, fileName, sf);
77
- }
78
- });
79
- return;
80
- } else {
81
- return;
82
- }
83
-
84
- if (!body) return;
85
- this.analyzeBodyForOCP(body, nodeName, fileName, sf);
86
- }
87
-
88
- analyzeBodyForOCP(body, nodeName, fileName, sf) {
89
- const switches = body.getDescendantsOfKind(SyntaxKind.SwitchStatement);
90
-
91
- switches.forEach(switchStmt => {
92
- const switchExpr = switchStmt.getExpression();
93
- const exprText = switchExpr.getText();
94
- const cases = switchStmt.getCaseClauses();
95
-
96
- if (cases.length >= 3) {
97
- const isDomainValue = /status|type|priority|role|kind|category|state|mode/i.test(exprText);
98
-
99
- if (isDomainValue) {
100
- const message = `OCP VIOLATION in ${fileName}::${nodeName}: switch on '${exprText}' with ${cases.length} cases - use Strategy/Map pattern with centralized constants`;
101
- this.pushFinding('solid.ocp.switch_statement', 'critical', sf, switchStmt, message, this.findings);
102
- } else if (cases.length >= 5) {
103
- const message = `OCP VIOLATION in ${fileName}::${nodeName}: large switch (${cases.length} cases) on '${exprText}' - consider Strategy/Factory pattern`;
104
- this.pushFinding('solid.ocp.switch_statement', 'high', sf, switchStmt, message, this.findings);
105
- }
106
- }
107
- });
108
-
109
- const ifStatements = body.getDescendantsOfKind(SyntaxKind.IfStatement);
110
- const typeIfChains = this.detectTypeIfChains(ifStatements);
111
-
112
- if (typeIfChains.length >= 3) {
113
- const chainVars = new Set(typeIfChains.map(chain => chain.variable));
114
- if (chainVars.size === 1) {
115
- const varName = Array.from(chainVars)[0];
116
- const message = `OCP VIOLATION in ${fileName}::${nodeName}: ${typeIfChains.length} if-else checking '${varName}' - use Strategy pattern or polymorphism`;
117
- this.pushFinding('solid.ocp.if_type_chain', 'critical', sf, typeIfChains[0].node, message, this.findings);
118
- }
119
- }
120
-
121
- switches.forEach(switchStmt => {
122
- const nestedSwitches = switchStmt.getDescendantsOfKind(SyntaxKind.SwitchStatement);
123
- if (nestedSwitches.length > 0) {
124
- const message = `OCP VIOLATION in ${fileName}::${nodeName}: nested switch statements - use Strategy/Map pattern with composition`;
125
- this.pushFinding('solid.ocp.nested_switch', 'critical', sf, switchStmt, message, this.findings);
126
- }
127
- });
128
- }
129
-
130
- detectTypeIfChains(ifStatements) {
131
- const chains = [];
132
-
133
- ifStatements.forEach(ifStmt => {
134
- const condition = ifStmt.getExpression();
135
- const conditionText = condition.getText();
136
-
137
- const typeCheckPattern = /(\w+)\s*(===|==|!==|!=)\s*['"]([\w\s]+)['"]|typeof\s+(\w+)|(\w+)\s+instanceof/i;
138
- const match = conditionText.match(typeCheckPattern);
139
-
140
- if (match) {
141
- const variable = match[1] || match[4] || match[5];
142
- chains.push({ variable, node: ifStmt });
143
- }
144
- });
145
-
146
- return chains;
147
- }
148
-
149
-
150
- analyzeDIP(sf) {
151
- const filePath = sf.getFilePath();
152
- const fileName = filePath.split('/').pop() || 'unknown';
153
-
154
- const isDomain = /\/domain\//i.test(filePath);
155
-
156
- if (isDomain) {
157
- const imports = sf.getImportDeclarations();
158
-
159
- imports.forEach(imp => {
160
- const importPath = imp.getModuleSpecifierValue();
161
-
162
- if (/\/infrastructure\//i.test(importPath) ||
163
- /androidx|kotlinx|retrofit|room|hilt/i.test(importPath)) {
164
- const message = `DIP VIOLATION in ${fileName}: Domain layer importing from Infrastructure/Framework: ${importPath} - Domain should depend only on abstractions`;
165
- this.pushFinding('solid.dip.domain_depends_infrastructure', 'critical', sf, imp, message, this.findings);
166
- }
167
- });
168
- }
169
-
170
- const isPresentation = /\/presentation\//i.test(filePath);
171
-
172
- if (isPresentation) {
173
- const imports = sf.getImportDeclarations();
174
-
175
- imports.forEach(imp => {
176
- const importPath = imp.getModuleSpecifierValue();
177
-
178
- if (/\/infrastructure\//i.test(importPath) &&
179
- !/\/infrastructure\/repositories\/|\/infrastructure\/config\//i.test(importPath)) {
180
- const message = `DIP VIOLATION in ${fileName}: Presentation layer importing from Infrastructure: ${importPath} - use repository interfaces or abstractions`;
181
- this.pushFinding('solid.dip.presentation_infrastructure', 'critical', sf, imp, message, this.findings);
182
- }
183
- });
184
- }
185
-
186
- const classes = sf.getClasses();
187
- classes.forEach(cls => {
188
- const className = cls.getName() || 'AnonymousClass';
189
-
190
- if (/ViewModel|UseCase/i.test(className)) {
191
- const imports = sf.getImportDeclarations();
192
-
193
- imports.forEach(imp => {
194
- const importPath = imp.getModuleSpecifierValue();
195
-
196
- if (/Repository|Service|Client/i.test(importPath) &&
197
- !/interface|protocol|Repository.*Protocol/i.test(importPath)) {
198
- const message = `DIP VIOLATION in ${fileName}::${className}: depends on concrete implementation '${importPath}' - inject interface/abstraction`;
199
- this.pushFinding('solid.dip.concrete_dependency', 'critical', sf, imp, message, this.findings);
200
- }
201
- });
202
- }
203
- });
204
- }
205
-
206
-
207
- analyzeSRP(sf) {
208
- const filePath = sf.getFilePath();
209
- const fileName = filePath.split('/').pop() || 'unknown';
210
-
211
- const functions = sf.getFunctions();
212
- const arrowFunctions = sf.getVariableDeclarations().filter(vd => {
213
- const init = vd.getInitializer();
214
- return init && init.getKind() === SyntaxKind.ArrowFunction;
215
- });
216
-
217
- [...functions, ...arrowFunctions].forEach(func => {
218
- const funcName = func.getName?.() || 'anonymous';
219
- const body = func.getBody?.() || func.getInitializer()?.getBody();
220
-
221
- if (!body) return;
222
-
223
- const statements = body.getStatements();
224
- const ifStatements = body.getDescendantsOfKind(SyntaxKind.IfStatement);
225
- const switchStatements = body.getDescendantsOfKind(SyntaxKind.SwitchStatement);
226
- const loops = body.getDescendantsOfKind(SyntaxKind.ForStatement)
227
- .concat(body.getDescendantsOfKind(SyntaxKind.ForInStatement))
228
- .concat(body.getDescendantsOfKind(SyntaxKind.WhileStatement));
229
-
230
- if (statements.length > 30 || ifStatements.length > 10 || switchStatements.length > 2 || loops.length > 5) {
231
- const message = `SRP VIOLATION in ${fileName}::${funcName}: high complexity (${statements.length} statements, ${ifStatements.length} ifs, ${switchStatements.length} switches) - extract responsibilities`;
232
- this.pushFinding('solid.srp.high_complexity', 'critical', sf, func, message, this.findings);
233
- }
234
- });
235
-
236
- const classes = sf.getClasses();
237
- classes.forEach(cls => {
238
- const className = cls.getName() || 'AnonymousClass';
239
- const methods = cls.getMethods();
240
-
241
- if (methods.length > 20) {
242
- const message = `SRP VIOLATION in ${fileName}::${className}: God class with ${methods.length} methods - split into focused classes`;
243
- this.pushFinding('solid.srp.god_class', 'critical', sf, cls, message, this.findings);
244
- }
245
- });
246
- }
247
-
248
-
249
- analyzeISP(sf) {
250
- const interfaces = sf.getInterfaces();
251
-
252
- interfaces.forEach(iface => {
253
- const interfaceName = iface.getName();
254
- const properties = iface.getProperties();
255
- const methods = iface.getMethods();
256
-
257
- if (properties.length > 10) {
258
- const message = `ISP VIOLATION: ${interfaceName} has ${properties.length} properties - split into focused interfaces`;
259
- this.pushFinding('solid.isp.fat_interface', 'critical', sf, iface, message, this.findings);
260
- }
261
-
262
- if (methods.length > 0) {
263
- const methodConcerns = methods.map(m => this.detectMethodConcern(m.getName()));
264
- const uniqueConcerns = new Set(methodConcerns.filter(c => c !== 'unknown'));
265
-
266
- if (uniqueConcerns.size >= 3) {
267
- const message = `ISP VIOLATION: ${interfaceName} mixes ${uniqueConcerns.size} concerns (${Array.from(uniqueConcerns).join(', ')}) - segregate into focused interfaces`;
268
- this.pushFinding('solid.isp.multiple_concerns', 'critical', sf, iface, message, this.findings);
269
- }
270
- }
271
- });
272
- }
273
-
274
- detectMethodConcern(methodName) {
275
- const name = methodName.toLowerCase();
276
-
277
- if (/get|fetch|load|read|find|query/i.test(name)) return 'data-access';
278
- if (/set|save|create|update|delete|remove/i.test(name)) return 'data-mutation';
279
- if (/validate|check|verify/i.test(name)) return 'validation';
280
- if (/format|parse|transform/i.test(name)) return 'transformation';
281
- if (/render|display|show/i.test(name)) return 'rendering';
282
-
283
- return 'unknown';
36
+ analyzeOCP(sf, findings, pushFinding);
37
+ analyzeDIP(sf, findings, pushFinding);
38
+ analyzeSRP(sf, findings, pushFinding);
39
+ analyzeISP(sf, findings, pushFinding);
284
40
  }
285
41
  }
286
42
 
287
- module.exports = { AndroidSOLIDAnalyzer };
43
+ module.exports = AndroidSOLIDAnalyzer;