@object-ui/data-objectstack 17.5.0 → 17.7.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 (53) hide show
  1. package/CHANGELOG.md +2311 -0
  2. package/README.md +557 -11
  3. package/dist/index.cjs +1663 -463
  4. package/dist/index.d.cts +1780 -518
  5. package/dist/index.d.ts +1780 -518
  6. package/dist/index.js +1648 -457
  7. package/package.json +9 -9
  8. package/dist/tsconfig.tsbuildinfo +0 -1
  9. package/src/aggregate-capability.test.ts +0 -177
  10. package/src/apiAccessDenied.test.ts +0 -233
  11. package/src/appAccessProbe.test.ts +0 -147
  12. package/src/bulkDelete.test.ts +0 -75
  13. package/src/bulkUpdate.test.ts +0 -93
  14. package/src/cache/MetadataCache.test.ts +0 -477
  15. package/src/cache/MetadataCache.ts +0 -289
  16. package/src/cloud-surface-retired-4152.pin.test.ts +0 -171
  17. package/src/connection.test.ts +0 -188
  18. package/src/contracts.ts +0 -115
  19. package/src/deleteView.homes.test.ts +0 -389
  20. package/src/deleteViewContract.types.test.ts +0 -246
  21. package/src/errors.test.ts +0 -426
  22. package/src/errors.ts +0 -293
  23. package/src/exportDownload.test.ts +0 -141
  24. package/src/filter-entry-translation.test.ts +0 -360
  25. package/src/filter-operator-ast-parity.test.ts +0 -135
  26. package/src/getObjectSchema.test.ts +0 -145
  27. package/src/httpFailureLogging.test.ts +0 -109
  28. package/src/importJob.test.ts +0 -71
  29. package/src/index.ts +0 -4442
  30. package/src/integration.ts +0 -200
  31. package/src/listViewOverrides.test.ts +0 -241
  32. package/src/listViews.test.ts +0 -175
  33. package/src/metadata-client.get-envelope.test.ts +0 -171
  34. package/src/metadata-client.saveAdvisories.test.ts +0 -226
  35. package/src/metadata-client.test.ts +0 -303
  36. package/src/metadata-client.ts +0 -1046
  37. package/src/occ.test.ts +0 -101
  38. package/src/onMutation.test.ts +0 -589
  39. package/src/onSaveAdvisory.test.ts +0 -311
  40. package/src/onWriteWarning.test.ts +0 -273
  41. package/src/orderby-serialization.test.ts +0 -115
  42. package/src/queryDataset.test.ts +0 -543
  43. package/src/searchAll.test.ts +0 -120
  44. package/src/security.ts +0 -243
  45. package/src/spec-symbol-batch6.test.ts +0 -326
  46. package/src/studio.ts +0 -152
  47. package/src/updateView.draft.test.ts +0 -242
  48. package/src/userState.test.ts +0 -315
  49. package/src/userState.ts +0 -238
  50. package/src/v3-compat.test.ts +0 -229
  51. package/src/validation-error.test.ts +0 -94
  52. package/src/viewCacheInvalidation.pin.test.ts +0 -260
  53. package/src/viewInvalidationSeam.pin.test.ts +0 -162
@@ -1,162 +0,0 @@
1
- /**
2
- * ObjectUI
3
- * Copyright (c) 2024-present ObjectStack Inc.
4
- *
5
- * This source code is licensed under the MIT license found in the
6
- * LICENSE file in the root directory of this source tree.
7
- */
8
-
9
- import { describe, it, expect, vi } from 'vitest';
10
- import ts from 'typescript';
11
- import { ObjectStackAdapter } from './index';
12
-
13
- /**
14
- * `invalidateViewKeys` is the ONE place that knows the view cache key set
15
- * (objectui#4373).
16
- *
17
- * The behavioural half of this rule is already pinned next door, in
18
- * `viewCacheInvalidation.pin.test.ts`: eight cases assert the exact key list
19
- * every adapter write path emits. Those eight are deliberately unchanged by
20
- * #4373 — routing the four paths through a seam must change nothing they can
21
- * observe, and their staying green IS the refactor's acceptance evidence.
22
- *
23
- * But that is also their blind spot. A future edit that re-inlines
24
- * ``this.metadataCache.invalidate?.(`view-overrides:${objectName}`)`` back into
25
- * one write path emits the identical keys in the identical order, so every one
26
- * of those eight stays green while the seam quietly stops being the single
27
- * source of truth — and the next writer after that inherits a key list to
28
- * forget. That is not a hypothetical failure mode, it is the repo's measured
29
- * history: objectui#3778 removed five restated copies of a key no reader ever
30
- * populated, objectui#4363 fixed four restated copies that named half the live
31
- * set, and objectui#4373 is the third instalment — a writer OUTSIDE this class
32
- * (the console's create/publish flow through app-shell's ADR-0034 seam) that
33
- * never learned the key list at all.
34
- *
35
- * So the guard has to be structural, and the assertions below are on the SOURCE
36
- * TEXT of `index.ts`:
37
- *
38
- * | key template | may appear exactly twice |
39
- * |-----------------------|-------------------------------------------------|
40
- * | `` `view:${…}:${…}` `` | the `getView` READ + the seam |
41
- * | `` `view-overrides:${…}` ``| the `listViewOverrides` READ + the seam |
42
- *
43
- * Two, not one: a reader must spell the key it caches under — that is where the
44
- * key is *defined*. What must not recur is a THIRD spelling, because the only
45
- * thing a third spelling can be is a writer restating what the seam already
46
- * knows. Re-inline any write path's key list and the count goes to three.
47
- *
48
- * If this goes red on a legitimate change: adding a new cached view-shaped READ
49
- * is the one case that raises a count honestly — pin the new reader here (and
50
- * teach {@link ObjectStackAdapter.invalidateViewKeys} to drop its key), rather
51
- * than relaxing the assertion to "at most N".
52
- */
53
-
54
- /**
55
- * Read through `ts.sys`, not `node:fs` — the convention this package's
56
- * `cloud-surface-retired-4152.pin.test.ts` records and explains: `tsconfig.json`
57
- * compiles the whole test tree here, and keeping `@types/node` out of a
58
- * browser-side adapter's type environment is deliberate. TypeScript's own
59
- * system host is typed by the `typescript` devDependency.
60
- */
61
- const INDEX_TS = new URL(import.meta.url).pathname.replace(/[^/]+$/, 'index.ts');
62
- const adapterSrc = (() => {
63
- const raw = ts.sys.readFile(INDEX_TS);
64
- if (!raw) throw new Error(`cannot read ${INDEX_TS}`);
65
- return raw;
66
- })();
67
-
68
- /**
69
- * Code occurrences only. Both keys are also written out in prose in this
70
- * file's neighbours and in `index.ts`'s own doc comments, in the placeholder
71
- * form `view-overrides:{object}` — documentation is not a second source of
72
- * truth and must not be counted as one. Requiring the `${` interpolation
73
- * marker separates the two exactly.
74
- */
75
- const PER_VIEW_KEY = /`view:\$\{/g;
76
- const OVERRIDE_MAP_KEY = /`view-overrides:\$\{/g;
77
-
78
- function count(re: RegExp, src: string): number {
79
- return src.match(re)?.length ?? 0;
80
- }
81
-
82
- describe('the view cache key set has exactly one owner (objectui#4373)', () => {
83
- it('is reading real source, not an empty string', () => {
84
- // Premise guard: a path typo would make every count 0, and every
85
- // assertion below would pass by reading nothing.
86
- expect(adapterSrc.length).toBeGreaterThan(10_000);
87
- expect(adapterSrc).toContain('invalidateViewKeys(objectName: string, viewName: string): void');
88
- });
89
-
90
- it('spells `view:{object}:{name}` exactly twice — the getView read, and the seam', () => {
91
- expect(count(PER_VIEW_KEY, adapterSrc)).toBe(2);
92
- });
93
-
94
- it('spells `view-overrides:{object}` exactly twice — the listViewOverrides read, and the seam', () => {
95
- expect(count(OVERRIDE_MAP_KEY, adapterSrc)).toBe(2);
96
- });
97
-
98
- it('no write path names a view cache key itself — they all call the seam', () => {
99
- // The complementary statement of the two counts, asserted where a reader
100
- // will look for it: every `invalidate` call in the adapter that concerns a
101
- // view goes through `invalidateViewKeys`, so the ONLY `metadataCache
102
- // .invalidate` lines naming a view key are the seam's own two.
103
- const invalidateLines = adapterSrc
104
- .split('\n')
105
- .filter((l: string) => l.includes('metadataCache.invalidate'))
106
- .filter((l: string) => /`view(-overrides)?:/.test(l));
107
-
108
- expect(invalidateLines.map((l: string) => l.trim())).toEqual([
109
- 'this.metadataCache.invalidate?.(`view:${objectName}:${viewName}`);',
110
- 'this.metadataCache.invalidate?.(`view-overrides:${objectName}`);',
111
- ]);
112
- });
113
- });
114
-
115
- describe('invalidateViewKeys — the seam itself', () => {
116
- function makeAdapter() {
117
- const invalidated: string[] = [];
118
- const ds: any = new ObjectStackAdapter({
119
- baseUrl: 'http://test.local',
120
- fetch: vi.fn(async () =>
121
- new Response(JSON.stringify({ success: true, data: { capabilities: {}, routes: {} } }), {
122
- status: 200,
123
- headers: { 'Content-Type': 'application/json' },
124
- }),
125
- ),
126
- });
127
- ds.metadataCache = { invalidate: (key: string) => invalidated.push(key) };
128
- return { ds: ds as ObjectStackAdapter, invalidated };
129
- }
130
-
131
- it('drops the per-view key then the object override map, in that order', () => {
132
- const { ds, invalidated } = makeAdapter();
133
-
134
- ds.invalidateViewKeys('account', 'account.mine');
135
-
136
- expect(invalidated).toEqual(['view:account:account.mine', 'view-overrides:account']);
137
- });
138
-
139
- it('takes a qualified `<object>.<key>` name as-is — it is a row key, not a path', () => {
140
- // The console's runtime-created views are named `<object>.<key>`
141
- // (`viewEnvelope`, app-shell). Splitting that on `.` would key the cache
142
- // under something no reader asks for, which is the objectui#3774 class of
143
- // bug one rename later.
144
- const { ds, invalidated } = makeAdapter();
145
-
146
- ds.invalidateViewKeys('account', 'account.top_deals');
147
-
148
- expect(invalidated[0]).toBe('view:account:account.top_deals');
149
- });
150
-
151
- it('is callable from outside the class — the writers are not all in it', () => {
152
- // The seam is public because app-shell's ADR-0034 persistence module and
153
- // `MetadataService` write the same rows. A structural (non-class) caller
154
- // must be able to hold it; this is that call shape.
155
- const { ds, invalidated } = makeAdapter();
156
- const seam: { invalidateViewKeys(o: string, v: string): void } = ds;
157
-
158
- seam.invalidateViewKeys('lead', 'lead.hot');
159
-
160
- expect(invalidated).toEqual(['view:lead:lead.hot', 'view-overrides:lead']);
161
- });
162
- });