@quantform/core 0.7.20 → 0.7.22

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 (104) hide show
  1. package/lib/cli/replay.d.ts +1 -0
  2. package/lib/cli/replay.d.ts.map +1 -1
  3. package/lib/cli/replay.js +4 -3
  4. package/lib/index.d.ts +1 -1
  5. package/lib/index.d.ts.map +1 -1
  6. package/lib/index.js +1 -1
  7. package/lib/replay/index.d.ts +3 -6
  8. package/lib/replay/index.d.ts.map +1 -1
  9. package/lib/replay/index.js +3 -6
  10. package/lib/replay/use-replay-options.d.ts +6 -1
  11. package/lib/replay/use-replay-options.d.ts.map +1 -1
  12. package/lib/replay/use-replay-options.js +1 -1
  13. package/lib/replay/{use-replay-manager.d.ts → use-replay-scheduler.d.ts} +4 -4
  14. package/lib/replay/use-replay-scheduler.d.ts.map +1 -0
  15. package/lib/{backtest/use-backtest-scheduler.js → replay/use-replay-scheduler.js} +6 -6
  16. package/lib/replay/{storage/use-replay-storage-buffer.d.ts → use-replay-storage-buffer.d.ts} +2 -2
  17. package/lib/replay/use-replay-storage-buffer.d.ts.map +1 -0
  18. package/lib/{backtest/use-backtest-storage-buffer.js → replay/use-replay-storage-buffer.js} +6 -6
  19. package/lib/{backtest/use-backtest-storage-cursor.d.ts → replay/use-replay-storage-cursor.d.ts} +4 -4
  20. package/lib/replay/use-replay-storage-cursor.d.ts.map +1 -0
  21. package/lib/{backtest/use-backtest-storage-cursor.js → replay/use-replay-storage-cursor.js} +4 -4
  22. package/lib/{backtest/use-backtest-storage.d.ts → replay/use-replay-storage.d.ts} +3 -3
  23. package/lib/replay/use-replay-storage.d.ts.map +1 -0
  24. package/lib/{backtest/use-backtest-storage.js → replay/use-replay-storage.js} +16 -9
  25. package/lib/replay/use-replay-sync.d.ts +3 -0
  26. package/lib/replay/use-replay-sync.d.ts.map +1 -0
  27. package/lib/{backtest/use-backtest-sync.js → replay/use-replay-sync.js} +5 -5
  28. package/lib/replay/use-replay.d.ts +1 -9
  29. package/lib/replay/use-replay.d.ts.map +1 -1
  30. package/lib/replay/use-replay.js +3 -14
  31. package/lib/replay/when-replay-finished.js +2 -2
  32. package/lib/use-timestamp.js +2 -2
  33. package/package.json +1 -1
  34. package/src/cli/replay.ts +3 -2
  35. package/src/index.ts +1 -1
  36. package/src/replay/index.ts +3 -6
  37. package/src/replay/use-replay-options.ts +10 -2
  38. package/src/{backtest/use-backtest-scheduler.ts → replay/use-replay-scheduler.ts} +8 -11
  39. package/src/{backtest/use-backtest-storage-buffer.ts → replay/use-replay-storage-buffer.ts} +5 -5
  40. package/src/{backtest/use-backtest-storage-cursor.ts → replay/use-replay-storage-cursor.ts} +7 -7
  41. package/src/replay/use-replay-storage.ts +101 -0
  42. package/src/{backtest/use-backtest-sync.ts → replay/use-replay-sync.ts} +3 -3
  43. package/src/replay/use-replay.ts +3 -24
  44. package/src/replay/when-replay-finished.ts +2 -2
  45. package/src/use-timestamp.ts +2 -2
  46. package/lib/backtest/index.d.ts +0 -7
  47. package/lib/backtest/index.d.ts.map +0 -1
  48. package/lib/backtest/index.js +0 -22
  49. package/lib/backtest/use-backtest-options.d.ts +0 -15
  50. package/lib/backtest/use-backtest-options.d.ts.map +0 -1
  51. package/lib/backtest/use-backtest-options.js +0 -20
  52. package/lib/backtest/use-backtest-scheduler.d.ts +0 -28
  53. package/lib/backtest/use-backtest-scheduler.d.ts.map +0 -1
  54. package/lib/backtest/use-backtest-storage-buffer.d.ts +0 -15
  55. package/lib/backtest/use-backtest-storage-buffer.d.ts.map +0 -1
  56. package/lib/backtest/use-backtest-storage-cursor.d.ts.map +0 -1
  57. package/lib/backtest/use-backtest-storage.d.ts.map +0 -1
  58. package/lib/backtest/use-backtest-sync.d.ts +0 -3
  59. package/lib/backtest/use-backtest-sync.d.ts.map +0 -1
  60. package/lib/backtest/use-backtest.d.ts +0 -2
  61. package/lib/backtest/use-backtest.d.ts.map +0 -1
  62. package/lib/backtest/use-backtest.js +0 -9
  63. package/lib/backtest/when-backtest-finished.d.ts +0 -2
  64. package/lib/backtest/when-backtest-finished.d.ts.map +0 -1
  65. package/lib/backtest/when-backtest-finished.js +0 -15
  66. package/lib/replay/replay-guard.d.ts +0 -10
  67. package/lib/replay/replay-guard.d.ts.map +0 -1
  68. package/lib/replay/replay-guard.js +0 -8
  69. package/lib/replay/replay.d.ts +0 -10
  70. package/lib/replay/replay.d.ts.map +0 -1
  71. package/lib/replay/replay.js +0 -9
  72. package/lib/replay/storage/use-replay-storage-buffer.d.ts.map +0 -1
  73. package/lib/replay/storage/use-replay-storage-buffer.js +0 -57
  74. package/lib/replay/storage/use-replay-storage-cursor.d.ts +0 -30
  75. package/lib/replay/storage/use-replay-storage-cursor.d.ts.map +0 -1
  76. package/lib/replay/storage/use-replay-storage-cursor.js +0 -49
  77. package/lib/replay/storage/use-replay-storage.d.ts +0 -13
  78. package/lib/replay/storage/use-replay-storage.d.ts.map +0 -1
  79. package/lib/replay/storage/use-replay-storage.js +0 -39
  80. package/lib/replay/storage/use-replay-storage.spec.d.ts +0 -2
  81. package/lib/replay/storage/use-replay-storage.spec.d.ts.map +0 -1
  82. package/lib/replay/storage/use-replay-storage.spec.js +0 -74
  83. package/lib/replay/use-replay-lock.d.ts +0 -3
  84. package/lib/replay/use-replay-lock.d.ts.map +0 -1
  85. package/lib/replay/use-replay-lock.js +0 -22
  86. package/lib/replay/use-replay-manager.d.ts.map +0 -1
  87. package/lib/replay/use-replay-manager.js +0 -68
  88. package/lib/replay/use-replay.spec.d.ts +0 -2
  89. package/lib/replay/use-replay.spec.d.ts.map +0 -1
  90. package/lib/replay/use-replay.spec.js +0 -130
  91. package/src/backtest/index.ts +0 -6
  92. package/src/backtest/use-backtest-options.ts +0 -23
  93. package/src/backtest/use-backtest-storage.ts +0 -87
  94. package/src/backtest/use-backtest.ts +0 -7
  95. package/src/backtest/when-backtest-finished.ts +0 -20
  96. package/src/replay/replay-guard.ts +0 -11
  97. package/src/replay/replay.ts +0 -13
  98. package/src/replay/storage/use-replay-storage-buffer.ts +0 -52
  99. package/src/replay/storage/use-replay-storage-cursor.ts +0 -44
  100. package/src/replay/storage/use-replay-storage.spec.ts +0 -84
  101. package/src/replay/storage/use-replay-storage.ts +0 -29
  102. package/src/replay/use-replay-lock.ts +0 -29
  103. package/src/replay/use-replay-manager.ts +0 -83
  104. package/src/replay/use-replay.spec.ts +0 -138
@@ -1,84 +0,0 @@
1
- import { makeTestModule, mockedFunc } from '@lib/make-test-module';
2
- import { Query, QueryObject, Storage } from '@lib/storage';
3
- import { useStorage } from '@lib/storage';
4
-
5
- import { useReplayStorage } from './use-replay-storage';
6
-
7
- jest.mock('@lib/storage', () => ({
8
- ...jest.requireActual('@lib/storage'),
9
- useStorage: jest.fn()
10
- }));
11
-
12
- describe(useReplayStorage.name, () => {
13
- let fixtures: Awaited<ReturnType<typeof getFixtures>>;
14
-
15
- beforeEach(async () => {
16
- fixtures = await getFixtures();
17
- });
18
-
19
- describe('query', () => {
20
- test('happy path', async () => {
21
- await fixtures.given.stored(fixtures.sample);
22
- const sample = await fixtures.when.queried({});
23
-
24
- expect(sample).toEqual(fixtures.sample);
25
- });
26
- });
27
-
28
- describe('save', () => {
29
- test('happy path', async () => {
30
- await fixtures.when.saved(fixtures.sample);
31
- await fixtures.then.stored(fixtures.sample);
32
- });
33
- });
34
- });
35
-
36
- async function getFixtures() {
37
- const { act } = await makeTestModule([]);
38
-
39
- const dependencies = ['binance:btc-usdt', 'candle', 'h1'];
40
- const save: Storage['save'] = jest.fn();
41
- const query: jest.MockedFunction<Storage['query']> = jest.fn();
42
-
43
- mockedFunc(useStorage).mockReturnValue({ save, query } as any);
44
-
45
- return {
46
- sample: [
47
- { timestamp: 1, payload: { o: 1.1, h: 1.1, l: 1.1, c: 1.1 } },
48
- { timestamp: 2, payload: { o: 1.1, h: 2.2, l: 1.1, c: 2.2 } },
49
- { timestamp: 3, payload: { o: 1.1, h: 3.3, l: 1.1, c: 3.3 } }
50
- ],
51
-
52
- given: {
53
- stored<T>(sample: { timestamp: number; payload: T }[]) {
54
- return query.mockReturnValue(
55
- Promise.resolve(
56
- sample.map(it => ({
57
- timestamp: it.timestamp,
58
- payload: JSON.stringify(it.payload)
59
- }))
60
- )
61
- );
62
- }
63
- },
64
- when: {
65
- saved<T>(sample: { timestamp: number; payload: T }[]) {
66
- return act(() => useReplayStorage(dependencies).save(sample));
67
- },
68
- queried<T>(query: Query<QueryObject>) {
69
- return act(() => useReplayStorage<T>(dependencies).query(query));
70
- }
71
- },
72
- then: {
73
- stored<T>(sample: { timestamp: number; payload: T }[]) {
74
- expect(save).toHaveBeenCalledWith(
75
- expect.anything(),
76
- sample.map(it => ({
77
- timestamp: it.timestamp,
78
- payload: JSON.stringify(it.payload)
79
- }))
80
- );
81
- }
82
- }
83
- };
84
- }
@@ -1,29 +0,0 @@
1
- import { Query, QueryObject, Storage, useStorage } from '@lib/storage';
2
- import { dependency, useHash } from '@lib/use-hash';
3
-
4
- export function useReplayStorage<T>(dependencies: dependency[]) {
5
- const storage = useStorage(['replay']);
6
- const storageObjectKey = useHash(dependencies);
7
- const storageObject = Storage.createObject(storageObjectKey, {
8
- timestamp: 'number',
9
- payload: 'string'
10
- });
11
-
12
- return {
13
- async query(query: Query<QueryObject>) {
14
- return (await storage.query(storageObject, query)).map(it => ({
15
- timestamp: it.timestamp,
16
- payload: JSON.parse(it.payload) as T
17
- }));
18
- },
19
- save(objects: { timestamp: number; payload: T }[]) {
20
- return storage.save(
21
- storageObject,
22
- objects.map(it => ({
23
- timestamp: it.timestamp,
24
- payload: JSON.stringify(it.payload)
25
- }))
26
- );
27
- }
28
- };
29
- }
@@ -1,29 +0,0 @@
1
- import { finalize, Observable } from 'rxjs';
2
-
3
- import { useExecutionMode } from '@lib/use-execution-mode';
4
- import { useLogger } from '@lib/use-logger';
5
-
6
- import { useReplayManager } from './use-replay-manager';
7
-
8
- export function useReplayLock<T>(input: Observable<T>): Observable<T> {
9
- const { isReplay } = useExecutionMode();
10
-
11
- if (!isReplay) {
12
- return input;
13
- }
14
-
15
- const { info } = useLogger('replay');
16
- const { stop, tryContinue } = useReplayManager();
17
-
18
- info('lock acquired');
19
-
20
- stop();
21
-
22
- return input.pipe(
23
- finalize(() => {
24
- info('lock released');
25
-
26
- tryContinue();
27
- })
28
- );
29
- }
@@ -1,83 +0,0 @@
1
- import { defer, filter, map, Observable, Subject } from 'rxjs';
2
-
3
- import { dependency } from '@lib/use-hash';
4
- import { withMemo } from '@lib/with-memo';
5
-
6
- import { useReplayStorageBuffer } from './storage/use-replay-storage-buffer';
7
- import { useReplayStorageCursor } from './storage/use-replay-storage-cursor';
8
- import { useReplayOptions } from './use-replay-options';
9
-
10
- export const useReplayManager = withMemo(() => {
11
- const { from } = useReplayOptions();
12
- const { get, cursor } = useReplayStorageCursor();
13
-
14
- let timestamp = from;
15
- let stopAcquire = 1;
16
-
17
- const stream$ = new Subject<
18
- [ReturnType<typeof useReplayStorageBuffer<any>>, { timestamp: number; payload: any }]
19
- >();
20
-
21
- const processNext = async () => {
22
- const storage = await cursor();
23
-
24
- if (!storage || !storage.peek()) {
25
- stream$.complete();
26
-
27
- return false;
28
- }
29
-
30
- const sample = storage.dequeue();
31
-
32
- timestamp = sample.timestamp;
33
-
34
- stream$.next([storage, sample]);
35
-
36
- return true;
37
- };
38
-
39
- const next = async () => {
40
- if (await processNext()) {
41
- if (stopAcquire === 0) {
42
- setImmediate(next);
43
- }
44
- }
45
- };
46
-
47
- const tryContinue = () => {
48
- if (stopAcquire == 0) {
49
- return;
50
- }
51
-
52
- stopAcquire = Math.max(0, stopAcquire - 1);
53
-
54
- if (stopAcquire != 0) {
55
- return;
56
- }
57
-
58
- next();
59
- };
60
-
61
- return {
62
- stream: stream$.asObservable(),
63
- timestamp() {
64
- return timestamp;
65
- },
66
- stop() {
67
- stopAcquire++;
68
- },
69
- tryContinue,
70
- watch<T>(dependencies: dependency[]): Observable<{ timestamp: number; payload: T }> {
71
- const storage = get<T>(dependencies);
72
-
73
- return defer(() => {
74
- tryContinue();
75
-
76
- return stream$.pipe(
77
- filter(([cur]) => cur === storage),
78
- map(([, it]) => ({ timestamp: it.timestamp, payload: it.payload as T }))
79
- );
80
- });
81
- }
82
- };
83
- });
@@ -1,138 +0,0 @@
1
- import exp from 'constants';
2
- import { from, lastValueFrom, tap } from 'rxjs';
3
-
4
- import { makeTestModule } from '@lib/make-test-module';
5
- import { dependency } from '@lib/use-hash';
6
-
7
- import { between } from '..';
8
- import { useReplay } from './use-replay';
9
- import { replayOptions } from './use-replay-options';
10
-
11
- describe(useReplay.name, () => {
12
- test('happy path', () => {
13
- expect(true).toBe(true);
14
- });
15
- });
16
-
17
- /*
18
-
19
- describe.skip(useReplayCoordinator.name, () => {
20
- let fixtures: Awaited<ReturnType<typeof getFixtures>>;
21
-
22
- beforeEach(async () => {
23
- fixtures = await getFixtures();
24
- });
25
-
26
- test('return single data stream for single data source', async () => {
27
- fixtures.givenRecordingEnabled(false);
28
- await fixtures.givenSampleStored(fixtures.sample1, ['sample1']);
29
-
30
- const sample1 = fixtures.whenUseReplayCalled(fixtures.sample1, ['sample']);
31
- await fixtures.whenUseSampleStreamerStarted();
32
-
33
- expect(await sample1).toEqual(fixtures.sample1);
34
- });
35
-
36
- test('return combined data stream for multiple data sources', async () => {
37
- fixtures.givenRecordingEnabled(false);
38
- await fixtures.givenSampleStored(fixtures.sample1, ['sample1']);
39
- await fixtures.givenSampleStored(fixtures.sample2, ['sample2']);
40
-
41
- const sample1 = fixtures.whenUseReplayCalled(fixtures.sample1, ['sample1']);
42
- const sample2 = fixtures.whenUseReplayCalled(fixtures.sample2, ['sample2']);
43
- await fixtures.whenUseSampleStreamerStarted();
44
-
45
- expect(await sample1).toEqual(fixtures.sample1);
46
- expect(await sample2).toEqual(fixtures.sample2);
47
- });
48
-
49
- test('record and write data stream into storage', async () => {
50
- fixtures.givenRecordingEnabled(true);
51
- const sample1 = await fixtures.whenUseReplayCalled(fixtures.sample1, ['sample1x']);
52
- const sample2 = await fixtures.whenUseReplayCalled(fixtures.sample2, ['sample2x']);
53
-
54
- fixtures.thenReplaySampleStored(sample1, ['sample1x']);
55
- fixtures.thenReplaySampleStored(sample2, ['sample2x']);
56
- });
57
- });
58
-
59
- async function getFixtures() {
60
- const executionMode = replayExecutionMode();
61
-
62
- const { act } = await makeTestModule([
63
- executionMode,
64
- replayOptions({ from: 0, to: Number.MAX_VALUE })
65
- ]);
66
-
67
- return {
68
- sample1: [
69
- { timestamp: 1, payload: { o: 111, h: 112, l: 113, c: 114 } },
70
- { timestamp: 2, payload: { o: 121, h: 122, l: 123, c: 124 } },
71
- { timestamp: 3, payload: { o: 131, h: 132, l: 133, c: 134 } }
72
- ],
73
- sample2: [
74
- { timestamp: 1, payload: { o: 211, h: 212, l: 213, c: 214 } },
75
- { timestamp: 2, payload: { o: 221, h: 222, l: 223, c: 224 } },
76
- { timestamp: 3, payload: { o: 231, h: 232, l: 233, c: 234 } }
77
- ],
78
-
79
- givenRecordingEnabled(recording: boolean) {
80
- executionMode.useValue.recording = recording;
81
- },
82
-
83
- givenSampleStored<T>(
84
- sample: { timestamp: number; payload: T }[],
85
- dependencies: dependency[]
86
- ) {
87
- return act(() => {
88
- const writer = useReplayWriter(dependencies);
89
-
90
- return writer(sample);
91
- });
92
- },
93
-
94
- async whenUseReplayCalled<T>(
95
- input: { timestamp: number; payload: T }[],
96
- dependencies: dependency[]
97
- ) {
98
- const sample = Array.of<{ timestamp: number; payload: T }>();
99
-
100
- await act(() =>
101
- lastValueFrom(
102
- useReplay<T>(from(input), dependencies).pipe(tap(it => sample.push(it)))
103
- )
104
- );
105
-
106
- return sample;
107
- },
108
-
109
- whenUseSampleStreamerStarted() {
110
- act(() => {
111
- const { tryContinue } = useReplayCoordinator();
112
-
113
- tryContinue();
114
- });
115
- },
116
-
117
- async thenReplaySampleStored<T extends { timestamp: number }>(
118
- sample: T[],
119
- dependencies: dependency[]
120
- ) {
121
- const stored = await act(() => {
122
- const reader = useReplayReader(dependencies);
123
-
124
- return reader({
125
- where: {
126
- timestamp: between(
127
- sample[0].timestamp,
128
- sample[sample.length - 1].timestamp + 1
129
- )
130
- }
131
- });
132
- });
133
-
134
- expect(stored).toEqual(sample);
135
- }
136
- };
137
- }
138
- */