parent
66666617e1
commit
504f581182
@ -1,16 +1,18 @@ |
||||
import { describe, expect, it } from '@jest/globals'; |
||||
import { _, cnst, fromNative, id, toNative } from '../src/core'; |
||||
import { _, cnst, fromNative, id, toNative, undef } from '../src/core'; |
||||
|
||||
describe('id', () => { |
||||
it('returns first argument', () => { |
||||
expect(id).toDeferEvaluationOf('first'); |
||||
expect(toNative(id._(fromNative('first')))).toBe('first'); |
||||
}); |
||||
}); |
||||
|
||||
describe('cnst', () => { |
||||
it('returns first argument after receiving second', () => { |
||||
expect(cnst).toDeferEvaluationOf('first', expect.skipped(fromNative('second'))); |
||||
expect(toNative(cnst._(fromNative('first'))._(fromNative('second')))).toBe('first'); |
||||
}); |
||||
|
||||
it('ignores second argument', () => { |
||||
expect(toNative(cnst._(fromNative('first'))._(undef))).toBe('first'); |
||||
}); |
||||
}); |
||||
|
||||
@ -1,99 +0,0 @@ |
||||
import { expect } from '@jest/globals'; |
||||
import type { MatcherFunction } from 'expect'; |
||||
import { L, P, _, fromNative } from '../src/core'; |
||||
|
||||
class Deferrable<T extends P> { |
||||
constructor( |
||||
public readonly when: 'always' | 'deferred' | 'never', |
||||
public readonly what: T) { } |
||||
} |
||||
|
||||
const toEvaluateTo: MatcherFunction<[expected: unknown]> = |
||||
function (actual, expected) { |
||||
if (!(actual instanceof L)) { |
||||
throw new TypeError('Actual must be of type Lazy!'); |
||||
} |
||||
if (this.equals(fromNative(actual), expected)) { |
||||
return { |
||||
message: () => `expected ${this.utils.printReceived(fromNative(actual))} not to evaluate to ${this.utils.printExpected(expected)}`, |
||||
pass: true, |
||||
}; |
||||
} else { |
||||
return { |
||||
message: () => `expected ${this.utils.printReceived(fromNative(actual))} to evaluate to ${this.utils.printExpected(expected)}`, |
||||
pass: false, |
||||
}; |
||||
} |
||||
}; |
||||
|
||||
const toDeferEvaluationOf: MatcherFunction<(unknown | Deferrable<P>)[]> = |
||||
function (actual, ...args) { |
||||
while (actual instanceof L) { |
||||
actual = actual.value; |
||||
} |
||||
if (typeof actual !== 'function') { |
||||
throw new TypeError('Actual must be of type function!'); |
||||
} |
||||
if (this.isNot) { |
||||
throw new TypeError('`toDeferEvaluationOf` can not be `not`ted, use `always`/`deferred`/`never` on arguments!'); |
||||
} |
||||
const largs: Deferrable<P>[] = args.map(v => |
||||
v instanceof Deferrable ? v |
||||
: v instanceof L ? new Deferrable('deferred', _(v.value)) |
||||
: new Deferrable('deferred', _(v as any))); |
||||
const cargs: Deferrable<P>[] = []; |
||||
let result = actual; |
||||
for (const la of largs) { |
||||
result = result instanceof L ? result._(la.what) : result(la.what); |
||||
cargs.push(la); |
||||
const mismatchingArg: Deferrable<P> | undefined = cargs.find(v => v.when === 'always' ? !v.what.evaluated : v.what.evaluated); |
||||
if (mismatchingArg) { |
||||
return { |
||||
message: () => |
||||
mismatchingArg.when === 'always' |
||||
? `expected ${this.utils.printExpected(actual.name)} to evaluate ${this.utils.printReceived(`${largs.indexOf(mismatchingArg) + 1}th argument`)} immediately` |
||||
: `expected ${this.utils.printExpected(actual.name)} not to evaluate ${this.utils.printReceived(`${largs.indexOf(mismatchingArg) + 1}th argument`)} immediately`, |
||||
pass: false, |
||||
}; |
||||
} |
||||
} |
||||
if (!(result instanceof L)) { |
||||
throw new TypeError('Actual did not resolve to value, more arguments expected.'); |
||||
} |
||||
(() => result.value)(); |
||||
const mismatchingArg: Deferrable<P> | undefined = cargs.find(v => v.when === 'never' && v.what.evaluated); |
||||
if (mismatchingArg) { |
||||
return { |
||||
message: () => `expected ${this.utils.printExpected(actual.name)} not to evaluate ${this.utils.printReceived(`${largs.indexOf(mismatchingArg) + 1}th argument`)}`, |
||||
pass: false, |
||||
}; |
||||
} |
||||
|
||||
return { |
||||
message: () => `expected ${this.utils.printExpected('toDeferEvaluationOf')} to ${this.utils.printReceived('fail')}`, |
||||
pass: true, |
||||
}; |
||||
}; |
||||
|
||||
expect.extend({ |
||||
toEvaluateTo, |
||||
toDeferEvaluationOf, |
||||
}); |
||||
|
||||
expect.evaluated = (v) => new Deferrable('always', _(v.value) as any); |
||||
expect.deferred = (v) => new Deferrable('deferred', _(v.value) as any); |
||||
expect.skipped = (v) => new Deferrable('never', _(v.value) as any); |
||||
|
||||
declare module 'expect' { |
||||
interface AsymmetricMatchers { |
||||
evaluated<T extends P>(value: T): Deferrable<T>; |
||||
deferred<T extends P>(value: T): Deferrable<T>; |
||||
skipped<T extends P>(value: T): Deferrable<T>; |
||||
toEvaluateTo(value: any): void; |
||||
toDeferEvaluationOf(...args: any[]): void; |
||||
} |
||||
interface Matchers<R> { |
||||
toEvaluateTo(value: any): R; |
||||
toDeferEvaluationOf(...args: any[]): R; |
||||
} |
||||
} |
||||
Loading…
Reference in new issue