Skip to content

Commit 26e6970

Browse files
committed
fix(spec): the D3 filter-rule-array entry states the per-door refusal and the TODO listing
Claude-Session: https://claude.ai/code/session_01CiCTczDo7tGhafXjf61dUJ Co-authored-by: Claude <noreply@anthropic.com>
1 parent 4a86b39 commit 26e6970

2 files changed

Lines changed: 18 additions & 5 deletions

File tree

‎packages/metadata-protocol/src/protocol.stored-migration.test.ts‎

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -767,7 +767,11 @@ describe('migrateStoredMetadata — a site the chain leaves as stored is a TODO,
767767
grid({ stage: 'open' }),
768768
{ type: 'object-kanban', dataSource: { object: 'deal', filter: COMBINATOR }, properties: { objectName: 'deal' } },
769769
]);
770-
const { engine, tables } = makeStubEngine([mixedPage, bindingMixed]);
770+
// The third door: `defaultFilters` on the grid, the same open bag.
771+
const defaultsMixed = pageRow('deal_grid', [
772+
{ type: 'object-grid', properties: { objectName: 'deal', filter: { stage: 'open' }, defaultFilters: COMBINATOR } },
773+
]);
774+
const { engine, tables } = makeStubEngine([mixedPage, bindingMixed, defaultsMixed]);
771775
const protocol = new ObjectStackProtocolImplementation(engine);
772776

773777
const report = await protocol.migrateStoredMetadata({ apply: true });
@@ -778,6 +782,11 @@ describe('migrateStoredMetadata — a site the chain leaves as stored is a TODO,
778782
const binding = report.rows.find((r) => r.name === 'deal_room')!;
779783
expect(binding.outcome).toBe('failed');
780784
expect(binding.todos.map((t) => t.path)).toEqual(['pages[0].regions[0].components[1].dataSource.filter']);
785+
const defaults = report.rows.find((r) => r.name === 'deal_grid')!;
786+
expect(defaults.outcome).toBe('rewritten');
787+
expect(defaults.todos.map((t) => t.path)).toEqual(['pages[0].regions[0].components[0].properties.defaultFilters']);
788+
const storedDefaults = JSON.parse(metaRows(tables).find((r) => r.name === 'deal_grid')!.metadata);
789+
expect(storedDefaults.regions[0].components[0].properties.defaultFilters).toEqual(COMBINATOR);
781790

782791
// The rewritten row persisted its lossless half; the combinator is byte-identical.
783792
const stored = JSON.parse(metaRows(tables).find((r) => r.name === 'deal_desk')!.metadata);

‎packages/spec/src/migrations/entries/semantic/18.element-data-source-and-object-block-filter-rule-array.ts‎

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -76,10 +76,14 @@ export const entry: SemanticMigration = {
7676
+ 'their own rows in an in-memory data source that reads the record form and excludes '
7777
+ 'EVERY row for a rule array, so a rewrite there would empty the block. Such a row keeps loading unchanged '
7878
+ '(`applyConversionsToStoredItem` replays the chain without validating, by its own '
79-
+ 'contract) and is refused at the `filter` door on its next save — for a combinator '
80-
+ 'record, a refusal that names the combinator and says why no rule spells it. '
81-
+ '`os migrate meta --stored` does not list these rows yet: a row the conversion leaves '
82-
+ 'as stored reports there as already on protocol.',
79+
+ 'contract), and its `filter` door refuses the form: at `dataSource.filter` on the page\'s '
80+
+ 'next save; at a block\'s `properties.filter` — like `properties.defaultFilters`, a key of '
81+
+ 'the open `properties` bag — only as the component-props gate\'s advisory finding '
82+
+ '(`os validate`), since a re-save through the metadata API is not refused there. For a '
83+
+ 'combinator record that refusal names the combinator and says why no rule spells it. '
84+
+ '`os migrate meta --stored` lists each filter left as stored as a TODO under its row, '
85+
+ 'naming the block and what blocks the rewrite; a row whose only finding is such a TODO is '
86+
+ 'reported `skipped`, and the run\'s exit code does not change for it.',
8387
acceptanceCriteria:
8488
'`ElementDataSourceSchema.safeParse({ object, filter: [{ field: \'status\', operator: '
8589
+ '\'equals\', value: \'active\' }] })` succeeds and the parsed `filter` is the same rule '

0 commit comments

Comments
 (0)