@object-ui/data-objectstack 17.5.0 → 17.6.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 (52) hide show
  1. package/CHANGELOG.md +219 -0
  2. package/dist/index.cjs +262 -357
  3. package/dist/index.d.cts +385 -448
  4. package/dist/index.d.ts +385 -448
  5. package/dist/index.js +258 -350
  6. package/package.json +5 -6
  7. package/dist/tsconfig.tsbuildinfo +0 -1
  8. package/src/aggregate-capability.test.ts +0 -177
  9. package/src/apiAccessDenied.test.ts +0 -233
  10. package/src/appAccessProbe.test.ts +0 -147
  11. package/src/bulkDelete.test.ts +0 -75
  12. package/src/bulkUpdate.test.ts +0 -93
  13. package/src/cache/MetadataCache.test.ts +0 -477
  14. package/src/cache/MetadataCache.ts +0 -289
  15. package/src/cloud-surface-retired-4152.pin.test.ts +0 -171
  16. package/src/connection.test.ts +0 -188
  17. package/src/contracts.ts +0 -115
  18. package/src/deleteView.homes.test.ts +0 -389
  19. package/src/deleteViewContract.types.test.ts +0 -246
  20. package/src/errors.test.ts +0 -426
  21. package/src/errors.ts +0 -293
  22. package/src/exportDownload.test.ts +0 -141
  23. package/src/filter-entry-translation.test.ts +0 -360
  24. package/src/filter-operator-ast-parity.test.ts +0 -135
  25. package/src/getObjectSchema.test.ts +0 -145
  26. package/src/httpFailureLogging.test.ts +0 -109
  27. package/src/importJob.test.ts +0 -71
  28. package/src/index.ts +0 -4442
  29. package/src/integration.ts +0 -200
  30. package/src/listViewOverrides.test.ts +0 -241
  31. package/src/listViews.test.ts +0 -175
  32. package/src/metadata-client.get-envelope.test.ts +0 -171
  33. package/src/metadata-client.saveAdvisories.test.ts +0 -226
  34. package/src/metadata-client.test.ts +0 -303
  35. package/src/metadata-client.ts +0 -1046
  36. package/src/occ.test.ts +0 -101
  37. package/src/onMutation.test.ts +0 -589
  38. package/src/onSaveAdvisory.test.ts +0 -311
  39. package/src/onWriteWarning.test.ts +0 -273
  40. package/src/orderby-serialization.test.ts +0 -115
  41. package/src/queryDataset.test.ts +0 -543
  42. package/src/searchAll.test.ts +0 -120
  43. package/src/security.ts +0 -243
  44. package/src/spec-symbol-batch6.test.ts +0 -326
  45. package/src/studio.ts +0 -152
  46. package/src/updateView.draft.test.ts +0 -242
  47. package/src/userState.test.ts +0 -315
  48. package/src/userState.ts +0 -238
  49. package/src/v3-compat.test.ts +0 -229
  50. package/src/validation-error.test.ts +0 -94
  51. package/src/viewCacheInvalidation.pin.test.ts +0 -260
  52. 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
- });