match
A module for matching elements from pages.
Install
npm install --save @blackglory/match
# or
yarn add @blackglory/match
Usage
import { matchElement, element, css, childNodes, textNode, children, multiple } from '@blackglory/match'
const result = matchElement(node
, element(
css`header`
, childNodes(
textNode`heading`()
)
)
, element(
css`section`
, children(
multiple([1, Infinity], element(
css`p`
, childNodes(
textNode`paragraph`()
)
))
)
)
)
// { heading: Text, paragraph: [ Text, Text ] }
API
interface IContext {
readonly document: Document
readonly next: (node: Node, distance?: number) => Node | undefined
readonly collection: {
[name: string]: Node | Node[]
}
}
interface IReadonlyContext {
readonly document: Document
readonly next: (node: Node, distance?: number) => Node | undefined
readonly collection: {
readonly [name: string]: Node | Node[]
}
}
type IMatcher<T extends Node> =
| ITerminalMatcher<T>
| INestedMatcher<T>
| ISkipMatcher<T>
type ITerminalMatcher<T extends Node> = (
this: IReadonlyContext<T>
, node: T
) => boolean
type INestedMatcher<T extends Node> = (
this: IReadonlyContext<T>
, node: T
) => boolean
type ISkipMatcher<T extends Node> = (
this: IReadonlyContext<T>
, node: T
) => number | false
match
function match(
this: void | Document
, node: Node
, ...matchers: Array<IMatcher<Node>>
): { [name: string]: Node | Node[] } | null
matchElement
function matchElement(
this: void | Document
, element: Element
, ...matchers: Array<IMatcher<Element>>
): { [name: string]: Node | Node[] } | null
Matchers
anyOf
function anyOf<T extends Node>(
...matchers: [
INestedMatcher<T> | ITerminalMatcher<T>
, INestedMatcher<T> | ITerminalMatcher<T>
, ...Array<INestedMatcher<T> | ITerminalMatcher<T>>
]
): INestedMatcher<T>
childNodes
function childNodes(...matchers: Array<IMatcher<Node>>): INestedMatcher<Node>
children
function children(...matchers: Array<IMatcher<Element>>): INestedMatcher<Element>
css
function css(strings: TemplateStringsArray, ...values: string[]): ITerminalMatcher<Element>
function css(selector: string): ITerminalMatcher<Element>
element
function element(
strings: TemplateStringsArray
, ...values: string[]
): (...matchers: Array<INestedMatcher<Element> | ITerminalMatcher<Element>>) => INestedMatcher<Node>
function element(name: string, ...matchers: Array<INestedMatcher<Element>>):
INestedMatcher<Node>
function element(...matchers: Array<INestedMatcher<Element>>):
INestedMatcher<Node>
multiple
interface IMultipleOptions {
greedy: boolean
}
function multiple<T extends Node>(
range: [min: number, max: number]
, matcher: INestedMatcher<T> | ITerminalMatcher<T>
, options: IMultipleOptions = { greedy: true }
): ISkipMatcher<T>
node
function node(
strings: TemplateStringsArray
, ...values: string[]
): (...matchers: Array<INestedMatcher<Node> | ITerminalMatcher<Node>>) => INestedMatcher<Node>
function node(
name: string
, ...matchers: Array<INestedMatcher<Node> | ITerminalMatcher<Node>>
): INestedMatcher<Node>
function node(
...matchers: Array<INestedMatcher<Node> | ITerminalMatcher<Node>>
): INestedMatcher<Node>
optional
function optional<T extends Node>(
matcher: INestedMatcher<T> | ITerminalMatcher<T>
): ISkipMatcher<T>
repeat
function repeat<T extends Node>(
times: number
, matcher: INestedMatcher<T> | ITerminalMatcher<T>
): ISkipMatcher<T>
tap
function tap<T extends Node, U extends ReturnType<IMatcher<any>>>(
matcher: (this: IReadonlyContext, node: T) => U
, callback: (value: U) => void
): (this: IReadonlyContext, node: T) => U
textContentEquals
interface ITextContentEqualsOptions {
caseSensitive?: boolean
trim?: boolean
}
function textContentEquals(
text: string
, {
caseSensitive = true
, trim = false
}: ITextContentEqualsOptions = {}
): ITerminalMatcher<Node>
textContentIncludes
interface ITextContentIncludesOptions {
caseSensitive?: boolean
trim?: boolean
}
export function textContentIncludes(
searchString: string
, {
caseSensitive = true
, trim = false
}: ITextContentIncludesOptions = {}
): ITerminalMatcher<Node>
textContentMatches
interface ITextContentMatchesOptions {
trim?: boolean
}
export function textContentMatches(
pattern: RegExp
, { trim = false }: ITextContentMatchesOptions = {}
): ITerminalMatcher<Node>
textNode
function textNode(
strings: TemplateStringsArray
, ...values: string[]
): (...matchers: Array<ITerminalMatcher<Node>>) => INestedMatcher<Node>
function textNode(
name: string
, ...matchers: Array<ITerminalMatcher<Node>>
): INestedMatcher<Node>
function textNode(
...matchers: Array<ITerminalMatcher<Node>>
): INestedMatcher<Node>
xpath
function xpath(
strings: TemplateStringsArray
, ...values: string[]
): ITerminalMatcher<Node>
function xpath(experssion: string): ITerminalMatcher<Node>