import {expect, test} from 'vitest'; import Arbitrary from './arbitrary.js'; import Query from './query.js'; import Schema from './schema.js'; function wrapSpecification(name, specification) { return class Component extends Arbitrary { static name = name; static schema = new Schema({ type: 'object', properties: specification, }); }; } const A = new (wrapSpecification('A', {a: {type: 'int32', defaultValue: 420}})); const B = new (wrapSpecification('B', {b: {type: 'int32', defaultValue: 69}})); const C = new (wrapSpecification('C', {c: {type: 'int32'}})); const Components = {A, B, C}; Components.A.createMany([[2], [3]]); Components.B.createMany([[1], [2]]); Components.C.createMany([[2], [4]]); function testQuery(parameters, expected) { const query = new Query(parameters, Components); query.reindex([1, 2, 3]); expect(query.count) .to.equal(expected.length); for (const _ of query.select()) { expect(_.length) .to.equal(parameters.filter((spec) => '!'.charCodeAt(0) !== spec.charCodeAt(0)).length + 1); expect(expected.includes(_.pop())) .to.equal(true); } } test('can query all', () => { testQuery([], [1, 2, 3]); }); test('can query some', () => { testQuery(['A'], [2, 3]); testQuery(['A', 'B'], [2]); }); test('can query excluding', () => { testQuery(['!A'], [1]); testQuery(['A', '!B'], [3]); }); test('can deindex', () => { const query = new Query(['A'], Components); query.reindex([1, 2, 3]); expect(query.count) .to.equal(2); query.deindex([2]); expect(query.count) .to.equal(1); }); test('can reindex', () => { const Test = new (wrapSpecification('Test', {a: {type: 'int32', defaultValue: 420}})); Test.createMany([[2], [3]]); const query = new Query(['Test'], {Test}); query.reindex([2, 3]); expect(query.count) .to.equal(2); Test.destroy(2); query.reindex([2, 3]); expect(query.count) .to.equal(1); }); test('can select', () => { const query = new Query(['A'], Components); query.reindex([1, 2, 3]); const it = query.select(); const result = it.next(); expect(result.value[0].a) .to.equal(420); });