import { Parser, Result, Input, Output } from '../parser'; import { always } from '../control/state'; import { tester } from '../delimiter'; export function contract

(patterns: string | RegExp, parser: P, cond: (input: Parser.Input

, output: Output>) => boolean): P; export function contract

(precond: (input: Parser.Input

, output: Output>) => boolean, parser: P, postcond: (input: Parser.Input

, output: Output>) => boolean): P; export function contract(precond: string | RegExp | ((input: Input, output: Output) => boolean), parser: Parser, postcond: (input: Input, output: Output) => boolean): Parser { if (typeof precond !== 'function') { precond = tester(precond, false); } return validate(precond, verify(parser, postcond)); } export function validate

(pattern: string | RegExp, parser: P): P; export function validate

(cond: (input: Parser.Input

, output: Output>) => boolean, parser: P): P; export function validate(cond: string | RegExp | ((input: Input, output: Output) => boolean), parser: Parser): Parser { if (typeof cond !== 'function') { cond = tester(cond, false); } return always([ (input, output) => output.state && cond(input, output) ? output.context : Result.skip, parser, ]); } export function verify

(parser: P, cond: (input: Parser.Input

, output: Output>) => boolean): P; export function verify(parser: Parser, cond: (input: Input, output: Output) => boolean): Parser { assert(parser); return always([ parser, (input, output) => output.state && cond(input, output) ? output.context : Result.fail, ]); }