declare const DEFAULT = '_'
interface None {
readonly _tag: 'None'
}
interface Some {
readonly _tag: 'Some'
readonly value: A
}
export declare type Option = None | Some
interface DefaultCase {
readonly _tag: typeof DEFAULT
readonly value: unknown
}
interface DefaultCase {
readonly [DEFAULT]: () => unknown
}
declare type _Tag<
T extends {
readonly _tag: string
}
> = T['_tag']
declare type MatchingType = Extract<
T,
{
readonly _tag: Type
}
>
declare type X = 'left' | 'right' | 'value'
declare type Match = {
readonly [k in X]?: unknown
} & {
readonly _tag: string
}
declare type MatchW = (
p: Extract<
A,
{
[_tag in _Tag]: X
}
>
) => R
/**
* Strict `Pattern Maching` Implementation
*
* @example
* import * as M from 'pattern-matching-ts/lib/match'
*
* const optionMatching = M.match, string>({
* Some: (x) => x.value,
* None: () => 'Nothing',
* })
*
* assert.deepStrictEqual(optionMatching(O.some('data')), 'data')
* assert.deepStrictEqual(optionMatching(O.none), 'Nothing')
*
* type Cases = ChangeColor | Move | Write
*
* const matchMessage = M.match({
* ChangeColor: ({ value: { r, g, b } }) => `Change the color to Red: ${r} | Green: ${g} | Blue: ${b}`,
* Move: ({ value: { x, y } }) => `Move in the x direction: ${x} and in the y direction: ${y}`,
* Write: ({ value: { text } }) => `Text message: ${text}`,
* _: () => 'Default message'
* })
*
* assert.deepStrictEqual(matchMessage(ChangeColor({ r: 12, g: 20, b: 30 })),'Change the color to Red: 12 | Green: 20 | Blue: 30')
* assert.deepStrictEqual(matchMessage(Move({ x: 500, y: 100 })),'Move in the x direction: 500 and in the y direction: 100')
*
*/
export declare function match(
pattern: T extends Option
? {
[K in _Tag]: (x: MatchingType) => R
}
: {
[K in _Tag | DefaultCase['_tag']]: (x: MatchingType) => R
}
): (x: T) => R
/**
* A Wider pipeable `Pattern Maching` Implementation
*
* @example
* import * as M from 'pattern-matching-ts/lib/match'
*
* const optionMatching = (o: O.Option) =>
* pipe(
* o,
* M.matchW('_tag')({
* Some: ({ value }) => 'Something: ' + value,
* None: () => 'Nothing',
* }))
*
* assert.deepStrictEqual(optionMatching(O.some('data')), 'Something: data')
* assert.deepStrictEqual(optionMatching(O.none), 'Nothing')
*
* const matchResponse = (response: Responses) =>
* pipe(
* response,
* M.matchW('code')({
* 500: ({ detail }) => ({ message: 'Internal server error', detail }),
* 404: () => ({ message: 'The page cannot be found!' }),
* 200: ({ response }) => response.body,
* _: () => 'Unexpected response'
* })
* )
*
* assert.deepStrictEqual(matchResponse({ code: 200, response: { body: ['data'] } }), ['data'])
* assert.deepStrictEqual(matchResponse({ code: 500, detail: 'Cannot connect to the database' }), {
* message: 'Internal server error',
* detail: 'Cannot connect to the database'
* })
* assert.deepStrictEqual(matchResponse({ code: 404 }), { message: 'The page cannot be found!' })
* @since 2.0.
*/
export declare const matchW: <_Tag extends string>(
_tag: _Tag
) => {
<
A extends {
[X in _Tag]: string | number | typeof DEFAULT
},
K extends {
[X in A[_Tag]]: MatchW
}
>(
k: K
): (match: A) => ReturnType | DefaultCase
}
export {}