@lensjs/core 1.0.12 → 2.0.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.
Files changed (74) hide show
  1. package/dist/abstracts/store.cjs +10 -0
  2. package/dist/abstracts/store.d.cts +2 -0
  3. package/dist/abstracts/store.d.ts +2 -0
  4. package/dist/abstracts/store.js +10 -0
  5. package/dist/core/api_controller.cjs +26 -4
  6. package/dist/core/api_controller.d.cts +3 -1
  7. package/dist/core/api_controller.d.ts +3 -1
  8. package/dist/core/api_controller.js +26 -4
  9. package/dist/core/lens.cjs +58 -7
  10. package/dist/core/lens.js +59 -8
  11. package/dist/index.cjs +112 -7
  12. package/dist/index.d.cts +5 -2
  13. package/dist/index.d.ts +5 -2
  14. package/dist/index.js +110 -8
  15. package/dist/stores/better_sqlite.cjs +21 -3
  16. package/dist/stores/better_sqlite.d.cts +8 -0
  17. package/dist/stores/better_sqlite.d.ts +8 -0
  18. package/dist/stores/better_sqlite.js +22 -4
  19. package/dist/stores/index.cjs +21 -3
  20. package/dist/stores/index.js +22 -4
  21. package/dist/types/index.cjs +1 -0
  22. package/dist/types/index.d.cts +25 -2
  23. package/dist/types/index.d.ts +25 -2
  24. package/dist/types/index.js +1 -0
  25. package/dist/ui/assets/CacheActionBadge-3jjmNjC6.js +1 -0
  26. package/dist/ui/assets/CacheEntriesTable-DPLre6br.js +1 -0
  27. package/dist/ui/assets/CacheEntryContainer-WN6LkoCR.js +2 -0
  28. package/dist/ui/assets/CacheEntryDetails-CHt_pNTk.js +1 -0
  29. package/dist/ui/assets/CacheEntryDetailsContainer-BhquSApO.js +2 -0
  30. package/dist/ui/assets/LoadMore-DHOrhPsi.js +1 -0
  31. package/dist/ui/assets/QueriesContainer-Cl6rq4dH.js +2 -0
  32. package/dist/ui/assets/{QueryDetailsContainer-E7P-IO7f.js → QueryDetailsContainer-eoLkgEjj.js} +15 -15
  33. package/dist/ui/assets/QueryTable-BXSzT-Cm.js +1 -0
  34. package/dist/ui/assets/RequestDetails-CIB7_XWh.js +1 -0
  35. package/dist/ui/assets/{RequestDetailsContainer-DuDo-IqS.js → RequestDetailsContainer-BaH6fUK7.js} +2 -2
  36. package/dist/ui/assets/RequestsContainer-DLS17BWP.js +2 -0
  37. package/dist/ui/assets/RequetsTable-B51VXisk.js +1 -0
  38. package/dist/ui/assets/{StatusCode-FQEjz7gK.js → StatusCode-DVhX11V3.js} +1 -1
  39. package/dist/ui/assets/{TabbedDataViewer-cBDdPwIz.js → TabbedDataViewer-CNSEhc6h.js} +1 -1
  40. package/dist/ui/assets/{Table-DYaXk80S.js → Table-D1Kpw7PA.js} +2 -2
  41. package/dist/ui/assets/columns-BIDLCW64.js +1 -0
  42. package/dist/ui/assets/columns-jYfhBxOM.js +1 -0
  43. package/dist/ui/assets/{index-BS8XxorB.js → index-BdvbrZNf.js} +24 -19
  44. package/dist/ui/assets/index-C04tuZDI.css +1 -0
  45. package/dist/ui/assets/useCacheEntries-vuHEIj6E.js +1 -0
  46. package/dist/ui/assets/useLensApi-Bzmx8hps.js +1 -0
  47. package/dist/ui/assets/{useLoadMore-CJltToLI.js → useLoadMore-twYxPJ-d.js} +1 -1
  48. package/dist/ui/assets/useQueries-BYFLoUQR.js +1 -0
  49. package/dist/ui/index.html +2 -2
  50. package/dist/utils/async_context.cjs +31 -0
  51. package/dist/utils/async_context.d.cts +8 -0
  52. package/dist/utils/async_context.d.ts +8 -0
  53. package/dist/utils/async_context.js +6 -0
  54. package/dist/utils/event_emitter.cjs +5 -2
  55. package/dist/utils/event_emitter.d.cts +8 -1
  56. package/dist/utils/event_emitter.d.ts +8 -1
  57. package/dist/utils/event_emitter.js +3 -1
  58. package/dist/watchers/cache_watcher.cjs +111 -0
  59. package/dist/watchers/cache_watcher.d.cts +11 -0
  60. package/dist/watchers/cache_watcher.d.ts +11 -0
  61. package/dist/watchers/cache_watcher.js +88 -0
  62. package/dist/watchers/index.cjs +44 -0
  63. package/dist/watchers/index.d.cts +1 -0
  64. package/dist/watchers/index.d.ts +1 -0
  65. package/dist/watchers/index.js +43 -0
  66. package/package.json +1 -1
  67. package/dist/ui/assets/QueriesContainer-CAAsjjW5.js +0 -2
  68. package/dist/ui/assets/QueryTable-BcrtUssT.js +0 -1
  69. package/dist/ui/assets/RequestDetails-C2DZBu5H.js +0 -1
  70. package/dist/ui/assets/RequestsContainer-DK3hQVz9.js +0 -2
  71. package/dist/ui/assets/RequetsTable-DgP8p60b.js +0 -1
  72. package/dist/ui/assets/index-DzNHqeKh.css +0 -1
  73. package/dist/ui/assets/useLensApi-DG6atd6d.js +0 -1
  74. package/dist/ui/assets/useQueries-C8mDDDc6.js +0 -1
package/dist/index.d.ts CHANGED
@@ -2,13 +2,16 @@ export { default as Lens } from './core/lens.js';
2
2
  export { default as BetterSqliteStore } from './stores/better_sqlite.js';
3
3
  export { default as QueryWatcher } from './watchers/query_watcher.js';
4
4
  export { default as RequestWatcher } from './watchers/request_watcher.js';
5
- export { ApiResponse, Entry, HttpMethod, LensConfig, LensEntry, PaginationParams, Paginator, QueryEntry, QueryType, RequestEntry, RouteDefinition, RouteDefinitionHandler, RouteHttpMethod, SqlQueryType, UserEntry, WatcherTypeEnum } from './types/index.js';
5
+ export { default as CacheWatcher } from './watchers/cache_watcher.js';
6
+ export { ApiResponse, CacheAction, CacheEntry, Entry, HttpMethod, LensConfig, LensEntry, PaginationParams, Paginator, QueryEntry, QueryType, RequestEntry, RouteDefinition, RouteDefinitionHandler, RouteHttpMethod, SqlQueryType, UserEntry, WatcherTypeEnum } from './types/index.js';
6
7
  export { default as LensAdapter } from './abstracts/adapter.js';
7
8
  export { default as LensStore } from './abstracts/store.js';
8
9
  export { default as LensWatcher } from './core/watcher.js';
9
10
  export { getStore as getLensStore } from './context/context.js';
10
11
  export { i as lensUtils } from './index-DiLfwsvc.js';
11
- export { createEmittery } from './utils/event_emitter.js';
12
+ export { createEmittery, lensEmitter } from './utils/event_emitter.js';
13
+ export { lensContext } from './utils/async_context.js';
12
14
  import 'libsql';
13
15
  import 'sql-formatter';
14
16
  import 'emittery';
17
+ import 'async_hooks';
package/dist/index.js CHANGED
@@ -51,6 +51,7 @@ var getUiConfig = () => {
51
51
  var WatcherTypeEnum = /* @__PURE__ */ ((WatcherTypeEnum2) => {
52
52
  WatcherTypeEnum2["REQUEST"] = "request";
53
53
  WatcherTypeEnum2["QUERY"] = "query";
54
+ WatcherTypeEnum2["CACHE"] = "cache";
54
55
  return WatcherTypeEnum2;
55
56
  })(WatcherTypeEnum || {});
56
57
 
@@ -61,14 +62,24 @@ var ApiController = class {
61
62
  await getStore().getAllRequests(this.extractPaginationParams(qs))
62
63
  );
63
64
  }
64
- static async getRequest({
65
- params
66
- }) {
65
+ static async getRequest({ params }) {
67
66
  const request = await getStore().find("request" /* REQUEST */, params.id);
68
67
  if (!request) {
69
68
  return this.notFoundResponse();
70
69
  }
71
- return this.resourceResponse(request);
70
+ const queries = await getStore().allByRequestId(
71
+ request.id,
72
+ "query" /* QUERY */
73
+ );
74
+ const cacheEntries = await getStore().allByRequestId(
75
+ request.id,
76
+ "cache" /* CACHE */
77
+ );
78
+ return this.resourceResponse({
79
+ request,
80
+ queries,
81
+ cacheEntries
82
+ });
72
83
  }
73
84
  static async getQueries({
74
85
  qs
@@ -87,6 +98,18 @@ var ApiController = class {
87
98
  }
88
99
  return this.resourceResponse(query);
89
100
  }
101
+ static async getCacheEntries({ qs }) {
102
+ return this.paginatedResponse(
103
+ await getStore().getAllCacheEntries(this.extractPaginationParams(qs))
104
+ );
105
+ }
106
+ static async getCacheEntry({ params }) {
107
+ const cacheEntry = await getStore().find("cache" /* CACHE */, params.id);
108
+ if (!cacheEntry) {
109
+ return this.notFoundResponse();
110
+ }
111
+ return this.resourceResponse(cacheEntry);
112
+ }
90
113
  static async truncate() {
91
114
  await getStore().truncate();
92
115
  return this.baseResponse({}, 200, "All entries cleared");
@@ -138,12 +161,22 @@ import * as path2 from "path";
138
161
 
139
162
  // src/abstracts/store.ts
140
163
  var Store = class {
164
+ stringifyData(data) {
165
+ if (typeof data === "string") {
166
+ return data;
167
+ }
168
+ try {
169
+ return JSON.stringify(data);
170
+ } catch (e) {
171
+ console.error(`Failed to stringify lens data: ${e}`);
172
+ }
173
+ }
141
174
  };
142
175
 
143
176
  // src/stores/better_sqlite.ts
144
177
  import { randomUUID } from "crypto";
145
178
  import Database from "libsql";
146
- import { sqlDateTime } from "@lensjs/date";
179
+ import { nowISO } from "@lensjs/date";
147
180
  var TABLE_NAME = "lens_entries";
148
181
  var BetterSqliteStore = class extends Store {
149
182
  connection;
@@ -160,11 +193,11 @@ var BetterSqliteStore = class extends Store {
160
193
  `INSERT INTO ${TABLE_NAME} (id, data, type, created_at, lens_entry_id, minimal_data) values($id, $data, $type, $created_at, $lens_entry_id, $minimalData)`
161
194
  ).run({
162
195
  id: entry.id ?? randomUUID(),
163
- data: JSON.stringify(entry.data),
196
+ data: this.stringifyData(entry.data),
164
197
  type: entry.type,
165
- created_at: entry.timestamp ?? sqlDateTime(),
198
+ created_at: entry.timestamp ?? nowISO(),
166
199
  lens_entry_id: entry.requestId || null,
167
- minimalData: JSON.stringify(entry.minimal_data ?? {})
200
+ minimalData: this.stringifyData(entry.minimal_data ?? {})
168
201
  });
169
202
  }
170
203
  async getAllQueries(pagination) {
@@ -173,6 +206,9 @@ var BetterSqliteStore = class extends Store {
173
206
  async getAllRequests(pagination) {
174
207
  return await this.paginate("request" /* REQUEST */, pagination, false);
175
208
  }
209
+ async getAllCacheEntries(pagination) {
210
+ return await this.paginate("cache" /* CACHE */, pagination);
211
+ }
176
212
  async allByRequestId(requestId, type) {
177
213
  const rows = this.connection.prepare(
178
214
  `${this.getSelectedColumns()} FROM ${TABLE_NAME} WHERE type = $type AND lens_entry_id = $requestId ORDER BY created_at DESC`
@@ -225,8 +261,13 @@ var BetterSqliteStore = class extends Store {
225
261
  CREATE INDEX IF NOT EXISTS lens_entries_id_type_index
226
262
  ON ${TABLE_NAME} (id, type);
227
263
  `;
264
+ const lensEntryIdIndex = `
265
+ CREATE INDEX IF NOT EXISTS lens_entry_id_index
266
+ ON ${TABLE_NAME} (lens_entry_id);
267
+ `;
228
268
  this.connection.exec(createTable);
229
269
  this.connection.exec(createIndex);
270
+ this.connection.exec(lensEntryIdIndex);
230
271
  }
231
272
  mapRow(row, includeFullData = true) {
232
273
  let data = includeFullData ? JSON.parse(row.data) : {};
@@ -434,6 +475,7 @@ var Lens = class {
434
475
  api: {
435
476
  requests: `/${config.basePath}/api/requests`,
436
477
  queries: `/${config.basePath}/api/queries`,
478
+ cache: `/${config.basePath}/api/cache`,
437
479
  truncate: `/${config.basePath}/api/truncate`
438
480
  }
439
481
  };
@@ -466,6 +508,16 @@ var Lens = class {
466
508
  path: `${basePath}/api/queries/:id`,
467
509
  handler: async (data) => await ApiController.getQuery(data)
468
510
  },
511
+ {
512
+ method: "GET",
513
+ path: `${basePath}/api/cache`,
514
+ handler: async (data) => await ApiController.getCacheEntries(data)
515
+ },
516
+ {
517
+ method: "GET",
518
+ path: `${basePath}/api/cache/:id`,
519
+ handler: async (data) => await ApiController.getCacheEntry(data)
520
+ },
469
521
  {
470
522
  method: "DELETE",
471
523
  path: `${basePath}/api/truncate`,
@@ -524,6 +576,48 @@ var RequestWatcher = class extends Watcher {
524
576
  }
525
577
  };
526
578
 
579
+ // src/watchers/cache_watcher.ts
580
+ var CacheWatcher = class extends Watcher {
581
+ name = "cache" /* CACHE */;
582
+ async log(data) {
583
+ const payload = {
584
+ action: data.action,
585
+ data: this.normalizePayload(data),
586
+ requestId: data.requestId ?? "",
587
+ createdAt: data.createdAt
588
+ };
589
+ await getStore().save({
590
+ requestId: data.requestId ?? "",
591
+ type: this.name,
592
+ data: payload,
593
+ minimal_data: {
594
+ action: data.action,
595
+ key: payload.data.key,
596
+ createdAt: payload.createdAt
597
+ }
598
+ });
599
+ }
600
+ normalizePayload(data) {
601
+ let normalizedData = "data" in data ? data.data : {
602
+ key: "",
603
+ value: ""
604
+ };
605
+ if (!normalizedData || typeof normalizedData === "object" && Object.keys(normalizedData).length === 0) {
606
+ normalizedData = {
607
+ key: "",
608
+ value: ""
609
+ };
610
+ }
611
+ if (!normalizedData["key"]) {
612
+ normalizedData.key = "";
613
+ }
614
+ if (!normalizedData["value"]) {
615
+ normalizedData["value"] = "";
616
+ }
617
+ return normalizedData;
618
+ }
619
+ };
620
+
527
621
  // src/abstracts/adapter.ts
528
622
  var Adapter = class {
529
623
  watchers = [];
@@ -554,8 +648,14 @@ import Emittery from "emittery";
554
648
  var createEmittery = () => {
555
649
  return new Emittery();
556
650
  };
651
+ var lensEmitter = createEmittery();
652
+
653
+ // src/utils/async_context.ts
654
+ import { AsyncLocalStorage } from "async_hooks";
655
+ var lensContext = new AsyncLocalStorage();
557
656
  export {
558
657
  BetterSqliteStore,
658
+ CacheWatcher,
559
659
  Lens,
560
660
  Adapter as LensAdapter,
561
661
  Store as LensStore,
@@ -565,5 +665,7 @@ export {
565
665
  WatcherTypeEnum,
566
666
  createEmittery,
567
667
  getStore as getLensStore,
668
+ lensContext,
669
+ lensEmitter,
568
670
  utils_exports as lensUtils
569
671
  };
@@ -36,6 +36,16 @@ module.exports = __toCommonJS(better_sqlite_exports);
36
36
 
37
37
  // src/abstracts/store.ts
38
38
  var Store = class {
39
+ stringifyData(data) {
40
+ if (typeof data === "string") {
41
+ return data;
42
+ }
43
+ try {
44
+ return JSON.stringify(data);
45
+ } catch (e) {
46
+ console.error(`Failed to stringify lens data: ${e}`);
47
+ }
48
+ }
39
49
  };
40
50
 
41
51
  // src/stores/better_sqlite.ts
@@ -58,11 +68,11 @@ var BetterSqliteStore = class extends Store {
58
68
  `INSERT INTO ${TABLE_NAME} (id, data, type, created_at, lens_entry_id, minimal_data) values($id, $data, $type, $created_at, $lens_entry_id, $minimalData)`
59
69
  ).run({
60
70
  id: entry.id ?? (0, import_crypto.randomUUID)(),
61
- data: JSON.stringify(entry.data),
71
+ data: this.stringifyData(entry.data),
62
72
  type: entry.type,
63
- created_at: entry.timestamp ?? (0, import_date.sqlDateTime)(),
73
+ created_at: entry.timestamp ?? (0, import_date.nowISO)(),
64
74
  lens_entry_id: entry.requestId || null,
65
- minimalData: JSON.stringify(entry.minimal_data ?? {})
75
+ minimalData: this.stringifyData(entry.minimal_data ?? {})
66
76
  });
67
77
  }
68
78
  async getAllQueries(pagination) {
@@ -71,6 +81,9 @@ var BetterSqliteStore = class extends Store {
71
81
  async getAllRequests(pagination) {
72
82
  return await this.paginate("request" /* REQUEST */, pagination, false);
73
83
  }
84
+ async getAllCacheEntries(pagination) {
85
+ return await this.paginate("cache" /* CACHE */, pagination);
86
+ }
74
87
  async allByRequestId(requestId, type) {
75
88
  const rows = this.connection.prepare(
76
89
  `${this.getSelectedColumns()} FROM ${TABLE_NAME} WHERE type = $type AND lens_entry_id = $requestId ORDER BY created_at DESC`
@@ -123,8 +136,13 @@ var BetterSqliteStore = class extends Store {
123
136
  CREATE INDEX IF NOT EXISTS lens_entries_id_type_index
124
137
  ON ${TABLE_NAME} (id, type);
125
138
  `;
139
+ const lensEntryIdIndex = `
140
+ CREATE INDEX IF NOT EXISTS lens_entry_id_index
141
+ ON ${TABLE_NAME} (lens_entry_id);
142
+ `;
126
143
  this.connection.exec(createTable);
127
144
  this.connection.exec(createIndex);
145
+ this.connection.exec(lensEntryIdIndex);
128
146
  }
129
147
  mapRow(row, includeFullData = true) {
130
148
  let data = includeFullData ? JSON.parse(row.data) : {};
@@ -31,6 +31,14 @@ declare class BetterSqliteStore extends Store {
31
31
  };
32
32
  data: T;
33
33
  }>;
34
+ getAllCacheEntries<T extends Omit<LensEntry, "data">[]>(pagination: PaginationParams): Promise<{
35
+ meta: {
36
+ total: number;
37
+ lastPage: number;
38
+ currentPage: number;
39
+ };
40
+ data: T;
41
+ }>;
34
42
  allByRequestId(requestId: string, type: WatcherTypeEnum): Promise<LensEntry[]>;
35
43
  paginate<T>(type: WatcherTypeEnum, { page, perPage }: PaginationParams, includeFullData?: boolean): Promise<{
36
44
  meta: {
@@ -31,6 +31,14 @@ declare class BetterSqliteStore extends Store {
31
31
  };
32
32
  data: T;
33
33
  }>;
34
+ getAllCacheEntries<T extends Omit<LensEntry, "data">[]>(pagination: PaginationParams): Promise<{
35
+ meta: {
36
+ total: number;
37
+ lastPage: number;
38
+ currentPage: number;
39
+ };
40
+ data: T;
41
+ }>;
34
42
  allByRequestId(requestId: string, type: WatcherTypeEnum): Promise<LensEntry[]>;
35
43
  paginate<T>(type: WatcherTypeEnum, { page, perPage }: PaginationParams, includeFullData?: boolean): Promise<{
36
44
  meta: {
@@ -1,11 +1,21 @@
1
1
  // src/abstracts/store.ts
2
2
  var Store = class {
3
+ stringifyData(data) {
4
+ if (typeof data === "string") {
5
+ return data;
6
+ }
7
+ try {
8
+ return JSON.stringify(data);
9
+ } catch (e) {
10
+ console.error(`Failed to stringify lens data: ${e}`);
11
+ }
12
+ }
3
13
  };
4
14
 
5
15
  // src/stores/better_sqlite.ts
6
16
  import { randomUUID } from "crypto";
7
17
  import Database from "libsql";
8
- import { sqlDateTime } from "@lensjs/date";
18
+ import { nowISO } from "@lensjs/date";
9
19
  var TABLE_NAME = "lens_entries";
10
20
  var BetterSqliteStore = class extends Store {
11
21
  connection;
@@ -22,11 +32,11 @@ var BetterSqliteStore = class extends Store {
22
32
  `INSERT INTO ${TABLE_NAME} (id, data, type, created_at, lens_entry_id, minimal_data) values($id, $data, $type, $created_at, $lens_entry_id, $minimalData)`
23
33
  ).run({
24
34
  id: entry.id ?? randomUUID(),
25
- data: JSON.stringify(entry.data),
35
+ data: this.stringifyData(entry.data),
26
36
  type: entry.type,
27
- created_at: entry.timestamp ?? sqlDateTime(),
37
+ created_at: entry.timestamp ?? nowISO(),
28
38
  lens_entry_id: entry.requestId || null,
29
- minimalData: JSON.stringify(entry.minimal_data ?? {})
39
+ minimalData: this.stringifyData(entry.minimal_data ?? {})
30
40
  });
31
41
  }
32
42
  async getAllQueries(pagination) {
@@ -35,6 +45,9 @@ var BetterSqliteStore = class extends Store {
35
45
  async getAllRequests(pagination) {
36
46
  return await this.paginate("request" /* REQUEST */, pagination, false);
37
47
  }
48
+ async getAllCacheEntries(pagination) {
49
+ return await this.paginate("cache" /* CACHE */, pagination);
50
+ }
38
51
  async allByRequestId(requestId, type) {
39
52
  const rows = this.connection.prepare(
40
53
  `${this.getSelectedColumns()} FROM ${TABLE_NAME} WHERE type = $type AND lens_entry_id = $requestId ORDER BY created_at DESC`
@@ -87,8 +100,13 @@ var BetterSqliteStore = class extends Store {
87
100
  CREATE INDEX IF NOT EXISTS lens_entries_id_type_index
88
101
  ON ${TABLE_NAME} (id, type);
89
102
  `;
103
+ const lensEntryIdIndex = `
104
+ CREATE INDEX IF NOT EXISTS lens_entry_id_index
105
+ ON ${TABLE_NAME} (lens_entry_id);
106
+ `;
90
107
  this.connection.exec(createTable);
91
108
  this.connection.exec(createIndex);
109
+ this.connection.exec(lensEntryIdIndex);
92
110
  }
93
111
  mapRow(row, includeFullData = true) {
94
112
  let data = includeFullData ? JSON.parse(row.data) : {};
@@ -36,6 +36,16 @@ module.exports = __toCommonJS(stores_exports);
36
36
 
37
37
  // src/abstracts/store.ts
38
38
  var Store = class {
39
+ stringifyData(data) {
40
+ if (typeof data === "string") {
41
+ return data;
42
+ }
43
+ try {
44
+ return JSON.stringify(data);
45
+ } catch (e) {
46
+ console.error(`Failed to stringify lens data: ${e}`);
47
+ }
48
+ }
39
49
  };
40
50
 
41
51
  // src/stores/better_sqlite.ts
@@ -58,11 +68,11 @@ var BetterSqliteStore = class extends Store {
58
68
  `INSERT INTO ${TABLE_NAME} (id, data, type, created_at, lens_entry_id, minimal_data) values($id, $data, $type, $created_at, $lens_entry_id, $minimalData)`
59
69
  ).run({
60
70
  id: entry.id ?? (0, import_crypto.randomUUID)(),
61
- data: JSON.stringify(entry.data),
71
+ data: this.stringifyData(entry.data),
62
72
  type: entry.type,
63
- created_at: entry.timestamp ?? (0, import_date.sqlDateTime)(),
73
+ created_at: entry.timestamp ?? (0, import_date.nowISO)(),
64
74
  lens_entry_id: entry.requestId || null,
65
- minimalData: JSON.stringify(entry.minimal_data ?? {})
75
+ minimalData: this.stringifyData(entry.minimal_data ?? {})
66
76
  });
67
77
  }
68
78
  async getAllQueries(pagination) {
@@ -71,6 +81,9 @@ var BetterSqliteStore = class extends Store {
71
81
  async getAllRequests(pagination) {
72
82
  return await this.paginate("request" /* REQUEST */, pagination, false);
73
83
  }
84
+ async getAllCacheEntries(pagination) {
85
+ return await this.paginate("cache" /* CACHE */, pagination);
86
+ }
74
87
  async allByRequestId(requestId, type) {
75
88
  const rows = this.connection.prepare(
76
89
  `${this.getSelectedColumns()} FROM ${TABLE_NAME} WHERE type = $type AND lens_entry_id = $requestId ORDER BY created_at DESC`
@@ -123,8 +136,13 @@ var BetterSqliteStore = class extends Store {
123
136
  CREATE INDEX IF NOT EXISTS lens_entries_id_type_index
124
137
  ON ${TABLE_NAME} (id, type);
125
138
  `;
139
+ const lensEntryIdIndex = `
140
+ CREATE INDEX IF NOT EXISTS lens_entry_id_index
141
+ ON ${TABLE_NAME} (lens_entry_id);
142
+ `;
126
143
  this.connection.exec(createTable);
127
144
  this.connection.exec(createIndex);
145
+ this.connection.exec(lensEntryIdIndex);
128
146
  }
129
147
  mapRow(row, includeFullData = true) {
130
148
  let data = includeFullData ? JSON.parse(row.data) : {};
@@ -1,11 +1,21 @@
1
1
  // src/abstracts/store.ts
2
2
  var Store = class {
3
+ stringifyData(data) {
4
+ if (typeof data === "string") {
5
+ return data;
6
+ }
7
+ try {
8
+ return JSON.stringify(data);
9
+ } catch (e) {
10
+ console.error(`Failed to stringify lens data: ${e}`);
11
+ }
12
+ }
3
13
  };
4
14
 
5
15
  // src/stores/better_sqlite.ts
6
16
  import { randomUUID } from "crypto";
7
17
  import Database from "libsql";
8
- import { sqlDateTime } from "@lensjs/date";
18
+ import { nowISO } from "@lensjs/date";
9
19
  var TABLE_NAME = "lens_entries";
10
20
  var BetterSqliteStore = class extends Store {
11
21
  connection;
@@ -22,11 +32,11 @@ var BetterSqliteStore = class extends Store {
22
32
  `INSERT INTO ${TABLE_NAME} (id, data, type, created_at, lens_entry_id, minimal_data) values($id, $data, $type, $created_at, $lens_entry_id, $minimalData)`
23
33
  ).run({
24
34
  id: entry.id ?? randomUUID(),
25
- data: JSON.stringify(entry.data),
35
+ data: this.stringifyData(entry.data),
26
36
  type: entry.type,
27
- created_at: entry.timestamp ?? sqlDateTime(),
37
+ created_at: entry.timestamp ?? nowISO(),
28
38
  lens_entry_id: entry.requestId || null,
29
- minimalData: JSON.stringify(entry.minimal_data ?? {})
39
+ minimalData: this.stringifyData(entry.minimal_data ?? {})
30
40
  });
31
41
  }
32
42
  async getAllQueries(pagination) {
@@ -35,6 +45,9 @@ var BetterSqliteStore = class extends Store {
35
45
  async getAllRequests(pagination) {
36
46
  return await this.paginate("request" /* REQUEST */, pagination, false);
37
47
  }
48
+ async getAllCacheEntries(pagination) {
49
+ return await this.paginate("cache" /* CACHE */, pagination);
50
+ }
38
51
  async allByRequestId(requestId, type) {
39
52
  const rows = this.connection.prepare(
40
53
  `${this.getSelectedColumns()} FROM ${TABLE_NAME} WHERE type = $type AND lens_entry_id = $requestId ORDER BY created_at DESC`
@@ -87,8 +100,13 @@ var BetterSqliteStore = class extends Store {
87
100
  CREATE INDEX IF NOT EXISTS lens_entries_id_type_index
88
101
  ON ${TABLE_NAME} (id, type);
89
102
  `;
103
+ const lensEntryIdIndex = `
104
+ CREATE INDEX IF NOT EXISTS lens_entry_id_index
105
+ ON ${TABLE_NAME} (lens_entry_id);
106
+ `;
90
107
  this.connection.exec(createTable);
91
108
  this.connection.exec(createIndex);
109
+ this.connection.exec(lensEntryIdIndex);
92
110
  }
93
111
  mapRow(row, includeFullData = true) {
94
112
  let data = includeFullData ? JSON.parse(row.data) : {};
@@ -26,6 +26,7 @@ module.exports = __toCommonJS(types_exports);
26
26
  var WatcherTypeEnum = /* @__PURE__ */ ((WatcherTypeEnum2) => {
27
27
  WatcherTypeEnum2["REQUEST"] = "request";
28
28
  WatcherTypeEnum2["QUERY"] = "query";
29
+ WatcherTypeEnum2["CACHE"] = "cache";
29
30
  return WatcherTypeEnum2;
30
31
  })(WatcherTypeEnum || {});
31
32
  // Annotate the CommonJS export names for ESM import in node:
@@ -11,6 +11,28 @@ type QueryEntry = {
11
11
  };
12
12
  requestId?: string;
13
13
  };
14
+ type CacheAction = "miss" | "hit" | "delete" | "clear" | "write";
15
+ type CacheEntry = {
16
+ action: "hit" | "write";
17
+ requestId?: string;
18
+ createdAt: string;
19
+ data: {
20
+ key: string;
21
+ value: any;
22
+ };
23
+ } | {
24
+ action: "clear";
25
+ requestId?: string;
26
+ createdAt: string;
27
+ data?: undefined | {};
28
+ } | {
29
+ action: "delete" | "miss";
30
+ requestId?: string;
31
+ createdAt: string;
32
+ data: {
33
+ key: string;
34
+ };
35
+ };
14
36
  type UserEntry = {
15
37
  id: number | string;
16
38
  name: string;
@@ -43,7 +65,8 @@ type Entry = {
43
65
  };
44
66
  declare enum WatcherTypeEnum {
45
67
  REQUEST = "request",
46
- QUERY = "query"
68
+ QUERY = "query",
69
+ CACHE = "cache"
47
70
  }
48
71
  type LensConfig = {
49
72
  basePath: string;
@@ -88,4 +111,4 @@ type ApiResponse<T> = {
88
111
  type HttpMethod = "GET" | "POST" | "PUT" | "DELETE" | "PATCH" | "HEAD" | "OPTIONS";
89
112
  type RouteHttpMethod = "get" | "post" | "put" | "delete" | "patch";
90
113
 
91
- export { type ApiResponse, type Entry, type HttpMethod, type LensConfig, type LensEntry, type PaginationParams, type Paginator, type QueryEntry, type QueryType, type RequestEntry, type RouteDefinition, type RouteDefinitionHandler, type RouteHttpMethod, type SqlQueryType, type UserEntry, WatcherTypeEnum };
114
+ export { type ApiResponse, type CacheAction, type CacheEntry, type Entry, type HttpMethod, type LensConfig, type LensEntry, type PaginationParams, type Paginator, type QueryEntry, type QueryType, type RequestEntry, type RouteDefinition, type RouteDefinitionHandler, type RouteHttpMethod, type SqlQueryType, type UserEntry, WatcherTypeEnum };
@@ -11,6 +11,28 @@ type QueryEntry = {
11
11
  };
12
12
  requestId?: string;
13
13
  };
14
+ type CacheAction = "miss" | "hit" | "delete" | "clear" | "write";
15
+ type CacheEntry = {
16
+ action: "hit" | "write";
17
+ requestId?: string;
18
+ createdAt: string;
19
+ data: {
20
+ key: string;
21
+ value: any;
22
+ };
23
+ } | {
24
+ action: "clear";
25
+ requestId?: string;
26
+ createdAt: string;
27
+ data?: undefined | {};
28
+ } | {
29
+ action: "delete" | "miss";
30
+ requestId?: string;
31
+ createdAt: string;
32
+ data: {
33
+ key: string;
34
+ };
35
+ };
14
36
  type UserEntry = {
15
37
  id: number | string;
16
38
  name: string;
@@ -43,7 +65,8 @@ type Entry = {
43
65
  };
44
66
  declare enum WatcherTypeEnum {
45
67
  REQUEST = "request",
46
- QUERY = "query"
68
+ QUERY = "query",
69
+ CACHE = "cache"
47
70
  }
48
71
  type LensConfig = {
49
72
  basePath: string;
@@ -88,4 +111,4 @@ type ApiResponse<T> = {
88
111
  type HttpMethod = "GET" | "POST" | "PUT" | "DELETE" | "PATCH" | "HEAD" | "OPTIONS";
89
112
  type RouteHttpMethod = "get" | "post" | "put" | "delete" | "patch";
90
113
 
91
- export { type ApiResponse, type Entry, type HttpMethod, type LensConfig, type LensEntry, type PaginationParams, type Paginator, type QueryEntry, type QueryType, type RequestEntry, type RouteDefinition, type RouteDefinitionHandler, type RouteHttpMethod, type SqlQueryType, type UserEntry, WatcherTypeEnum };
114
+ export { type ApiResponse, type CacheAction, type CacheEntry, type Entry, type HttpMethod, type LensConfig, type LensEntry, type PaginationParams, type Paginator, type QueryEntry, type QueryType, type RequestEntry, type RouteDefinition, type RouteDefinitionHandler, type RouteHttpMethod, type SqlQueryType, type UserEntry, WatcherTypeEnum };
@@ -2,6 +2,7 @@
2
2
  var WatcherTypeEnum = /* @__PURE__ */ ((WatcherTypeEnum2) => {
3
3
  WatcherTypeEnum2["REQUEST"] = "request";
4
4
  WatcherTypeEnum2["QUERY"] = "query";
5
+ WatcherTypeEnum2["CACHE"] = "cache";
5
6
  return WatcherTypeEnum2;
6
7
  })(WatcherTypeEnum || {});
7
8
  export {
@@ -0,0 +1 @@
1
+ import{j as r}from"./index-BdvbrZNf.js";const d=({action:e})=>{const t={hit:"bg-green-100 text-green-800 dark:bg-green-600 dark:text-white",miss:"bg-amber-100 text-amber-800 dark:bg-amber-600 dark:text-white",write:"bg-blue-100 text-blue-800 dark:bg-blue-600 dark:text-white",delete:"bg-red-100 text-red-800 dark:bg-red-600 dark:text-white",clear:"bg-gray-100 text-gray-800 dark:bg-gray-600 dark:text-white"};return r.jsx("span",{className:`rounded px-2 py-1 text-sm font-semibold ${t[e]||t.clear}`,children:e})};export{d as C};
@@ -0,0 +1 @@
1
+ import{j as a}from"./index-BdvbrZNf.js";import{L as s}from"./LoadMore-DHOrhPsi.js";import{T as t}from"./Table-D1Kpw7PA.js";import{g as r}from"./columns-BIDLCW64.js";import"./index-CpP2Ap5X.js";import"./CacheActionBadge-3jjmNjC6.js";const p=({hasMoreObject:o})=>a.jsxs("div",{className:"w-full",children:[a.jsx("div",{className:"overflow-x-auto",children:a.jsx(t,{columns:r(),data:o.data})}),a.jsx(s,{paginatedPage:o})]});export{p as default};
@@ -0,0 +1,2 @@
1
+ const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["./CacheEntriesTable-DPLre6br.js","./index-BdvbrZNf.js","./index-C04tuZDI.css","./LoadMore-DHOrhPsi.js","./Table-D1Kpw7PA.js","./columns-BIDLCW64.js","./index-CpP2Ap5X.js","./CacheActionBadge-3jjmNjC6.js"])))=>i.map(i=>d[i]);
2
+ import{r as t,j as a,_ as s}from"./index-BdvbrZNf.js";import{u as i}from"./useLoadMore-twYxPJ-d.js";import{u as m}from"./useCacheEntries-vuHEIj6E.js";import"./useLensApi-Bzmx8hps.js";const n=t.lazy(()=>s(()=>import("./CacheEntriesTable-DPLre6br.js"),__vite__mapDeps([0,1,2,3,4,5,6,7]),import.meta.url)),_=()=>{const{loadMoreItems:e,getItems:r}=m(),o=i({paginatedPage:e});return t.useEffect(()=>{r()},[]),a.jsx(n,{hasMoreObject:o})};export{_ as default};
@@ -0,0 +1 @@
1
+ import{j as a,L as s,q as i,k as r}from"./index-BdvbrZNf.js";import{D as n,T as o,J as u}from"./TabbedDataViewer-CNSEhc6h.js";import{C as d}from"./CacheActionBadge-3jjmNjC6.js";function y({data:e}){const t=[e.lens_entry_id?{label:"Request",value:a.jsx(s,{to:`${i(r()).REQUESTS}/${e.lens_entry_id}`,className:"text-blue-600 hover:underline font-semibold",children:"View Request"}),className:"text-gray-900 dark:text-gray-100"}:null,{label:"Operation",value:a.jsx(d,{action:e.data.action}),className:"text-gray-900 dark:text-gray-100"},e.data.data.key?{label:"Key",value:e.data.data.key??"__",className:"text-gray-900 dark:text-gray-100"}:null].filter(l=>!!l);return a.jsxs("div",{className:"flex flex-col gap-4",children:[a.jsx(n,{title:"Details",items:t}),a.jsx(o,{tabs:[{id:"value",label:"Value",shouldShow:!!e.data.data.value,content:a.jsx(u,{data:e.data.data.value})}],defaultActiveTab:"value"})]})}export{y as default};
@@ -0,0 +1,2 @@
1
+ const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["./CacheEntryDetails-CHt_pNTk.js","./index-BdvbrZNf.js","./index-C04tuZDI.css","./TabbedDataViewer-CNSEhc6h.js","./CacheActionBadge-3jjmNjC6.js"])))=>i.map(i=>d[i]);
2
+ import{m as o,r as s,j as r,_ as i}from"./index-BdvbrZNf.js";import{u as m}from"./useCacheEntries-vuHEIj6E.js";import"./useLensApi-Bzmx8hps.js";const n=s.lazy(()=>i(()=>import("./CacheEntryDetails-CHt_pNTk.js"),__vite__mapDeps([0,1,2,3,4]),import.meta.url)),E=()=>{const{item:e,getItem:a}=m(),{id:t}=o();return s.useEffect(()=>{t&&a(t)},[t]),r.jsx("div",{children:e&&r.jsx(n,{data:e})})};export{E as default};
@@ -0,0 +1 @@
1
+ import{j as o}from"./index-BdvbrZNf.js";import{t}from"./Table-D1Kpw7PA.js";function n({paginatedPage:r}){return r.hasMore?o.jsx("div",{className:"flex justify-center p-4",children:o.jsx("button",{onClick:r.loadMore,disabled:r.loading,className:t("px-4 py-2 rounded-md bg-gray-200 text-gray-800 dark:bg-neutral-800 dark:text-white text-sm hover:bg-gray-300 dark:hover:bg-neutral-700 transition-colors",r.loading&&"opacity-50 cursor-not-allowed"),children:r.loading?"Loading...":"Load More"})}):null}export{n as L};
@@ -0,0 +1,2 @@
1
+ const __vite__mapDeps=(i,m=__vite__mapDeps,d=(m.f||(m.f=["./QueryTable-BXSzT-Cm.js","./index-BdvbrZNf.js","./index-C04tuZDI.css","./LoadMore-DHOrhPsi.js","./Table-D1Kpw7PA.js","./columns-jYfhBxOM.js","./index-CpP2Ap5X.js"])))=>i.map(i=>d[i]);
2
+ import{r as e,j as s,_ as a}from"./index-BdvbrZNf.js";import{u as i}from"./useQueries-BYFLoUQR.js";import{u}from"./useLoadMore-twYxPJ-d.js";import"./useLensApi-Bzmx8hps.js";const m=e.lazy(()=>a(()=>import("./QueryTable-BXSzT-Cm.js"),__vite__mapDeps([0,1,2,3,4,5,6]),import.meta.url)),f=()=>{const{loadMoreRequests:r,fetchQueries:t}=i(),o=u({paginatedPage:r});return e.useEffect(()=>{t()},[]),s.jsx(m,{hasMoreObject:o})};export{f as default};