Skip to content
markpaper

src/mds/mds.test.ts

v0.1.0 · 2.5 KB

Download file
import { describe, expect, it, vi } from 'vitest';
import { createFakeExchange, FIXTURE_ACCOUNT } from '../testing/index.js';
import { createMarketDataStream } from './index.js';

function setup() {
  let time = 100;
  const fake = createFakeExchange({
    ackDelayMs: 0,
    readDelayMs: 0,
    dropAddReplies: false,
    canonicalAccountId: FIXTURE_ACCOUNT,
  });
  const stream = createMarketDataStream({
    url: 'ws://localhost',
    webSocketFactory: fake.webSocketFactory,
    pingIntervalMs: 1000,
    deadAfterMs: 3000,
    backoffMinMs: 30,
    backoffMaxMs: 100,
    stableAfterMs: 800,
    handshakeTimeoutMs: 100,
    symbolsPerFrame: 7,
    logWindowMs: 160,
    closeWaitMs: 150,
    maxPayloadBytes: 2 ** 20,
    clock: {
      now: () => time,
      setTimer: (ms, fn) => {
        const handle = setTimeout(fn, ms);
        return { cancel: () => clearTimeout(handle) };
      },
    },
  });
  return {
    fake,
    stream,
    advance: (at: number) => {
      time = at;
    },
    close: async () => {
      await stream.close();
      fake.close();
    },
  };
}
describe('market-data boundaries', () => {
  it('does not refresh an old price band from a new quote', async () => {
    const test = setup();
    try {
      test.stream.watch(['BTC-USD']);
      await vi.waitFor(() => expect(test.stream.health().state).toBe('open'));
      test.fake.emit({ type: 'minmax_price', symbol: 'BTC-USD', min_price: '80', max_price: '180' });
      await Promise.resolve();
      test.advance(250);
      test.fake.emit({ type: 'bbo', symbol: 'BTC-USD', bid: [['119', '0.2']], ask: [['121', '0.3']] });
      await Promise.resolve();
      expect(test.stream.bbo('BTC-USD')?.at).toBe(250);
      expect(test.stream.band('BTC-USD')?.at).toBe(100);
      expect(test.stream.freshBand('BTC-USD', 50)).toBeNull();
    } finally {
      await test.close();
    }
  });
  it('rejects nonfinite quotes and bands even though exact decimals parse them', async () => {
    const test = setup();
    try {
      test.stream.watch(['BTC-USD']);
      await vi.waitFor(() => expect(test.stream.health().state).toBe('open'));
      test.fake.emit({ type: 'bbo', symbol: 'BTC-USD', bid: [['119', '0.2']], ask: [['1e400', '0.3']] });
      test.fake.emit({ type: 'minmax_price', symbol: 'BTC-USD', min_price: '80', max_price: '1e400' });
      await Promise.resolve();
      expect(test.stream.bbo('BTC-USD')).toBeNull();
      expect(test.stream.band('BTC-USD')).toBeNull();
    } finally {
      await test.close();
    }
  });
});
All files