@rotorsoft/act-tck 1.1.0 → 1.3.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.
- package/dist/.tsbuildinfo +1 -1
- package/dist/@types/store-tck.d.ts.map +1 -1
- package/dist/index.cjs +110 -39
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +117 -40
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
package/dist/index.js
CHANGED
|
@@ -189,7 +189,13 @@ var runLoggerTck = (options) => {
|
|
|
189
189
|
};
|
|
190
190
|
|
|
191
191
|
// src/store-tck.ts
|
|
192
|
-
import {
|
|
192
|
+
import {
|
|
193
|
+
act,
|
|
194
|
+
ConcurrencyError,
|
|
195
|
+
InMemoryCache,
|
|
196
|
+
SNAP_EVENT,
|
|
197
|
+
TOMBSTONE_EVENT
|
|
198
|
+
} from "@rotorsoft/act";
|
|
193
199
|
import { afterAll, beforeAll, describe as describe3, expect as expect3, it as it3 } from "vitest";
|
|
194
200
|
var runStoreTck = (options) => {
|
|
195
201
|
describe3(`TCK / Store / ${options.name}`, () => {
|
|
@@ -1509,10 +1515,20 @@ var runStoreTck = (options) => {
|
|
|
1509
1515
|
await store.drop();
|
|
1510
1516
|
await store.seed();
|
|
1511
1517
|
});
|
|
1512
|
-
const asSource = (
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1518
|
+
const asSource = (events) => ({
|
|
1519
|
+
async query(callback) {
|
|
1520
|
+
for (const e of events)
|
|
1521
|
+
await Promise.resolve(
|
|
1522
|
+
callback(
|
|
1523
|
+
e
|
|
1524
|
+
)
|
|
1525
|
+
);
|
|
1526
|
+
return events.length;
|
|
1527
|
+
},
|
|
1528
|
+
async dispose() {
|
|
1529
|
+
}
|
|
1530
|
+
});
|
|
1531
|
+
const event = (originalId, stream, version, name, created, data = {}) => ({
|
|
1516
1532
|
id: originalId,
|
|
1517
1533
|
name,
|
|
1518
1534
|
data,
|
|
@@ -1521,11 +1537,20 @@ var runStoreTck = (options) => {
|
|
|
1521
1537
|
created,
|
|
1522
1538
|
meta: { correlation: "restore-tck", causation: {} }
|
|
1523
1539
|
});
|
|
1540
|
+
const restore = async (source, opts = {}) => {
|
|
1541
|
+
const cache = new InMemoryCache();
|
|
1542
|
+
const app = act().build({ scoped: { store, cache } });
|
|
1543
|
+
try {
|
|
1544
|
+
return await app.restore(source, opts);
|
|
1545
|
+
} finally {
|
|
1546
|
+
await source.dispose();
|
|
1547
|
+
await cache.dispose();
|
|
1548
|
+
}
|
|
1549
|
+
};
|
|
1524
1550
|
it3("returns kept=0 on an empty source", async () => {
|
|
1525
|
-
const result = await
|
|
1551
|
+
const result = await restore(asSource([]));
|
|
1526
1552
|
expect3(result.kept).toBe(0);
|
|
1527
1553
|
expect3(result.duration_ms).toBeGreaterThanOrEqual(0);
|
|
1528
|
-
expect3(result.dry_run).toBe(false);
|
|
1529
1554
|
expect3(result.dropped).toEqual({
|
|
1530
1555
|
closed_streams: 0,
|
|
1531
1556
|
snapshots: 0,
|
|
@@ -1539,12 +1564,12 @@ var runStoreTck = (options) => {
|
|
|
1539
1564
|
const t0 = /* @__PURE__ */ new Date("2020-01-01T00:00:00.000Z");
|
|
1540
1565
|
const t1 = /* @__PURE__ */ new Date("2020-01-02T00:00:00.000Z");
|
|
1541
1566
|
const t2 = /* @__PURE__ */ new Date("2020-01-03T00:00:00.000Z");
|
|
1542
|
-
const
|
|
1543
|
-
|
|
1544
|
-
|
|
1545
|
-
|
|
1567
|
+
const events = [
|
|
1568
|
+
event(1, s, 0, "Incremented", t0, { amount: 1 }),
|
|
1569
|
+
event(2, s, 1, "Incremented", t1, { amount: 2 }),
|
|
1570
|
+
event(3, s, 2, "Decremented", t2, { amount: 1 })
|
|
1546
1571
|
];
|
|
1547
|
-
const result = await
|
|
1572
|
+
const result = await restore(asSource(events));
|
|
1548
1573
|
expect3(result.kept).toBe(3);
|
|
1549
1574
|
const back = [];
|
|
1550
1575
|
await store.query(
|
|
@@ -1590,13 +1615,13 @@ var runStoreTck = (options) => {
|
|
|
1590
1615
|
const a = `restore-multi-a-${uid()}`;
|
|
1591
1616
|
const b = `restore-multi-b-${uid()}`;
|
|
1592
1617
|
const t = /* @__PURE__ */ new Date("2020-06-01T00:00:00.000Z");
|
|
1593
|
-
const
|
|
1594
|
-
|
|
1595
|
-
|
|
1596
|
-
|
|
1597
|
-
|
|
1618
|
+
const events = [
|
|
1619
|
+
event(1, a, 0, "Incremented", t, { amount: 10 }),
|
|
1620
|
+
event(2, b, 0, "Incremented", t, { amount: 20 }),
|
|
1621
|
+
event(3, a, 1, "Decremented", t, { amount: 5 }),
|
|
1622
|
+
event(4, b, 1, "Incremented", t, { amount: 30 })
|
|
1598
1623
|
];
|
|
1599
|
-
const result = await
|
|
1624
|
+
const result = await restore(asSource(events));
|
|
1600
1625
|
expect3(result.kept).toBe(4);
|
|
1601
1626
|
const aBack = [];
|
|
1602
1627
|
const bBack = [];
|
|
@@ -1615,10 +1640,10 @@ var runStoreTck = (options) => {
|
|
|
1615
1640
|
expect3(aBack.map((e) => e.version)).toEqual([0, 1]);
|
|
1616
1641
|
expect3(bBack.map((e) => e.version)).toEqual([0, 1]);
|
|
1617
1642
|
});
|
|
1618
|
-
it3("
|
|
1643
|
+
it3("preserves Date `created` verbatim", async () => {
|
|
1619
1644
|
const s = `restore-isoc-${uid()}`;
|
|
1620
1645
|
const iso = "2021-07-15T12:34:56.789Z";
|
|
1621
|
-
await
|
|
1646
|
+
await restore(
|
|
1622
1647
|
asSource([
|
|
1623
1648
|
{
|
|
1624
1649
|
id: 1,
|
|
@@ -1626,7 +1651,7 @@ var runStoreTck = (options) => {
|
|
|
1626
1651
|
version: 0,
|
|
1627
1652
|
name: "Incremented",
|
|
1628
1653
|
data: { amount: 1 },
|
|
1629
|
-
created: iso,
|
|
1654
|
+
created: new Date(iso),
|
|
1630
1655
|
meta: { correlation: "restore-tck", causation: {} }
|
|
1631
1656
|
}
|
|
1632
1657
|
])
|
|
@@ -1650,8 +1675,8 @@ var runStoreTck = (options) => {
|
|
|
1650
1675
|
);
|
|
1651
1676
|
const fresh = `restore-fresh-${uid()}`;
|
|
1652
1677
|
const t = /* @__PURE__ */ new Date("2020-01-01T00:00:00.000Z");
|
|
1653
|
-
await
|
|
1654
|
-
asSource([
|
|
1678
|
+
await restore(
|
|
1679
|
+
asSource([event(1, fresh, 0, "Incremented", t, { amount: 99 })])
|
|
1655
1680
|
);
|
|
1656
1681
|
const oldBack = await collect(store, {
|
|
1657
1682
|
stream: old,
|
|
@@ -1676,14 +1701,14 @@ var runStoreTck = (options) => {
|
|
|
1676
1701
|
};
|
|
1677
1702
|
const before = await collectStreams();
|
|
1678
1703
|
expect3(before.includes(sub)).toBe(true);
|
|
1679
|
-
await
|
|
1704
|
+
await restore(asSource([]));
|
|
1680
1705
|
const after = await collectStreams();
|
|
1681
1706
|
expect3(after.includes(sub)).toBe(false);
|
|
1682
1707
|
});
|
|
1683
1708
|
it3("preserves snapshot events through restore", async () => {
|
|
1684
1709
|
const s = `restore-snap-${uid()}`;
|
|
1685
1710
|
const t = /* @__PURE__ */ new Date("2020-04-01T00:00:00.000Z");
|
|
1686
|
-
await
|
|
1711
|
+
await restore(
|
|
1687
1712
|
asSource([
|
|
1688
1713
|
{
|
|
1689
1714
|
id: 1,
|
|
@@ -1707,7 +1732,7 @@ var runStoreTck = (options) => {
|
|
|
1707
1732
|
it3("rewrites causation refs through the old\u2192new id map", async () => {
|
|
1708
1733
|
const s = `restore-caus-${uid()}`;
|
|
1709
1734
|
const t = /* @__PURE__ */ new Date("2020-08-01T00:00:00.000Z");
|
|
1710
|
-
const
|
|
1735
|
+
const events = [
|
|
1711
1736
|
{
|
|
1712
1737
|
id: 5,
|
|
1713
1738
|
stream: s,
|
|
@@ -1746,7 +1771,7 @@ var runStoreTck = (options) => {
|
|
|
1746
1771
|
}
|
|
1747
1772
|
}
|
|
1748
1773
|
];
|
|
1749
|
-
await
|
|
1774
|
+
await restore(asSource(events));
|
|
1750
1775
|
const back = [];
|
|
1751
1776
|
await store.query(
|
|
1752
1777
|
(e) => {
|
|
@@ -1762,7 +1787,7 @@ var runStoreTck = (options) => {
|
|
|
1762
1787
|
it3("leaves causation refs unmapped when the target isn't in the source", async () => {
|
|
1763
1788
|
const s = `restore-orphan-${uid()}`;
|
|
1764
1789
|
const t = /* @__PURE__ */ new Date("2020-09-01T00:00:00.000Z");
|
|
1765
|
-
await
|
|
1790
|
+
await restore(
|
|
1766
1791
|
asSource([
|
|
1767
1792
|
{
|
|
1768
1793
|
id: 1,
|
|
@@ -1796,18 +1821,26 @@ var runStoreTck = (options) => {
|
|
|
1796
1821
|
[inc(1), inc(2), inc(3)],
|
|
1797
1822
|
makeMeta({ stream: original })
|
|
1798
1823
|
);
|
|
1799
|
-
const explosive =
|
|
1800
|
-
|
|
1801
|
-
|
|
1802
|
-
|
|
1803
|
-
|
|
1804
|
-
|
|
1805
|
-
|
|
1806
|
-
|
|
1807
|
-
|
|
1808
|
-
|
|
1809
|
-
|
|
1810
|
-
|
|
1824
|
+
const explosive = {
|
|
1825
|
+
async query(callback) {
|
|
1826
|
+
await Promise.resolve(
|
|
1827
|
+
callback(
|
|
1828
|
+
event(
|
|
1829
|
+
1,
|
|
1830
|
+
`restore-explode-${uid()}`,
|
|
1831
|
+
0,
|
|
1832
|
+
"Incremented",
|
|
1833
|
+
/* @__PURE__ */ new Date(),
|
|
1834
|
+
{ amount: 1 }
|
|
1835
|
+
)
|
|
1836
|
+
)
|
|
1837
|
+
);
|
|
1838
|
+
throw new Error("boom");
|
|
1839
|
+
},
|
|
1840
|
+
async dispose() {
|
|
1841
|
+
}
|
|
1842
|
+
};
|
|
1843
|
+
await expect3(restore(explosive)).rejects.toThrow("boom");
|
|
1811
1844
|
const back = [];
|
|
1812
1845
|
await store.query(
|
|
1813
1846
|
(e) => {
|
|
@@ -1818,6 +1851,50 @@ var runStoreTck = (options) => {
|
|
|
1818
1851
|
expect3(back).toHaveLength(3);
|
|
1819
1852
|
expect3(back.map((e) => e.id)).toEqual(committed.map((c) => c.id));
|
|
1820
1853
|
});
|
|
1854
|
+
it3("drop_snapshots: skips SNAP_EVENT rows and counts them", async () => {
|
|
1855
|
+
const s = `restore-drop-snap-${uid()}`;
|
|
1856
|
+
const t = /* @__PURE__ */ new Date("2020-10-01T00:00:00.000Z");
|
|
1857
|
+
const result = await restore(
|
|
1858
|
+
asSource([
|
|
1859
|
+
event(1, s, 0, "Incremented", t, { amount: 1 }),
|
|
1860
|
+
{
|
|
1861
|
+
id: 2,
|
|
1862
|
+
stream: s,
|
|
1863
|
+
version: 1,
|
|
1864
|
+
name: SNAP_EVENT,
|
|
1865
|
+
data: { count: 1 },
|
|
1866
|
+
created: t,
|
|
1867
|
+
meta: { correlation: "snap", causation: {} }
|
|
1868
|
+
},
|
|
1869
|
+
event(3, s, 2, "Incremented", t, { amount: 2 })
|
|
1870
|
+
]),
|
|
1871
|
+
{ drop_snapshots: true }
|
|
1872
|
+
);
|
|
1873
|
+
expect3(result.kept).toBe(2);
|
|
1874
|
+
expect3(result.dropped.snapshots).toBe(1);
|
|
1875
|
+
const back = await collect(store, {
|
|
1876
|
+
stream: s,
|
|
1877
|
+
stream_exact: true,
|
|
1878
|
+
with_snaps: true
|
|
1879
|
+
});
|
|
1880
|
+
expect3(back).toHaveLength(2);
|
|
1881
|
+
expect3(
|
|
1882
|
+
back.every((e) => e.name !== SNAP_EVENT)
|
|
1883
|
+
).toBe(true);
|
|
1884
|
+
});
|
|
1885
|
+
it3("on_progress fires once per event (caller throttles)", async () => {
|
|
1886
|
+
const calls = [];
|
|
1887
|
+
const s = `restore-progress-${uid()}`;
|
|
1888
|
+
const t = /* @__PURE__ */ new Date("2021-02-01T00:00:00.000Z");
|
|
1889
|
+
await restore(
|
|
1890
|
+
asSource([
|
|
1891
|
+
event(1, s, 0, "Incremented", t, { amount: 1 }),
|
|
1892
|
+
event(2, s, 1, "Incremented", t, { amount: 2 })
|
|
1893
|
+
]),
|
|
1894
|
+
{ on_progress: (p) => calls.push(p.processed) }
|
|
1895
|
+
);
|
|
1896
|
+
expect3(calls).toEqual([1, 2]);
|
|
1897
|
+
});
|
|
1821
1898
|
});
|
|
1822
1899
|
if (caps.notify) {
|
|
1823
1900
|
describe3("notify (capability)", () => {
|