Js_re
Provides bindings for JavaScript Regular Expressions
Melange provides a bit of syntax sugar for regex literals: [%re "/foo/g"]
will evaluate to a t
that can be passed around and used like usual.
Note: This is not an immutable API. A RegExp object with the global
("g") flag set will modify the lastIndex
property when the RegExp object is used, and subsequent uses will ocntinue the search from the previous lastIndex
.
let maybeMatches = "banana" |> Js.String.match_ [\[%re "/na+/g"\]]
@see <https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp> JavaScript API reference on MDN
@see <https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Regular_Expressions> JavaScript Regular Expressions Guide on MDN
let captures: result => array(Js.nullable(string));
an array of the match and captures, the first is the full match and the remaining are the substring captures
let matches: result => array(string);
an array of the matches, the first is the full match and the remaining are the substring matches *
let index: result => int;
0-based index of the match in the input string
let input: result => string;
the original input string
let fromString: string => t;
Constructs a RegExp object (t
) from a string
Regex literals ([%re "/.../"]
) should generally be preferred, but fromString
is very useful when you need to insert a string into a regex.
(* A function that extracts the content of the first element with the given tag *)
let contentOf tag xmlString =
Js.Re.fromString ("<" ^ tag ^ ">(.*?)<\\/" ^ tag ^">")
|> Js.Re.exec xmlString
|> function
| Some result -> Js.Nullable.toOption (Js.Re.captures result).(1)
| None -> None
let fromStringWithFlags: string => flags:string => t;
Constructs a RegExp object (t
) from a string with the given flags
See fromString
Valid flags:
g | global | |
i | ignore case | |
m | multiline | |
u | unicode | (es2015) |
y | sticky | (es2015) |
let flags: t => string;
returns the enabled flags as a string
let global: t => bool;
returns a bool indicating whether the global
flag is set
let ignoreCase: t => bool;
returns a bool indicating whether the ignoreCase
flag is set
let lastIndex: t => int;
returns the index where the next match will start its search
This property will be modified when the RegExp object is used, if the global
("g") flag is set.
(* Finds and prints successive matches *)
let re = [%re "/ab*/g"] in
let str = "abbcdefabh" in
let break = ref false in
while not !break do
match re |> Js.Re.exec str with
| None -> break := true
| Some result ->
Js.Nullable.iter (Js.Re.captures result).(0) ((fun match_ ->
let next = string_of_int (Js.Re.lastIndex re) in
Js.log ("Found " ^ match_ ^ ". Next match starts at " ^ next)))
done
let setLastIndex: t => int => unit;
sets the index at which the next match will start its search from
let multiline: t => bool;
returns a bool indicating whether the multiline
flag is set
let source: t => string;
returns the pattern as a string
let sticky: t => bool;
returns a bool indicating whether the sticky
flag is set
let unicode: t => bool;
returns a bool indicating whether the unicode
flag is set
executes a search on a given string using the given RegExp object
returns Some
result
if a match is found, None
otherwise
(* Match "quick brown" followed by "jumps", ignoring characters in between
* Remember "brown" and "jumps"
* Ignore case
*)
let re = [%re "/quick\s(brown).+?(jumps)/ig"] in
let result = re |. Js.Re.exec_ "The Quick Brown Fox Jumps Over The Lazy Dog"
let test_: t => string => bool;
tests whether the given RegExp object will match a given string
returns true
if a match is found, false
otherwise
(* A simple implementation of Js.String.startsWith *)
let str = "hello world!"
let startsWith target substring =
Js.Re.fromString ("^" ^ substring)
|. Js.Re.test_ target
let () = Js.log (str |. startsWith "hello") (* prints "true" *)
let test: string => t => bool;