import assert from 'node:assert/strict'; import { mkdtempSync, rmSync } from 'node:fs'; import { tmpdir } from 'node:os'; import { join } from 'node:path'; import LibDashStore from '../src/index.js'; import { BetterSqlite3Provider } from '../src/providers/sqlite3/index.js'; async function run() { console.log('--- Testing Quote Summary & Filtering in dashdbschema ---'); const tempDir = mkdtempSync(join(tmpdir(), 'test-quote-summary-')); const dbFile = join(tempDir, 'test.db'); const storageDir = join(tempDir, 'storage'); const provider = new BetterSqlite3Provider({ filename: dbFile, storageDir, }); await provider.initialize(); const store = await new LibDashStore(provider); try { const googleAuthId = await store.google_auth.add('quote-summary-test@example.com'); const company = await store.company.create({ name: 'Quote Test Corp', iso639: 'de', taxrate: 19, reducedtaxrate: 7, googleAuthId, }); await store.google_auth.setSelectedCompany(googleAuthId, company.id); const groups = await store.customergroup.list(googleAuthId); const customerAlice = await store.entity.create(googleAuthId, { customergroupId: groups[0].id, firstName: 'Alice', name: 'Wonderland', }); const customerBob = await store.entity.create(googleAuthId, { customergroupId: groups[0].id, firstName: 'Bob', name: 'Builder', }); const art = await store.article.createUnderParent({ googleAuthId, parentId: company.rootCategoryId, name: 'Gadget', track_stock: 0, }); // 1. Create quote 1: Alice, Q-1001, 2 items of 100 net @ 19% tax => 238 gross, 2 total quantity const quote1 = await store.quote.create(googleAuthId, { number: 'Q-1001', date: '2026-08-01T10:00:00Z', entityId: customerAlice.id, lines: [{ sku: art.sku, name: 'Gadget', amount: 2, net: 100, taxrate: 19 }], }); assert.equal(quote1.number, 'Q-1001'); // Verify row in quotesummary table directly const directRows1 = provider.db.prepare('SELECT * FROM quotesummary WHERE manifest_id = ?').all(quote1.id); assert.equal(directRows1.length, 1); assert.equal(directRows1[0].quote_number, 'Q-1001'); assert.equal(directRows1[0].customer_name, 'Alice Wonderland'); assert.equal(directRows1[0].positions, 1); assert.equal(directRows1[0].gross_total, 238); assert.equal(directRows1[0].total_quantity, 2); // 2. Create quote 2: Bob, Q-1002, 3 items of 50 net @ 19% tax => 178.50 gross, 3 total quantity const quote2 = await store.quote.create(googleAuthId, { number: 'Q-1002', date: '2026-10-01T10:00:00Z', entityId: customerBob.id, lines: [{ sku: art.sku, name: 'Gadget', amount: 3, net: 50, taxrate: 19 }], }); // Test quote.list unpaged const unpaged = await store.quote.list(googleAuthId); assert.equal(unpaged.length, 2); const q1 = unpaged.find((q) => q.id === quote1.id); assert.equal(q1.positions, 1); assert.equal(q1.grossTotal, 238); assert.equal(q1.totalQuantity, 2); assert.equal(q1.customerName, 'Alice Wonderland'); // Test quote.list paged with search const searchAlice = await store.quote.list(googleAuthId, { search: 'Alice' }); assert.equal(searchAlice.total, 1); assert.equal(searchAlice.unfilteredTotal, 2); assert.equal(searchAlice.quotes[0].number, 'Q-1001'); const searchNumber = await store.quote.list(googleAuthId, { search: '1002' }); assert.equal(searchNumber.total, 1); assert.equal(searchNumber.quotes[0].number, 'Q-1002'); // Test quote.update updates summary await store.quote.update(googleAuthId, quote1.id, { lines: [ { sku: art.sku, name: 'Gadget', amount: 5, net: 100, taxrate: 19 }, { sku: art.sku, name: 'Gadget 2', amount: 1, net: 10, taxrate: 19 }, ], }); const updatedSummary = provider.db.prepare('SELECT * FROM quotesummary WHERE manifest_id = ?').get(quote1.id); assert.equal(updatedSummary.positions, 2); assert.equal(updatedSummary.total_quantity, 6); // (5 * 100 * 1.19) + (1 * 10 * 1.19) = 595 + 11.9 = 606.90 assert.equal(updatedSummary.gross_total, 606.9); // Test rebuildSummaries provider.db.prepare('DELETE FROM quotesummary').run(); const countBeforeRebuild = provider.db.prepare('SELECT COUNT(*) as cnt FROM quotesummary').get().cnt; assert.equal(countBeforeRebuild, 0); const rebuildRes = await store.quote.rebuildSummaries(googleAuthId); assert.equal(rebuildRes.ok, true); const countAfterRebuild = provider.db.prepare('SELECT COUNT(*) as cnt FROM quotesummary').get().cnt; assert.equal(countAfterRebuild, 2); const rebuiltQ1 = provider.db.prepare('SELECT * FROM quotesummary WHERE manifest_id = ?').get(quote1.id); assert.equal(rebuiltQ1.positions, 2); assert.equal(rebuiltQ1.total_quantity, 6); assert.equal(rebuiltQ1.gross_total, 606.9); // Test delete cascade await store.quote.delete(googleAuthId, quote1.id); const countAfterDelete = provider.db.prepare('SELECT COUNT(*) as cnt FROM quotesummary WHERE manifest_id = ?').get(quote1.id); assert.equal(countAfterDelete.cnt, 0); console.log('--- ALL QUOTE SUMMARY TESTS PASSED ---'); } finally { try { rmSync(tempDir, { recursive: true, force: true }); } catch {} } } run().catch((err) => { console.error('Test failed:', err); process.exit(1); });