fix: configure Jest for ES modules in kraiken-lib (#88)

Updates Jest configuration to properly handle ES module syntax:
- Switch to ts-jest/presets/default-esm preset
- Add custom resolver to map .js imports to .ts source files
- Configure extensionsToTreatAsEsm for TypeScript files
- Enable useESM in ts-jest globals

This resolves module resolution errors when running tests in
kraiken-lib which uses "type": "module" in package.json.

Fixes #85

Co-authored-by: openhands <openhands@all-hands.dev>
Reviewed-on: https://codeberg.org/johba/harb/pulls/88
This commit is contained in:
johba 2025-11-08 12:03:48 +01:00
parent 07a522e3fb
commit c2720c35a5
4 changed files with 56 additions and 29 deletions

View file

@ -1,5 +1,13 @@
module.exports = {
preset: 'ts-jest',
preset: 'ts-jest/presets/default-esm',
testEnvironment: 'node',
maxWorkers: 1
maxWorkers: 1,
extensionsToTreatAsEsm: ['.ts'],
resolver: './jest.resolver.cjs',
globals: {
'ts-jest': {
useESM: true,
tsconfig: './tsconfig.json'
}
}
};

View file

@ -0,0 +1,16 @@
module.exports = (request, options) => {
try {
return options.defaultResolver(request, options);
} catch (originalError) {
if (!request.endsWith('.js')) {
throw originalError;
}
const tsRequest = request.replace(/\.js$/, '.ts');
try {
return options.defaultResolver(tsRequest, options);
} catch (fallbackError) {
throw originalError;
}
}
};

View file

@ -1,27 +1,18 @@
import { describe, expect, test } from '@jest/globals';
import { bytesToUint256LittleEndian, uint256ToBytesLittleEndian } from '../subgraph';
import { Position, PositionStatus } from '../__generated__/graphql';
describe('BigInt Conversion Functions', () => {
test('converts uint256 to bytes and back (little endian)', async () => {
const mockPos: Position = {
__typename: 'Position',
id: uint256ToBytesLittleEndian(3n),
owner: '0x8db6b632d743aef641146dc943acb64957155388',
share: '0.000001',
creationTime: 1610000000,
taxRate: '0.01',
status: PositionStatus.Active, // Enum usage
};
const mockId = uint256ToBytesLittleEndian(3n);
let hexString = '0x';
for (let i = 0; i < mockPos.id.length; i++) {
for (let i = 0; i < mockId.length; i++) {
// Convert each byte to a hexadecimal string and pad with zero if needed
hexString += mockPos.id[i].toString(16).padStart(2, '0');
hexString += mockId[i].toString(16).padStart(2, '0');
}
expect(hexString).toEqual('0x03000000');
// return hexString;
expect(bytesToUint256LittleEndian(mockPos.id)).toEqual(3n);
expect(bytesToUint256LittleEndian(mockId)).toEqual(3n);
});
});

View file

@ -1,8 +1,6 @@
import { describe, expect, test } from '@jest/globals';
import { getSnatchList, minimumTaxRate, selectSnatchPositions, type SnatchablePosition } from '../snatch';
import { uint256ToBytesLittleEndian } from '../subgraph';
import type { Position } from '../__generated__/graphql';
import { PositionStatus } from '../__generated__/graphql';
import type { Positions } from '../__generated__/graphql';
describe('snatch', () => {
test('minimumTaxRate finds the lowest tax', () => {
@ -46,26 +44,40 @@ describe('snatch', () => {
test('getSnatchList converts subgraph positions', () => {
const stakeTotalSupply = 1_000_000n * 10n ** 18n;
const positions: Position[] = [
const positions: Positions[] = [
{
__typename: 'Position',
id: uint256ToBytesLittleEndian(1n),
__typename: 'positions',
id: '0x01',
owner: '0xowner1',
share: 0.0001,
creationTime: 0,
lastTaxTime: 0,
creationTime: '0',
lastTaxTime: '0',
taxRate: 0.02,
status: PositionStatus.Active,
status: 'Active',
createdAt: '0',
kraikenDeposit: '0',
payout: '0',
snatched: 0,
stakeDeposit: '0',
taxPaid: '0',
totalSupplyInit: '0',
},
{
__typename: 'Position',
id: uint256ToBytesLittleEndian(2n),
__typename: 'positions',
id: '0x02',
owner: '0xowner2',
share: 0.0002,
creationTime: 0,
lastTaxTime: 0,
creationTime: '0',
lastTaxTime: '0',
taxRate: 0.01,
status: PositionStatus.Active,
status: 'Active',
createdAt: '0',
kraikenDeposit: '0',
payout: '0',
snatched: 0,
stakeDeposit: '0',
taxPaid: '0',
totalSupplyInit: '0',
},
];