@lensjs/core 1.0.12 → 2.1.0
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 +69 -0
- package/dist/abstracts/store.cjs +23 -0
- package/dist/abstracts/store.d.cts +7 -2
- package/dist/abstracts/store.d.ts +7 -2
- package/dist/abstracts/store.js +23 -0
- package/dist/core/api_controller.cjs +47 -4
- package/dist/core/api_controller.d.cts +7 -3
- package/dist/core/api_controller.d.ts +7 -3
- package/dist/core/api_controller.js +47 -4
- package/dist/core/lens.cjs +109 -10
- package/dist/core/lens.js +110 -11
- package/dist/exception-3AZsPtAg.d.ts +52 -0
- package/dist/exception-C69UCHPk.d.cts +52 -0
- package/dist/index.cjs +301 -19
- package/dist/index.d.cts +7 -2
- package/dist/index.d.ts +7 -2
- package/dist/index.js +296 -20
- package/dist/stores/better_sqlite.cjs +40 -6
- package/dist/stores/better_sqlite.d.cts +17 -1
- package/dist/stores/better_sqlite.d.ts +17 -1
- package/dist/stores/better_sqlite.js +41 -7
- package/dist/stores/index.cjs +40 -6
- package/dist/stores/index.js +41 -7
- package/dist/types/index.cjs +2 -0
- package/dist/types/index.d.cts +49 -2
- package/dist/types/index.d.ts +49 -2
- package/dist/types/index.js +2 -0
- package/dist/ui/assets/CacheActionBadge-3t8U516j.js +1 -0
- package/dist/ui/assets/CacheEntriesTable-BqLquILg.js +1 -0
- package/dist/ui/assets/CacheEntryContainer-B86waEsR.js +2 -0
- package/dist/ui/assets/CacheEntryDetails-Dm-oXALj.js +1 -0
- package/dist/ui/assets/CacheEntryDetailsContainer-BCyXGgkx.js +2 -0
- package/dist/ui/assets/ExceptionContainer-DSQBz5cb.js +2 -0
- package/dist/ui/assets/ExceptionDetails-gmpSQ_eu.js +16 -0
- package/dist/ui/assets/ExceptionDetailsContainer-BHIz-TUv.js +2 -0
- package/dist/ui/assets/ExceptionTable-BhrX9MSS.js +1 -0
- package/dist/ui/assets/LoadMore-26PcNWcP.js +1 -0
- package/dist/ui/assets/QueriesContainer-BSF-O4s3.js +2 -0
- package/dist/ui/assets/{QueryDetailsContainer-E7P-IO7f.js → QueryDetailsContainer-BjQM9QIb.js} +15 -15
- package/dist/ui/assets/QueryTable-szgIT5Uc.js +1 -0
- package/dist/ui/assets/RequestDetails-CvQhX-2F.js +1 -0
- package/dist/ui/assets/{RequestDetailsContainer-DuDo-IqS.js → RequestDetailsContainer-XYPFJFX0.js} +2 -2
- package/dist/ui/assets/RequestsContainer-D0QPK2Ii.js +2 -0
- package/dist/ui/assets/RequetsTable-6Fqchsrt.js +1 -0
- package/dist/ui/assets/{StatusCode-FQEjz7gK.js → StatusCode-CfVCLID2.js} +1 -1
- package/dist/ui/assets/TabbedDataViewer-Cl5ednx4.js +1 -0
- package/dist/ui/assets/{Table-DYaXk80S.js → Table-CGe8JwTO.js} +2 -2
- package/dist/ui/assets/columns-BFxCubt5.js +1 -0
- package/dist/ui/assets/columns-Cw7tw3Em.js +1 -0
- package/dist/ui/assets/columns-RiCoo9Ea.js +1 -0
- package/dist/ui/assets/{index-CpP2Ap5X.js → index-BRRKsoNv.js} +1 -1
- package/dist/ui/assets/index-BzFeZyjf.css +1 -0
- package/dist/ui/assets/{index-BS8XxorB.js → index-XoJlyTFO.js} +32 -22
- package/dist/ui/assets/useCacheEntries-SCADuxKq.js +1 -0
- package/dist/ui/assets/useExceptions-BMGL3nir.js +1 -0
- package/dist/ui/assets/useLensApi-BYyiIIZR.js +1 -0
- package/dist/ui/assets/{useLoadMore-CJltToLI.js → useLoadMore-CksOcXOF.js} +1 -1
- package/dist/ui/assets/useQueries-6nYr0oG5.js +1 -0
- package/dist/ui/index.html +2 -2
- package/dist/utils/async_context.cjs +144 -0
- package/dist/utils/async_context.d.cts +13 -0
- package/dist/utils/async_context.d.ts +13 -0
- package/dist/utils/async_context.js +108 -0
- package/dist/utils/event_emitter.cjs +5 -2
- package/dist/utils/event_emitter.d.cts +8 -1
- package/dist/utils/event_emitter.d.ts +8 -1
- package/dist/utils/event_emitter.js +3 -1
- package/dist/utils/exception.cjs +130 -0
- package/dist/utils/exception.d.cts +3 -0
- package/dist/utils/exception.d.ts +3 -0
- package/dist/utils/exception.js +91 -0
- package/dist/watchers/cache_watcher.cjs +107 -0
- package/dist/watchers/cache_watcher.d.cts +11 -0
- package/dist/watchers/cache_watcher.d.ts +11 -0
- package/dist/watchers/cache_watcher.js +84 -0
- package/dist/watchers/exception_watcher.cjs +108 -0
- package/dist/watchers/exception_watcher.d.cts +10 -0
- package/dist/watchers/exception_watcher.d.ts +10 -0
- package/dist/watchers/exception_watcher.js +75 -0
- package/dist/watchers/index.cjs +81 -0
- package/dist/watchers/index.d.cts +2 -0
- package/dist/watchers/index.d.ts +2 -0
- package/dist/watchers/index.js +69 -0
- package/package.json +8 -6
- package/dist/ui/assets/QueriesContainer-CAAsjjW5.js +0 -2
- package/dist/ui/assets/QueryTable-BcrtUssT.js +0 -1
- package/dist/ui/assets/RequestDetails-C2DZBu5H.js +0 -1
- package/dist/ui/assets/RequestsContainer-DK3hQVz9.js +0 -2
- package/dist/ui/assets/RequetsTable-DgP8p60b.js +0 -1
- package/dist/ui/assets/TabbedDataViewer-cBDdPwIz.js +0 -1
- package/dist/ui/assets/index-DzNHqeKh.css +0 -1
- package/dist/ui/assets/useLensApi-DG6atd6d.js +0 -1
- package/dist/ui/assets/useQueries-C8mDDDc6.js +0 -1
package/README.md
ADDED
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
# @lensjs/core
|
|
2
|
+
|
|
3
|
+
The core library for Lens, providing the fundamental architecture for monitoring and debugging applications. It defines the abstract concepts of adapters, stores, and watchers, along with utilities for event emission, asynchronous context management, and SQL formatting. This package also includes the embedded UI for the Lens dashboard.
|
|
4
|
+
|
|
5
|
+
## Features
|
|
6
|
+
|
|
7
|
+
* **`Lens` class**: The central class for initializing Lens, setting up adapters and watchers, and starting the monitoring process.
|
|
8
|
+
* **`LensAdapter` (abstract class)**: Defines the interface for integrating Lens with different application frameworks (e.g., Express, Adonis). It handles route registration and UI serving.
|
|
9
|
+
* **`LensStore` (abstract class)**: Defines the interface for data storage, allowing Lens to persist and retrieve captured events (requests, queries, cache entries). Includes methods for saving, retrieving, and truncating data.
|
|
10
|
+
* **`LensWatcher` (abstract class)**: Defines the interface for capturing specific types of events within an application.
|
|
11
|
+
* **Concrete Watchers**:
|
|
12
|
+
* `RequestWatcher`: Captures and logs details of incoming HTTP requests.
|
|
13
|
+
* `QueryWatcher`: Captures and logs database queries.
|
|
14
|
+
* `CacheWatcher`: Captures and logs cache interactions.
|
|
15
|
+
* `ExceptionWatcher`: Captures and logs exceptions and errors.
|
|
16
|
+
* **`ApiController`**: Provides the API endpoints for the Lens UI to fetch monitoring data.
|
|
17
|
+
* **`lensEmitter`**: A global event emitter for internal communication between different parts of Lens.
|
|
18
|
+
* **`lensContext`**: Utilizes `AsyncLocalStorage` for managing asynchronous context, primarily to associate events with a specific request ID.
|
|
19
|
+
* **`lensUtils`**: A collection of utility functions, including:
|
|
20
|
+
* `generateRandomUuid`: Generates unique IDs.
|
|
21
|
+
* `interpolateQuery`: Interpolates SQL query placeholders with actual values.
|
|
22
|
+
* `formatSqlQuery`: Formats SQL queries for readability.
|
|
23
|
+
* `getMeta`: Provides `__filename` and `__dirname` in both CommonJS and ESM environments.
|
|
24
|
+
* `isStaticFile`, `stripBeforeAssetsPath`: Utilities for handling static file paths.
|
|
25
|
+
* `prepareIgnoredPaths`, `shouldIgnoreCurrentPath`: Logic for path-based filtering.
|
|
26
|
+
* `prettyHrTime`: Formats high-resolution time differences.
|
|
27
|
+
* **`BetterSqliteStore`**: A concrete implementation of `LensStore` using Better SQLite for data persistence.
|
|
28
|
+
* **Embedded UI**: Includes a built-in web interface for visualizing captured application data.
|
|
29
|
+
|
|
30
|
+
## Installation
|
|
31
|
+
|
|
32
|
+
```bash
|
|
33
|
+
pnpm add @lensjs/core
|
|
34
|
+
```
|
|
35
|
+
|
|
36
|
+
## Usage Example (Conceptual - typically used via framework adapters)
|
|
37
|
+
|
|
38
|
+
```typescript
|
|
39
|
+
import { Lens, RequestWatcher, QueryWatcher, CacheWatcher } from '@lensjs/core';
|
|
40
|
+
import { BetterSqliteStore } from '@lensjs/core/stores';
|
|
41
|
+
// Assuming you have a custom adapter for your framework
|
|
42
|
+
import MyFrameworkAdapter from './my-framework-adapter';
|
|
43
|
+
|
|
44
|
+
async function bootstrapLens(appInstance: any) {
|
|
45
|
+
const store = new BetterSqliteStore();
|
|
46
|
+
await store.initialize();
|
|
47
|
+
|
|
48
|
+
const adapter = new MyFrameworkAdapter({ app: appInstance });
|
|
49
|
+
|
|
50
|
+
await Lens.setStore(store)
|
|
51
|
+
.setAdapter(adapter)
|
|
52
|
+
.setWatchers([
|
|
53
|
+
new RequestWatcher(),
|
|
54
|
+
new QueryWatcher(),
|
|
55
|
+
new CacheWatcher(),
|
|
56
|
+
new ExceptionWatcher(),
|
|
57
|
+
])
|
|
58
|
+
.start({
|
|
59
|
+
appName: 'My Application',
|
|
60
|
+
enabled: process.env.NODE_ENV !== 'production',
|
|
61
|
+
basePath: 'lens-dashboard', // UI will be served at /lens-dashboard
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
console.log('Lens core initialized.');
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
// In your application's main entry point:
|
|
68
|
+
// bootstrapLens(yourFrameworkAppInstance);
|
|
69
|
+
```
|
package/dist/abstracts/store.cjs
CHANGED
|
@@ -24,4 +24,27 @@ __export(store_exports, {
|
|
|
24
24
|
});
|
|
25
25
|
module.exports = __toCommonJS(store_exports);
|
|
26
26
|
var Store = class {
|
|
27
|
+
getAllExceptions(_paginationParams) {
|
|
28
|
+
return this.defaultMinimalPaginate();
|
|
29
|
+
}
|
|
30
|
+
stringifyData(data) {
|
|
31
|
+
if (typeof data === "string") {
|
|
32
|
+
return data;
|
|
33
|
+
}
|
|
34
|
+
try {
|
|
35
|
+
return JSON.stringify(data);
|
|
36
|
+
} catch (e) {
|
|
37
|
+
console.error(`Failed to stringify lens data: ${e}`);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
defaultMinimalPaginate() {
|
|
41
|
+
return Promise.resolve({
|
|
42
|
+
data: [],
|
|
43
|
+
meta: {
|
|
44
|
+
currentPage: 0,
|
|
45
|
+
lastPage: 0,
|
|
46
|
+
total: 0
|
|
47
|
+
}
|
|
48
|
+
});
|
|
49
|
+
}
|
|
27
50
|
};
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { WatcherTypeEnum, PaginationParams, Paginator, LensEntry } from '../types/index.cjs';
|
|
2
2
|
import 'sql-formatter';
|
|
3
3
|
|
|
4
|
+
type MinimalPaginatePromise = Promise<Paginator<Omit<LensEntry, "data">[]>>;
|
|
4
5
|
declare abstract class Store {
|
|
5
6
|
abstract initialize(): Promise<void>;
|
|
6
7
|
abstract save(entry: {
|
|
@@ -11,13 +12,17 @@ declare abstract class Store {
|
|
|
11
12
|
timestamp?: string;
|
|
12
13
|
requestId?: string;
|
|
13
14
|
}): Promise<void>;
|
|
14
|
-
abstract getAllRequests(paginationParams: PaginationParams):
|
|
15
|
+
abstract getAllRequests(paginationParams: PaginationParams): MinimalPaginatePromise;
|
|
15
16
|
abstract getAllQueries(paginationParams: PaginationParams): Promise<Paginator<LensEntry[]>>;
|
|
16
|
-
abstract
|
|
17
|
+
abstract getAllCacheEntries(paginationParams: PaginationParams): MinimalPaginatePromise;
|
|
18
|
+
abstract allByRequestId(requestId: string, type: WatcherTypeEnum, includeFullData?: boolean): Promise<LensEntry[]>;
|
|
17
19
|
abstract find(type: WatcherTypeEnum, id: string): Promise<LensEntry | null>;
|
|
18
20
|
abstract truncate(): Promise<void>;
|
|
19
21
|
abstract paginate<T>(type: WatcherTypeEnum, pagination: PaginationParams): Promise<Paginator<T>>;
|
|
20
22
|
abstract count(type: WatcherTypeEnum): Promise<number>;
|
|
23
|
+
getAllExceptions(_paginationParams: PaginationParams): MinimalPaginatePromise;
|
|
24
|
+
protected stringifyData(data: Record<string, any> | string): string | undefined;
|
|
25
|
+
protected defaultMinimalPaginate(): MinimalPaginatePromise;
|
|
21
26
|
}
|
|
22
27
|
|
|
23
28
|
export { Store as default };
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { WatcherTypeEnum, PaginationParams, Paginator, LensEntry } from '../types/index.js';
|
|
2
2
|
import 'sql-formatter';
|
|
3
3
|
|
|
4
|
+
type MinimalPaginatePromise = Promise<Paginator<Omit<LensEntry, "data">[]>>;
|
|
4
5
|
declare abstract class Store {
|
|
5
6
|
abstract initialize(): Promise<void>;
|
|
6
7
|
abstract save(entry: {
|
|
@@ -11,13 +12,17 @@ declare abstract class Store {
|
|
|
11
12
|
timestamp?: string;
|
|
12
13
|
requestId?: string;
|
|
13
14
|
}): Promise<void>;
|
|
14
|
-
abstract getAllRequests(paginationParams: PaginationParams):
|
|
15
|
+
abstract getAllRequests(paginationParams: PaginationParams): MinimalPaginatePromise;
|
|
15
16
|
abstract getAllQueries(paginationParams: PaginationParams): Promise<Paginator<LensEntry[]>>;
|
|
16
|
-
abstract
|
|
17
|
+
abstract getAllCacheEntries(paginationParams: PaginationParams): MinimalPaginatePromise;
|
|
18
|
+
abstract allByRequestId(requestId: string, type: WatcherTypeEnum, includeFullData?: boolean): Promise<LensEntry[]>;
|
|
17
19
|
abstract find(type: WatcherTypeEnum, id: string): Promise<LensEntry | null>;
|
|
18
20
|
abstract truncate(): Promise<void>;
|
|
19
21
|
abstract paginate<T>(type: WatcherTypeEnum, pagination: PaginationParams): Promise<Paginator<T>>;
|
|
20
22
|
abstract count(type: WatcherTypeEnum): Promise<number>;
|
|
23
|
+
getAllExceptions(_paginationParams: PaginationParams): MinimalPaginatePromise;
|
|
24
|
+
protected stringifyData(data: Record<string, any> | string): string | undefined;
|
|
25
|
+
protected defaultMinimalPaginate(): MinimalPaginatePromise;
|
|
21
26
|
}
|
|
22
27
|
|
|
23
28
|
export { Store as default };
|
package/dist/abstracts/store.js
CHANGED
|
@@ -1,5 +1,28 @@
|
|
|
1
1
|
// src/abstracts/store.ts
|
|
2
2
|
var Store = class {
|
|
3
|
+
getAllExceptions(_paginationParams) {
|
|
4
|
+
return this.defaultMinimalPaginate();
|
|
5
|
+
}
|
|
6
|
+
stringifyData(data) {
|
|
7
|
+
if (typeof data === "string") {
|
|
8
|
+
return data;
|
|
9
|
+
}
|
|
10
|
+
try {
|
|
11
|
+
return JSON.stringify(data);
|
|
12
|
+
} catch (e) {
|
|
13
|
+
console.error(`Failed to stringify lens data: ${e}`);
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
defaultMinimalPaginate() {
|
|
17
|
+
return Promise.resolve({
|
|
18
|
+
data: [],
|
|
19
|
+
meta: {
|
|
20
|
+
currentPage: 0,
|
|
21
|
+
lastPage: 0,
|
|
22
|
+
total: 0
|
|
23
|
+
}
|
|
24
|
+
});
|
|
25
|
+
}
|
|
3
26
|
};
|
|
4
27
|
export {
|
|
5
28
|
Store as default
|
|
@@ -74,14 +74,30 @@ var ApiController = class {
|
|
|
74
74
|
await getStore().getAllRequests(this.extractPaginationParams(qs))
|
|
75
75
|
);
|
|
76
76
|
}
|
|
77
|
-
static async getRequest({
|
|
78
|
-
params
|
|
79
|
-
}) {
|
|
77
|
+
static async getRequest({ params }) {
|
|
80
78
|
const request = await getStore().find("request" /* REQUEST */, params.id);
|
|
81
79
|
if (!request) {
|
|
82
80
|
return this.notFoundResponse();
|
|
83
81
|
}
|
|
84
|
-
|
|
82
|
+
const queries = await getStore().allByRequestId(
|
|
83
|
+
request.id,
|
|
84
|
+
"query" /* QUERY */
|
|
85
|
+
);
|
|
86
|
+
const cacheEntries = await getStore().allByRequestId(
|
|
87
|
+
request.id,
|
|
88
|
+
"cache" /* CACHE */
|
|
89
|
+
);
|
|
90
|
+
const exceptions = await getStore().allByRequestId(
|
|
91
|
+
request.id,
|
|
92
|
+
"exception" /* EXCEPTION */,
|
|
93
|
+
false
|
|
94
|
+
);
|
|
95
|
+
return this.resourceResponse({
|
|
96
|
+
request,
|
|
97
|
+
queries,
|
|
98
|
+
cacheEntries,
|
|
99
|
+
exceptions
|
|
100
|
+
});
|
|
85
101
|
}
|
|
86
102
|
static async getQueries({
|
|
87
103
|
qs
|
|
@@ -100,6 +116,33 @@ var ApiController = class {
|
|
|
100
116
|
}
|
|
101
117
|
return this.resourceResponse(query);
|
|
102
118
|
}
|
|
119
|
+
static async getCacheEntries({ qs }) {
|
|
120
|
+
return this.paginatedResponse(
|
|
121
|
+
await getStore().getAllCacheEntries(this.extractPaginationParams(qs))
|
|
122
|
+
);
|
|
123
|
+
}
|
|
124
|
+
static async getCacheEntry({ params }) {
|
|
125
|
+
const cacheEntry = await getStore().find("cache" /* CACHE */, params.id);
|
|
126
|
+
if (!cacheEntry) {
|
|
127
|
+
return this.notFoundResponse();
|
|
128
|
+
}
|
|
129
|
+
return this.resourceResponse(cacheEntry);
|
|
130
|
+
}
|
|
131
|
+
static async getExceptions({ qs }) {
|
|
132
|
+
return this.paginatedResponse(
|
|
133
|
+
await getStore().getAllExceptions(this.extractPaginationParams(qs))
|
|
134
|
+
);
|
|
135
|
+
}
|
|
136
|
+
static async getException({ params }) {
|
|
137
|
+
const exception = await getStore().find(
|
|
138
|
+
"exception" /* EXCEPTION */,
|
|
139
|
+
params.id
|
|
140
|
+
);
|
|
141
|
+
if (!exception) {
|
|
142
|
+
return this.notFoundResponse();
|
|
143
|
+
}
|
|
144
|
+
return this.resourceResponse(exception);
|
|
145
|
+
}
|
|
103
146
|
static async truncate() {
|
|
104
147
|
await getStore().truncate();
|
|
105
148
|
return this.baseResponse({}, 200, "All entries cleared");
|
|
@@ -1,11 +1,15 @@
|
|
|
1
|
-
import { RouteDefinitionHandler, ApiResponse, LensEntry } from '../types/index.cjs';
|
|
1
|
+
import { RouteDefinitionHandler, ApiResponse, LensEntry, Paginator } from '../types/index.cjs';
|
|
2
2
|
import 'sql-formatter';
|
|
3
3
|
|
|
4
4
|
declare class ApiController {
|
|
5
5
|
static getRequests({ qs }: RouteDefinitionHandler): Promise<ApiResponse<Omit<LensEntry, "data">[]>>;
|
|
6
|
-
static getRequest({ params
|
|
6
|
+
static getRequest({ params }: RouteDefinitionHandler): Promise<ApiResponse<Object>>;
|
|
7
7
|
static getQueries({ qs, }: RouteDefinitionHandler): Promise<ApiResponse<LensEntry[]>>;
|
|
8
8
|
static getQuery({ params, }: RouteDefinitionHandler): Promise<ApiResponse<LensEntry>>;
|
|
9
|
+
static getCacheEntries({ qs }: RouteDefinitionHandler): Promise<ApiResponse<Omit<LensEntry, "data">[]>>;
|
|
10
|
+
static getCacheEntry({ params }: RouteDefinitionHandler): Promise<ApiResponse<Object>>;
|
|
11
|
+
static getExceptions({ qs }: RouteDefinitionHandler): Promise<ApiResponse<Omit<LensEntry, "data">[]>>;
|
|
12
|
+
static getException({ params }: RouteDefinitionHandler): Promise<ApiResponse<Object>>;
|
|
9
13
|
static truncate(): Promise<ApiResponse<{}>>;
|
|
10
14
|
static fetchUiConfig(): {
|
|
11
15
|
appName: string;
|
|
@@ -18,7 +22,7 @@ declare class ApiController {
|
|
|
18
22
|
private static extractPaginationParams;
|
|
19
23
|
private static resourceResponse;
|
|
20
24
|
private static notFoundResponse;
|
|
21
|
-
|
|
25
|
+
static paginatedResponse<T extends Object>(data: Paginator<T>): ApiResponse<T>;
|
|
22
26
|
private static baseResponse;
|
|
23
27
|
}
|
|
24
28
|
|
|
@@ -1,11 +1,15 @@
|
|
|
1
|
-
import { RouteDefinitionHandler, ApiResponse, LensEntry } from '../types/index.js';
|
|
1
|
+
import { RouteDefinitionHandler, ApiResponse, LensEntry, Paginator } from '../types/index.js';
|
|
2
2
|
import 'sql-formatter';
|
|
3
3
|
|
|
4
4
|
declare class ApiController {
|
|
5
5
|
static getRequests({ qs }: RouteDefinitionHandler): Promise<ApiResponse<Omit<LensEntry, "data">[]>>;
|
|
6
|
-
static getRequest({ params
|
|
6
|
+
static getRequest({ params }: RouteDefinitionHandler): Promise<ApiResponse<Object>>;
|
|
7
7
|
static getQueries({ qs, }: RouteDefinitionHandler): Promise<ApiResponse<LensEntry[]>>;
|
|
8
8
|
static getQuery({ params, }: RouteDefinitionHandler): Promise<ApiResponse<LensEntry>>;
|
|
9
|
+
static getCacheEntries({ qs }: RouteDefinitionHandler): Promise<ApiResponse<Omit<LensEntry, "data">[]>>;
|
|
10
|
+
static getCacheEntry({ params }: RouteDefinitionHandler): Promise<ApiResponse<Object>>;
|
|
11
|
+
static getExceptions({ qs }: RouteDefinitionHandler): Promise<ApiResponse<Omit<LensEntry, "data">[]>>;
|
|
12
|
+
static getException({ params }: RouteDefinitionHandler): Promise<ApiResponse<Object>>;
|
|
9
13
|
static truncate(): Promise<ApiResponse<{}>>;
|
|
10
14
|
static fetchUiConfig(): {
|
|
11
15
|
appName: string;
|
|
@@ -18,7 +22,7 @@ declare class ApiController {
|
|
|
18
22
|
private static extractPaginationParams;
|
|
19
23
|
private static resourceResponse;
|
|
20
24
|
private static notFoundResponse;
|
|
21
|
-
|
|
25
|
+
static paginatedResponse<T extends Object>(data: Paginator<T>): ApiResponse<T>;
|
|
22
26
|
private static baseResponse;
|
|
23
27
|
}
|
|
24
28
|
|
|
@@ -48,14 +48,30 @@ var ApiController = class {
|
|
|
48
48
|
await getStore().getAllRequests(this.extractPaginationParams(qs))
|
|
49
49
|
);
|
|
50
50
|
}
|
|
51
|
-
static async getRequest({
|
|
52
|
-
params
|
|
53
|
-
}) {
|
|
51
|
+
static async getRequest({ params }) {
|
|
54
52
|
const request = await getStore().find("request" /* REQUEST */, params.id);
|
|
55
53
|
if (!request) {
|
|
56
54
|
return this.notFoundResponse();
|
|
57
55
|
}
|
|
58
|
-
|
|
56
|
+
const queries = await getStore().allByRequestId(
|
|
57
|
+
request.id,
|
|
58
|
+
"query" /* QUERY */
|
|
59
|
+
);
|
|
60
|
+
const cacheEntries = await getStore().allByRequestId(
|
|
61
|
+
request.id,
|
|
62
|
+
"cache" /* CACHE */
|
|
63
|
+
);
|
|
64
|
+
const exceptions = await getStore().allByRequestId(
|
|
65
|
+
request.id,
|
|
66
|
+
"exception" /* EXCEPTION */,
|
|
67
|
+
false
|
|
68
|
+
);
|
|
69
|
+
return this.resourceResponse({
|
|
70
|
+
request,
|
|
71
|
+
queries,
|
|
72
|
+
cacheEntries,
|
|
73
|
+
exceptions
|
|
74
|
+
});
|
|
59
75
|
}
|
|
60
76
|
static async getQueries({
|
|
61
77
|
qs
|
|
@@ -74,6 +90,33 @@ var ApiController = class {
|
|
|
74
90
|
}
|
|
75
91
|
return this.resourceResponse(query);
|
|
76
92
|
}
|
|
93
|
+
static async getCacheEntries({ qs }) {
|
|
94
|
+
return this.paginatedResponse(
|
|
95
|
+
await getStore().getAllCacheEntries(this.extractPaginationParams(qs))
|
|
96
|
+
);
|
|
97
|
+
}
|
|
98
|
+
static async getCacheEntry({ params }) {
|
|
99
|
+
const cacheEntry = await getStore().find("cache" /* CACHE */, params.id);
|
|
100
|
+
if (!cacheEntry) {
|
|
101
|
+
return this.notFoundResponse();
|
|
102
|
+
}
|
|
103
|
+
return this.resourceResponse(cacheEntry);
|
|
104
|
+
}
|
|
105
|
+
static async getExceptions({ qs }) {
|
|
106
|
+
return this.paginatedResponse(
|
|
107
|
+
await getStore().getAllExceptions(this.extractPaginationParams(qs))
|
|
108
|
+
);
|
|
109
|
+
}
|
|
110
|
+
static async getException({ params }) {
|
|
111
|
+
const exception = await getStore().find(
|
|
112
|
+
"exception" /* EXCEPTION */,
|
|
113
|
+
params.id
|
|
114
|
+
);
|
|
115
|
+
if (!exception) {
|
|
116
|
+
return this.notFoundResponse();
|
|
117
|
+
}
|
|
118
|
+
return this.resourceResponse(exception);
|
|
119
|
+
}
|
|
77
120
|
static async truncate() {
|
|
78
121
|
await getStore().truncate();
|
|
79
122
|
return this.baseResponse({}, 200, "All entries cleared");
|
package/dist/core/lens.cjs
CHANGED
|
@@ -84,14 +84,30 @@ var ApiController = class {
|
|
|
84
84
|
await getStore().getAllRequests(this.extractPaginationParams(qs))
|
|
85
85
|
);
|
|
86
86
|
}
|
|
87
|
-
static async getRequest({
|
|
88
|
-
params
|
|
89
|
-
}) {
|
|
87
|
+
static async getRequest({ params }) {
|
|
90
88
|
const request = await getStore().find("request" /* REQUEST */, params.id);
|
|
91
89
|
if (!request) {
|
|
92
90
|
return this.notFoundResponse();
|
|
93
91
|
}
|
|
94
|
-
|
|
92
|
+
const queries = await getStore().allByRequestId(
|
|
93
|
+
request.id,
|
|
94
|
+
"query" /* QUERY */
|
|
95
|
+
);
|
|
96
|
+
const cacheEntries = await getStore().allByRequestId(
|
|
97
|
+
request.id,
|
|
98
|
+
"cache" /* CACHE */
|
|
99
|
+
);
|
|
100
|
+
const exceptions = await getStore().allByRequestId(
|
|
101
|
+
request.id,
|
|
102
|
+
"exception" /* EXCEPTION */,
|
|
103
|
+
false
|
|
104
|
+
);
|
|
105
|
+
return this.resourceResponse({
|
|
106
|
+
request,
|
|
107
|
+
queries,
|
|
108
|
+
cacheEntries,
|
|
109
|
+
exceptions
|
|
110
|
+
});
|
|
95
111
|
}
|
|
96
112
|
static async getQueries({
|
|
97
113
|
qs
|
|
@@ -110,6 +126,33 @@ var ApiController = class {
|
|
|
110
126
|
}
|
|
111
127
|
return this.resourceResponse(query);
|
|
112
128
|
}
|
|
129
|
+
static async getCacheEntries({ qs }) {
|
|
130
|
+
return this.paginatedResponse(
|
|
131
|
+
await getStore().getAllCacheEntries(this.extractPaginationParams(qs))
|
|
132
|
+
);
|
|
133
|
+
}
|
|
134
|
+
static async getCacheEntry({ params }) {
|
|
135
|
+
const cacheEntry = await getStore().find("cache" /* CACHE */, params.id);
|
|
136
|
+
if (!cacheEntry) {
|
|
137
|
+
return this.notFoundResponse();
|
|
138
|
+
}
|
|
139
|
+
return this.resourceResponse(cacheEntry);
|
|
140
|
+
}
|
|
141
|
+
static async getExceptions({ qs }) {
|
|
142
|
+
return this.paginatedResponse(
|
|
143
|
+
await getStore().getAllExceptions(this.extractPaginationParams(qs))
|
|
144
|
+
);
|
|
145
|
+
}
|
|
146
|
+
static async getException({ params }) {
|
|
147
|
+
const exception = await getStore().find(
|
|
148
|
+
"exception" /* EXCEPTION */,
|
|
149
|
+
params.id
|
|
150
|
+
);
|
|
151
|
+
if (!exception) {
|
|
152
|
+
return this.notFoundResponse();
|
|
153
|
+
}
|
|
154
|
+
return this.resourceResponse(exception);
|
|
155
|
+
}
|
|
113
156
|
static async truncate() {
|
|
114
157
|
await getStore().truncate();
|
|
115
158
|
return this.baseResponse({}, 200, "All entries cleared");
|
|
@@ -161,6 +204,29 @@ var path2 = __toESM(require("path"), 1);
|
|
|
161
204
|
|
|
162
205
|
// src/abstracts/store.ts
|
|
163
206
|
var Store = class {
|
|
207
|
+
getAllExceptions(_paginationParams) {
|
|
208
|
+
return this.defaultMinimalPaginate();
|
|
209
|
+
}
|
|
210
|
+
stringifyData(data) {
|
|
211
|
+
if (typeof data === "string") {
|
|
212
|
+
return data;
|
|
213
|
+
}
|
|
214
|
+
try {
|
|
215
|
+
return JSON.stringify(data);
|
|
216
|
+
} catch (e) {
|
|
217
|
+
console.error(`Failed to stringify lens data: ${e}`);
|
|
218
|
+
}
|
|
219
|
+
}
|
|
220
|
+
defaultMinimalPaginate() {
|
|
221
|
+
return Promise.resolve({
|
|
222
|
+
data: [],
|
|
223
|
+
meta: {
|
|
224
|
+
currentPage: 0,
|
|
225
|
+
lastPage: 0,
|
|
226
|
+
total: 0
|
|
227
|
+
}
|
|
228
|
+
});
|
|
229
|
+
}
|
|
164
230
|
};
|
|
165
231
|
|
|
166
232
|
// src/stores/better_sqlite.ts
|
|
@@ -183,11 +249,11 @@ var BetterSqliteStore = class extends Store {
|
|
|
183
249
|
`INSERT INTO ${TABLE_NAME} (id, data, type, created_at, lens_entry_id, minimal_data) values($id, $data, $type, $created_at, $lens_entry_id, $minimalData)`
|
|
184
250
|
).run({
|
|
185
251
|
id: entry.id ?? (0, import_crypto.randomUUID)(),
|
|
186
|
-
data:
|
|
252
|
+
data: this.stringifyData(entry.data),
|
|
187
253
|
type: entry.type,
|
|
188
|
-
created_at: entry.timestamp ?? (0, import_date.
|
|
254
|
+
created_at: entry.timestamp ?? (0, import_date.nowISO)(),
|
|
189
255
|
lens_entry_id: entry.requestId || null,
|
|
190
|
-
minimalData:
|
|
256
|
+
minimalData: this.stringifyData(entry.minimal_data ?? {})
|
|
191
257
|
});
|
|
192
258
|
}
|
|
193
259
|
async getAllQueries(pagination) {
|
|
@@ -196,11 +262,17 @@ var BetterSqliteStore = class extends Store {
|
|
|
196
262
|
async getAllRequests(pagination) {
|
|
197
263
|
return await this.paginate("request" /* REQUEST */, pagination, false);
|
|
198
264
|
}
|
|
199
|
-
async
|
|
265
|
+
async getAllCacheEntries(pagination) {
|
|
266
|
+
return await this.paginate("cache" /* CACHE */, pagination);
|
|
267
|
+
}
|
|
268
|
+
async getAllExceptions(pagination) {
|
|
269
|
+
return await this.paginate("exception" /* EXCEPTION */, pagination, false);
|
|
270
|
+
}
|
|
271
|
+
async allByRequestId(requestId, type, includeFullData = true) {
|
|
200
272
|
const rows = this.connection.prepare(
|
|
201
|
-
`${this.getSelectedColumns()} FROM ${TABLE_NAME} WHERE type = $type AND lens_entry_id = $requestId ORDER BY created_at DESC`
|
|
273
|
+
`${this.getSelectedColumns(includeFullData)} FROM ${TABLE_NAME} WHERE type = $type AND lens_entry_id = $requestId ORDER BY created_at DESC`
|
|
202
274
|
).all({ type, requestId });
|
|
203
|
-
return this.mapRows(rows);
|
|
275
|
+
return this.mapRows(rows, includeFullData);
|
|
204
276
|
}
|
|
205
277
|
async paginate(type, { page, perPage }, includeFullData = true) {
|
|
206
278
|
const offset = (page - 1) * perPage;
|
|
@@ -248,8 +320,13 @@ var BetterSqliteStore = class extends Store {
|
|
|
248
320
|
CREATE INDEX IF NOT EXISTS lens_entries_id_type_index
|
|
249
321
|
ON ${TABLE_NAME} (id, type);
|
|
250
322
|
`;
|
|
323
|
+
const lensEntryIdIndex = `
|
|
324
|
+
CREATE INDEX IF NOT EXISTS lens_entry_id_index
|
|
325
|
+
ON ${TABLE_NAME} (lens_entry_id);
|
|
326
|
+
`;
|
|
251
327
|
this.connection.exec(createTable);
|
|
252
328
|
this.connection.exec(createIndex);
|
|
329
|
+
this.connection.exec(lensEntryIdIndex);
|
|
253
330
|
}
|
|
254
331
|
mapRow(row, includeFullData = true) {
|
|
255
332
|
let data = includeFullData ? JSON.parse(row.data) : {};
|
|
@@ -356,6 +433,8 @@ var Lens = class {
|
|
|
356
433
|
api: {
|
|
357
434
|
requests: `/${config.basePath}/api/requests`,
|
|
358
435
|
queries: `/${config.basePath}/api/queries`,
|
|
436
|
+
cache: `/${config.basePath}/api/cache`,
|
|
437
|
+
exceptions: `/${config.basePath}/api/exceptions`,
|
|
359
438
|
truncate: `/${config.basePath}/api/truncate`
|
|
360
439
|
}
|
|
361
440
|
};
|
|
@@ -388,6 +467,26 @@ var Lens = class {
|
|
|
388
467
|
path: `${basePath}/api/queries/:id`,
|
|
389
468
|
handler: async (data) => await ApiController.getQuery(data)
|
|
390
469
|
},
|
|
470
|
+
{
|
|
471
|
+
method: "GET",
|
|
472
|
+
path: `${basePath}/api/cache`,
|
|
473
|
+
handler: async (data) => await ApiController.getCacheEntries(data)
|
|
474
|
+
},
|
|
475
|
+
{
|
|
476
|
+
method: "GET",
|
|
477
|
+
path: `${basePath}/api/cache/:id`,
|
|
478
|
+
handler: async (data) => await ApiController.getCacheEntry(data)
|
|
479
|
+
},
|
|
480
|
+
{
|
|
481
|
+
method: "GET",
|
|
482
|
+
path: `${basePath}/api/exceptions`,
|
|
483
|
+
handler: async (data) => await ApiController.getExceptions(data)
|
|
484
|
+
},
|
|
485
|
+
{
|
|
486
|
+
method: "GET",
|
|
487
|
+
path: `${basePath}/api/exceptions/:id`,
|
|
488
|
+
handler: async (data) => await ApiController.getException(data)
|
|
489
|
+
},
|
|
391
490
|
{
|
|
392
491
|
method: "DELETE",
|
|
393
492
|
path: `${basePath}/api/truncate`,
|