Skip to content

Commit

Permalink
Replace ts-jest by vitest
Browse files Browse the repository at this point in the history
  • Loading branch information
nvie committed Dec 28, 2023
1 parent c4c1e8b commit ebe44c9
Show file tree
Hide file tree
Showing 20 changed files with 3,259 additions and 5,092 deletions.
13 changes: 0 additions & 13 deletions jest.config.cjs

This file was deleted.

7,872 changes: 3,004 additions & 4,868 deletions package-lock.json

Large diffs are not rendered by default.

9 changes: 5 additions & 4 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@
"lint:docs": "cog -c --check docs/*.md || (npm run docs; git diff; echo 'Error: docs not up-to-date, please re-run \"npm docs\" to update them.' && exit 1)",
"lint:package": "publint --strict && attw --pack",
"format": "eslint --report-unused-disable-directives --fix src && prettier --write 'src/**/*.js'",
"test": "jest --coverage --coverageThreshold '{\"global\": {\"branches\": 100, \"functions\": 100, \"lines\": 100, \"statements\": 100}}'",
"test": "vitest run --coverage",
"test:completeness": "./bin/check.sh",
"test:typescript": "tsc --noEmit",
"test:types": "tsd",
Expand Down Expand Up @@ -150,17 +150,18 @@
"@types/jest": "^29.5.11",
"@typescript-eslint/eslint-plugin": "^6.16.0",
"@typescript-eslint/parser": "^6.16.0",
"@vitest/coverage-istanbul": "^1.1.0",
"eslint": "^8.56.0",
"eslint-plugin-import": "^2.29.1",
"eslint-plugin-simple-import-sort": "^10.0.0",
"itertools": "^2.2.0",
"jest": "^29.7.0",
"prettier": "^3.1.1",
"publint": "^0.2.7",
"ts-jest": "^29.1.1",
"tsd": "^0.30.1",
"tsup": "^8.0.1",
"typescript": "^5.3.3"
"typescript": "^5.3.3",
"vite-tsconfig-paths": "^4.2.2",
"vitest": "^1.1.0"
},
"githubUrl": "https://github.com/nvie/decoders",
"sideEffects": false
Expand Down
1 change: 0 additions & 1 deletion src/format.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,6 @@ function serializeObject(annotation: ObjectAnnotation, prefix: string): string {
}

export function serializeValue(value: unknown): string {
// istanbul ignore else
if (typeof value === 'string') {
return serializeString(value);
} else if (typeof value === 'number' || typeof value === 'boolean') {
Expand Down
33 changes: 17 additions & 16 deletions test/Decoder.test.ts
Original file line number Diff line number Diff line change
@@ -1,15 +1,16 @@
import { describe, expect, test } from 'vitest';
import { annotate } from '~/annotate';
import { formatInline, formatShort } from '~/format';
import { number } from '~/lib/numbers';
import { pojo } from '~/lib/objects';
import { string } from '~/lib/strings';

describe('.decode', () => {
test('.decode', () => {
// .decode() is tested implicitly because it's used _everywhere_
});

describe('.verify', () => {
it('valid', () => {
test('valid', () => {
const decoder = number;
expect(decoder.verify(0)).toBe(0);
expect(decoder.verify(1)).toBe(1);
Expand All @@ -18,12 +19,12 @@ describe('.verify', () => {
expect(decoder.verify(-3.14)).toBe(-3.14);
});

it('invalid', () => {
test('invalid', () => {
const decoder = number;
expect(() => decoder.verify('foo')).toThrow('Must be number');
});

it('different erroring styles', () => {
test('different erroring styles', () => {
const decoder = number;

// Default
Expand All @@ -47,7 +48,7 @@ describe('.verify', () => {
});

describe('.value', () => {
it('valid', () => {
test('valid', () => {
const decoder = number;
expect(decoder.value(0)).toBe(0);
expect(decoder.value(1)).toBe(1);
Expand All @@ -56,7 +57,7 @@ describe('.value', () => {
expect(decoder.value(-3.14)).toBe(-3.14);
});

it('invalid', () => {
test('invalid', () => {
const decoder = number;
expect(decoder.value('foo')).toBeUndefined();
});
Expand All @@ -74,30 +75,30 @@ describe('.then', () => {
},
);

it('valid type of decode result', () => {
test('valid type of decode result', () => {
expect(hex.verify('100')).toEqual(256);
expect(hex.verify('DEADC0DE')).toEqual(0xdeadc0de);
});

it('invalid', () => {
test('invalid', () => {
expect(() => hex.verify('no good hex value')).toThrow('Nope');
});
});

describe('.transform', () => {
it('change type of decode result', () => {
test('change type of decode result', () => {
const len = string.transform((s) => s.length);
expect(len.verify('foo')).toEqual(3);
expect(len.verify('Lorem ipsum dolor sit amet.')).toEqual(27);
});

it('change value, not type, of decoded results', () => {
test('change value, not type, of decoded results', () => {
const upcase = string.transform((s) => s.toUpperCase());
expect(upcase.verify('123')).toEqual('123');
expect(upcase.verify('I am Hulk')).toEqual('I AM HULK');
});

it('a failing transformation function will fail the decoder', () => {
test('a failing transformation function will fail the decoder', () => {
const odd = number.transform((n) => {
if (n % 2 !== 0) return n;
throw new Error('Must be odd');
Expand All @@ -120,7 +121,7 @@ describe('.transform', () => {
describe('.refine', () => {
const odd = number.refine((n) => n % 2 !== 0, 'Must be odd');

it('valid', () => {
test('valid', () => {
expect(odd.decode(0).ok).toEqual(false);
expect(odd.decode(1).ok).toEqual(true);
expect(odd.decode(2).ok).toEqual(false);
Expand All @@ -141,7 +142,7 @@ describe('.reject (simple)', () => {
return badKeys.length > 0 ? `Disallowed keys: ${badKeys.join(', ')}` : null;
});

it('valid', () => {
test('valid', () => {
expect(decoder.decode({ id: 123, name: 'Bob' }).ok).toEqual(true);
expect(() => decoder.verify({ id: 123, _x: 123, _y: 'Bob' })).toThrow(
/Disallowed keys: _x, _y/,
Expand All @@ -154,7 +155,7 @@ describe('.reject (w/ Annotation)', () => {
n % 2 === 0 ? annotate('***', "Can't show ya, but this must be odd") : null,
);

it('valid', () => {
test('valid', () => {
expect(odd.decode(0).ok).toEqual(false);
expect(odd.decode(1).ok).toEqual(true);
expect(odd.decode(2).ok).toEqual(false);
Expand All @@ -172,12 +173,12 @@ describe('.reject (w/ Annotation)', () => {
describe('.describe', () => {
const decoder = string.describe('Must be text');

it('valid', () => {
test('valid', () => {
expect(decoder.verify('foo')).toBe('foo');
expect(decoder.verify('')).toBe('');
});

it('invalid', () => {
test('invalid', () => {
expect(() => decoder.verify(0)).toThrow(/Must be text/);
});
});
11 changes: 6 additions & 5 deletions test/_utils.test.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
/* eslint-disable no-restricted-syntax */

import { describe, expect, test } from 'vitest';
import { indent, subtract } from '~/_utils';
import type { Scalar } from '~/Decoder';

Expand All @@ -11,25 +12,25 @@ describe('subtract', () => {
new Set([1, 2, 3]),
];

it('subtract(x, ∅) -> x', () => {
test('subtract(x, ∅) -> x', () => {
for (const example of exampleSets) {
expect(subtract(example, new Set())).toEqual(example);
}
});

it('subtract(∅, x) -> ∅', () => {
test('subtract(∅, x) -> ∅', () => {
for (const example of exampleSets) {
expect(subtract(new Set<Scalar>(), example)).toEqual(new Set());
}
});

it('subtract(x, x) -> ∅', () => {
test('subtract(x, x) -> ∅', () => {
for (const example of exampleSets) {
expect(subtract(example, example)).toEqual(new Set());
}
});

it('subtract(x, y)', () => {
test('subtract(x, y)', () => {
expect(subtract(new Set(['a', 'b', 'c']), new Set(['b', 'c']))).toEqual(
new Set(['a']),
);
Expand All @@ -43,7 +44,7 @@ describe('subtract', () => {
});

describe('indent', () => {
it('simple', () => {
test('simple', () => {
expect(indent('foo')).toBe(' foo');
expect(indent('foo', ' ')).toBe(' foo');
});
Expand Down
31 changes: 16 additions & 15 deletions test/annotate.test.ts
Original file line number Diff line number Diff line change
@@ -1,45 +1,46 @@
/* eslint-disable no-restricted-syntax */
/* eslint-disable @typescript-eslint/no-explicit-any */

import { describe, expect, test } from 'vitest';
import { annotate, array, circularRef, merge, object, scalar } from '~/annotate';

describe('parsing (scalars)', () => {
it('strings', () => {
test('strings', () => {
expect(annotate('foo')).toEqual(scalar('foo'));
expect(annotate('foo', '')).toEqual(scalar('foo', ''));
expect(annotate('foo', 'great')).toEqual(scalar('foo', 'great'));
});

it('booleans', () => {
test('booleans', () => {
expect(annotate(true)).toEqual(scalar(true));
expect(annotate(true, '')).toEqual(scalar(true, ''));
expect(annotate(false, 'lies!')).toEqual(scalar(false, 'lies!'));
});

it('numbers', () => {
test('numbers', () => {
expect(annotate(123)).toEqual(scalar(123));
expect(annotate(234, '')).toEqual(scalar(234, ''));
expect(annotate(314, '100x π')).toEqual(scalar(314, '100x π'));
});

it('dates', () => {
test('dates', () => {
const nyd = new Date(2018, 0, 1);
expect(annotate(nyd)).toEqual(scalar(nyd));
expect(annotate(nyd, '')).toEqual(scalar(nyd, ''));
expect(annotate(nyd, "new year's day")).toEqual(scalar(nyd, "new year's day"));
});

it('null', () => {
test('null', () => {
expect(annotate(null)).toEqual(scalar(null));
expect(annotate(null, 'foo')).toEqual(scalar(null, 'foo'));
});

it('undefined', () => {
test('undefined', () => {
expect(annotate(undefined)).toEqual(scalar(undefined));
expect(annotate(undefined, 'foo')).toEqual(scalar(undefined, 'foo'));
});

it('symbols', () => {
test('symbols', () => {
const sym1 = Symbol.for('xyz');
const sym2 = Symbol();
const sym3 = Symbol('hi');
Expand All @@ -51,15 +52,15 @@ describe('parsing (scalars)', () => {
});

describe('parsing (composite)', () => {
it('arrays', () => {
test('arrays', () => {
const arr1 = [1, 'foo'];
expect(annotate(arr1)).toEqual(array([scalar(1), scalar('foo')]));

const arr2 = [annotate(1, 'uno'), 'foo'];
expect(annotate(arr2)).toEqual(array([scalar(1, 'uno'), scalar('foo')]));
});

it('objects', () => {
test('objects', () => {
const obj = { name: 'Frank' };
expect(annotate(obj)).toEqual(
object({
Expand All @@ -68,7 +69,7 @@ describe('parsing (composite)', () => {
);
});

it('objects (values annotated)', () => {
test('objects (values annotated)', () => {
const obj = { name: annotate('nvie', 'Vincent'), age: 36 };
expect(annotate(obj)).toEqual(
object({
Expand All @@ -78,7 +79,7 @@ describe('parsing (composite)', () => {
);
});

it('annotates fields in object', () => {
test('annotates fields in object', () => {
// Annotate with a simple string
const objAnn = object({ name: scalar(null) });
expect(merge(objAnn, { name: scalar(null, 'Missing!') })).toEqual(
Expand All @@ -97,7 +98,7 @@ describe('parsing (composite)', () => {
);
});

it('annotates missing fields in object', () => {
test('annotates missing fields in object', () => {
// Annotate with a simple string
const obj = object({ foo: scalar('hello') });
expect(merge(obj, { bar: scalar(undefined, 'Missing') })).toEqual(
Expand All @@ -110,7 +111,7 @@ describe('parsing (composite)', () => {
});

describe('parsing is idempotent', () => {
it('parsing an annotation returns itself', () => {
test('parsing an annotation returns itself', () => {
for (const value of ['a string', 42, [], {}, function () {}]) {
// Annotated once yields an Annotation, but annotating it more often
// has no effect on the result
Expand All @@ -125,7 +126,7 @@ describe('parsing is idempotent', () => {
});

describe('annotating circular objects', () => {
it('circular arrays', () => {
test('circular arrays', () => {
const circularArray: any[] = ['foo', [42 /* circular ref will go here */]];
circularArray[1].push(circularArray);

Expand All @@ -137,7 +138,7 @@ describe('annotating circular objects', () => {
expect(annotate(annotate(annotate(circularArray)))).toEqual(expected);
});

it('circular objects', () => {
test('circular objects', () => {
const circularObject = {
foo: 42,
bar: { qux: 'hello' },
Expand Down
Loading

0 comments on commit ebe44c9

Please sign in to comment.