Glob
Allow you to match a string against a glob like pattern. You can find it in the @banquette/utils-glob
package.
Introduction
This package is not meant to support all the edge cases of the glob notation. In fact, it supports only the very basics, making it very lightweight.
The reason this package exists instead of using one of the thousands libraries out there, is mainly because of a need of partial matches.
In @banquette/form
for example, it is very useful to know if a mask partially match, to know to go down and test the children.
Anyway, if it can be of any use outside of Banquette
, the doc is worth it.
How it works
You have two methods at your disposal:
/**
* Match a mask against a path.
*/
match(mask: string, path: string, tags?: string[]): MatchResult;
/**
* Match multiple patterns and keep the best result.
*/
matchBest(masks: string[], path: string, tags?: string[]): MatchResult;
The mask
is the glob pattern, the path
is the string being tested. Here is a usage example:
import { MatchResult } from "@banquette/utils-glob";
const result: MatchResult = match('/category/*', '/category/name');
if (result.pattern === MatchType.Full) {
// The pattern fully matches.
}
Match result
MatchResult
is an object containing the following:
interface MatchResult {
/**
* Hold how the pattern part of the mask match.
*
* - MatchType.Full: the pattern perfectly match
* - MatchType.Partial: the beginning of the path match the pattern
* - MatchType.None: the pattern doesn't match at all
*/
pattern: MatchType;
/**
* Hold how the mask's tags match the subject.
*
* - MatchType.Full: all tags defined in the pattern have been found
* - MatchType.Partial: some tags defined in the pattern have been found
* - MatchType.None: none of the tags defined in the pattern have been found
*/
tags: MatchType;
}
MatchType
is th following:
enum MatchType {
None,
Partial,
Full
}
Tags
The third parameter of both match
and matchBest
takes an array of String
, called tags.
Tags are suffixes that can optionally be added to a mask, this is used in @banquette/form
to add the active states of the components being tested:
const path = '/category/name:focused:enabled';
const result = match(path, '/category/*', ['enabled']);
Here we're matching any path under /category/
that have at least a enabled
tag.
This is totally optional.
Examples
Here are some usage examples so you can see what syntax is supported:
// Fixed pattern
match('/firstName', '/firstName'); // full
match('/firstName', '/'); // partial
match('/category/name', '/category/name'); // full
match('/category/name', '/category'); // partial
match('/non-existent', '/'); // partial
// Star
match('/tags/*/color', '/tags/0/color'); // full
match('/tags/*/*', '/'); // partial
match('/*Name', '/firstName'); // full
match('/*Name', '/lastName'); // full
match('/*Name', '/'); // partial
// Globstar
match('/**/name', '/category/name'); // full
match('/**/name', '/articles/0/category/name'); // full
match('/**/name', '/tags/0/name'); // full
match('/**/name', '/'); // partial
match('/**/name', '/firstName'); // partial
match('/tags/**', '/tags'); // full
match('/tags/**', '/tags/0/color'); // full
match('/tags/**', '/tags/0/name'); // full
match('/tags/**', '/tags/0'); // full
match('/tags/**', '/'); // partial
// choices
match('/{firstName,lastName}', '/firstName'); // full
match('/{firstName,lastName}', '/lastName'); // full
match('/{category,tags}/name', '/category/name'); // full
match('/{category,tags}/name', '/category'); // partial