@devlens/core 2.0.0 → 2.0.1
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 +132 -17
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,6 +1,21 @@
|
|
|
1
1
|
# @devlens/core
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
**Stop wasting 30 minutes hunting silent failures. DevLens finds them for you -- automatically.**
|
|
4
|
+
|
|
5
|
+
Your UI renders blank. No error in console. You add `console.log` everywhere until you discover `user.profile.settings` is `undefined` because the API silently returned a 500. Sound familiar?
|
|
6
|
+
|
|
7
|
+
DevLens detects these failures the moment they happen and tells you exactly what went wrong, where, and how to fix it.
|
|
8
|
+
|
|
9
|
+
## What It Catches
|
|
10
|
+
|
|
11
|
+
| Category | What It Detects | Example |
|
|
12
|
+
|----------|----------------|---------|
|
|
13
|
+
| **Network** | Failed API calls, 4xx/5xx responses, timeouts | `POST /api/users returned 500` |
|
|
14
|
+
| **Null Access** | Property access on null objects | `user.profile.avatar is null` |
|
|
15
|
+
| **Undefined Data** | Accessing undefined properties | `settings.theme is undefined` |
|
|
16
|
+
| **Render Data** | State values your UI depends on that are nullish | `"posts" is undefined in Dashboard` |
|
|
17
|
+
| **Unhandled Errors** | Uncaught exceptions and promise rejections | `TypeError: Cannot read property...` |
|
|
18
|
+
| **Type Mismatch** | Unexpected data types at runtime | `Expected string, got number` |
|
|
4
19
|
|
|
5
20
|
## Installation
|
|
6
21
|
|
|
@@ -8,7 +23,7 @@ Automatic runtime error detection for JavaScript applications. Detects API failu
|
|
|
8
23
|
npm install @devlens/core
|
|
9
24
|
```
|
|
10
25
|
|
|
11
|
-
## Quick Start
|
|
26
|
+
## Quick Start -- 4 Lines to Full Coverage
|
|
12
27
|
|
|
13
28
|
```ts
|
|
14
29
|
import {
|
|
@@ -18,22 +33,28 @@ import {
|
|
|
18
33
|
createDataGuardian,
|
|
19
34
|
} from '@devlens/core';
|
|
20
35
|
|
|
36
|
+
// 1. Create the engine
|
|
21
37
|
const engine = createDetectionEngine();
|
|
22
38
|
|
|
39
|
+
// 2. Auto-detect failed API calls (fetch + XHR)
|
|
23
40
|
const network = createNetworkInterceptor(engine);
|
|
24
41
|
network.install();
|
|
25
42
|
|
|
43
|
+
// 3. Catch uncaught errors + unhandled promise rejections
|
|
26
44
|
const catcher = createGlobalCatcher(engine);
|
|
27
45
|
catcher.install();
|
|
28
46
|
|
|
47
|
+
// 4. Detect null/undefined property access on any object
|
|
29
48
|
const guardian = createDataGuardian(engine);
|
|
30
49
|
const data = guardian.guard(apiResponse, 'apiResponse');
|
|
31
50
|
|
|
32
|
-
//
|
|
51
|
+
// Now this silently-failing access gets logged with full context:
|
|
33
52
|
console.log(data.user.profile.avatar);
|
|
34
53
|
```
|
|
35
54
|
|
|
36
|
-
## Console
|
|
55
|
+
## What You See in Console
|
|
56
|
+
|
|
57
|
+
Instead of silence or a cryptic error, DevLens gives you:
|
|
37
58
|
|
|
38
59
|
```
|
|
39
60
|
[NET] DevLens [ERROR] network: POST /api/users returned 500 Internal Server Error
|
|
@@ -41,27 +62,121 @@ console.log(data.user.profile.avatar);
|
|
|
41
62
|
|- Duration: 1234ms
|
|
42
63
|
|- Suggestion: Server returned 500 -- check server logs
|
|
43
64
|
\- Source: NetworkInterceptor
|
|
65
|
+
|
|
66
|
+
[NULL] DevLens [WARN] null-access: Property "avatar" is null at path "user.profile.avatar"
|
|
67
|
+
|- Path: user.profile.avatar
|
|
68
|
+
|- Value: null
|
|
69
|
+
|- Source: UserProfile
|
|
70
|
+
\- Suggestion: Check if "avatar" is loaded/initialized before accessing
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
Every issue includes: **what** happened, **where** it happened, the actual **value** found, and a **suggestion** to fix it.
|
|
74
|
+
|
|
75
|
+
## Configuration
|
|
76
|
+
|
|
77
|
+
```ts
|
|
78
|
+
const engine = createDetectionEngine({
|
|
79
|
+
enabled: true, // auto-disabled in production
|
|
80
|
+
minSeverity: 'warn', // 'error' | 'warn' | 'info'
|
|
81
|
+
throttleMs: 1000, // prevent log spam
|
|
82
|
+
maxIssues: 100, // memory buffer limit
|
|
83
|
+
modules: {
|
|
84
|
+
network: {
|
|
85
|
+
fetch: true, // intercept fetch()
|
|
86
|
+
xhr: true, // intercept XMLHttpRequest
|
|
87
|
+
ignoreUrls: ['/health', /\.hot-update\./],
|
|
88
|
+
logSuccess: false, // only log failures
|
|
89
|
+
},
|
|
90
|
+
guardian: {
|
|
91
|
+
maxDepth: 5, // proxy depth limit
|
|
92
|
+
ignorePaths: ['_internal'],
|
|
93
|
+
},
|
|
94
|
+
catcher: {
|
|
95
|
+
windowErrors: true, // window.onerror
|
|
96
|
+
unhandledRejections: true, // unhandled promises
|
|
97
|
+
consoleErrors: false, // console.error interception
|
|
98
|
+
},
|
|
99
|
+
},
|
|
100
|
+
ignore: {
|
|
101
|
+
urls: ['/analytics'],
|
|
102
|
+
messages: [/ResizeObserver/],
|
|
103
|
+
},
|
|
104
|
+
});
|
|
44
105
|
```
|
|
45
106
|
|
|
46
107
|
## API Reference
|
|
47
108
|
|
|
109
|
+
### Functions
|
|
110
|
+
|
|
48
111
|
| Export | Description |
|
|
49
112
|
|--------|-------------|
|
|
50
|
-
| `createDetectionEngine(config?)` | Creates the core detection
|
|
51
|
-
| `createNetworkInterceptor(engine, config?)` |
|
|
52
|
-
| `createDataGuardian(engine, config?)` | Proxy
|
|
53
|
-
| `createGlobalCatcher(engine, config?)` |
|
|
54
|
-
| `createConsoleReporter()` | Formatted console output |
|
|
113
|
+
| `createDetectionEngine(config?)` | Creates the core engine that coordinates all detection modules |
|
|
114
|
+
| `createNetworkInterceptor(engine, config?)` | Intercepts `fetch()` and `XMLHttpRequest` to detect API failures |
|
|
115
|
+
| `createDataGuardian(engine, config?)` | Wraps objects in ES6 Proxy to detect null/undefined property access |
|
|
116
|
+
| `createGlobalCatcher(engine, config?)` | Captures `window.onerror` and unhandled promise rejections |
|
|
117
|
+
| `createConsoleReporter()` | Formatted console output with severity colors and structured details |
|
|
118
|
+
|
|
119
|
+
### Types
|
|
120
|
+
|
|
121
|
+
| Export | Description |
|
|
122
|
+
|--------|-------------|
|
|
123
|
+
| `DetectedIssue` | Full issue object with id, severity, category, message, path, suggestion, stack |
|
|
124
|
+
| `DevLensConfig` | Engine configuration |
|
|
125
|
+
| `DevLensEngine` | Engine instance interface (report, subscribe, getIssues, isEnabled) |
|
|
126
|
+
| `Reporter` | Custom reporter interface -- implement to send issues anywhere |
|
|
127
|
+
| `Severity` | `'error' \| 'warn' \| 'info'` |
|
|
128
|
+
| `IssueCategory` | `'network' \| 'null-access' \| 'undefined-data' \| 'render-data' \| ...` |
|
|
129
|
+
| `NetworkInterceptorConfig` | Network module config |
|
|
130
|
+
| `DataGuardianConfig` | Guardian module config |
|
|
131
|
+
| `GlobalCatcherConfig` | Catcher module config |
|
|
132
|
+
|
|
133
|
+
## Custom Reporter
|
|
134
|
+
|
|
135
|
+
Send issues to your own logging service:
|
|
136
|
+
|
|
137
|
+
```ts
|
|
138
|
+
import type { Reporter, DetectedIssue } from '@devlens/core';
|
|
139
|
+
|
|
140
|
+
const myReporter: Reporter = {
|
|
141
|
+
report(issue: DetectedIssue) {
|
|
142
|
+
fetch('/api/logs', {
|
|
143
|
+
method: 'POST',
|
|
144
|
+
body: JSON.stringify(issue),
|
|
145
|
+
});
|
|
146
|
+
},
|
|
147
|
+
};
|
|
148
|
+
|
|
149
|
+
const engine = createDetectionEngine({ reporter: myReporter });
|
|
150
|
+
```
|
|
151
|
+
|
|
152
|
+
## Framework Adapters
|
|
153
|
+
|
|
154
|
+
| Package | Framework | What It Adds |
|
|
155
|
+
|---------|-----------|-------------|
|
|
156
|
+
| [@devlens/react](https://www.npmjs.com/package/@devlens/react) | React 17+ | Provider, ErrorBoundary, guarded hooks |
|
|
157
|
+
| [@devlens/vue](https://www.npmjs.com/package/@devlens/vue) | Vue 3.3+ | Plugin, auto error/warn handlers, guarded composables |
|
|
158
|
+
| [@devlens/ui](https://www.npmjs.com/package/@devlens/ui) | Any | Visual debug panel overlay |
|
|
159
|
+
|
|
160
|
+
## Why @devlens/core
|
|
161
|
+
|
|
162
|
+
- **Zero dependencies** -- nothing to audit, nothing to break
|
|
163
|
+
- **~20KB** ESM bundle, tree-shakeable
|
|
164
|
+
- **Dual ESM + CJS** output with full TypeScript declarations
|
|
165
|
+
- **Production-safe** -- auto-disabled when `NODE_ENV === 'production'`, zero overhead
|
|
166
|
+
- **Framework-agnostic** -- works with React, Vue, Svelte, vanilla JS, anything
|
|
167
|
+
- **Pluggable** -- custom reporters, custom validators, ignore patterns
|
|
168
|
+
- **Non-invasive** -- no global state pollution, clean install/uninstall lifecycle
|
|
169
|
+
|
|
170
|
+
|
|
171
|
+
## Roadmap
|
|
55
172
|
|
|
56
|
-
|
|
173
|
+
| Version | Feature | Status |
|
|
174
|
+
|---------|---------|--------|
|
|
175
|
+
| v2.0 | Detection engine with network interceptor, data guardian, global catcher, console reporter | Current |
|
|
176
|
+
| v3.0 | AI-powered analysis -- integrate Claude and Gemini models to analyze detected issues, identify root-cause patterns across your issue history, and generate actionable fix suggestions | Planned |
|
|
57
177
|
|
|
58
|
-
|
|
59
|
-
- ~20KB ESM bundle
|
|
60
|
-
- Dual ESM + CJS output
|
|
61
|
-
- Full TypeScript declarations
|
|
62
|
-
- Production-safe -- auto-disabled when `NODE_ENV === 'production'`
|
|
63
|
-
- Tree-shakeable (`sideEffects: false`)
|
|
178
|
+
The v3.0 AI integration will analyze patterns across your detected issues, identify root causes, and suggest fixes -- directly in your dev console or UI panel.
|
|
64
179
|
|
|
65
180
|
## License
|
|
66
181
|
|
|
67
|
-
MIT -- [github.com/crashsense/devlens](https://github.com/crashsense/devlens)
|
|
182
|
+
MIT -- [GitHub](https://github.com/crashsense/devlens) -- [Changelog](https://github.com/crashsense/devlens/blob/main/CHANGELOG.md)
|