moex-vibe/apps/backend/src/modules/candles/candles.service.spec.ts

118 lines
2.9 KiB
TypeScript

import { Test, TestingModule } from '@nestjs/testing';
import { CandlesService } from './candles.service';
import { MoexClientService } from '../moex-client/moex-client.service';
import { CacheService } from '../cache/cache.service';
import { CandleInterval } from './dto/candles-query.dto';
describe('CandlesService', () => {
let service: CandlesService;
let moexClient: Pick<MoexClientService, 'getCandles'>;
let cache: Pick<CacheService, 'getOrFetch'>;
beforeEach(async () => {
moexClient = {
getCandles: vi.fn(),
};
cache = {
getOrFetch: vi.fn(async (_keyPrefix, _keyParts, fetchFn) => ({
data: await fetchFn(),
fromCache: false,
cachedAt: '2026-06-15T00:00:00.000Z',
})),
};
const module: TestingModule = await Test.createTestingModule({
providers: [
CandlesService,
{ provide: MoexClientService, useValue: moexClient },
{ provide: CacheService, useValue: cache },
],
}).compile();
service = module.get<CandlesService>(CandlesService);
});
it('uses MOEX interval 24 for daily share candles and maps output envelope', async () => {
vi.mocked(moexClient.getCandles).mockResolvedValue([
{
open: 320,
high: 325,
low: 318,
close: 323,
volume: 1500000,
value: 480000000,
begin: '2026-05-01 00:00:00',
end: '2026-05-01 23:59:59',
},
]);
const result = await service.getCandles(
'shares',
'SBER',
CandleInterval.DAY,
'2026-05-01',
'2026-06-01',
);
expect(cache.getOrFetch).toHaveBeenCalledWith(
'candles',
['shares', 'SBER', '24', '2026-05-01', '2026-06-01'],
expect.any(Function),
'candlesTtl',
);
expect(moexClient.getCandles).toHaveBeenCalledWith(
'stock',
'shares',
'SBER',
24,
'2026-05-01',
'2026-06-01',
);
expect(result).toEqual({
data: [
{
open: 320,
high: 325,
low: 318,
close: 323,
volume: 1500000,
value: 480000000,
begin: '2026-05-01 00:00:00',
end: '2026-05-01 23:59:59',
},
],
meta: {
fromCache: false,
cachedAt: '2026-06-15T00:00:00.000Z',
},
});
});
it('uses MOEX interval 60 for hourly bond candles without live MOEX dependency', async () => {
vi.mocked(moexClient.getCandles).mockResolvedValue([]);
await service.getCandles(
'bonds',
'SU26238RMFS5',
CandleInterval.HOUR,
'2026-05-01',
'2026-06-01',
);
expect(cache.getOrFetch).toHaveBeenCalledWith(
'candles',
['bonds', 'SU26238RMFS5', '60', '2026-05-01', '2026-06-01'],
expect.any(Function),
'candlesTtl',
);
expect(moexClient.getCandles).toHaveBeenCalledWith(
'stock',
'bonds',
'SU26238RMFS5',
60,
'2026-05-01',
'2026-06-01',
);
});
});