Bindings for RE2: fast, safe alternative to backtracking regular expression engines.
—
Quality
Pending
Does it follow best practices?
Impact
Pending
No eval scenarios have been run
String processing methods compatible with JavaScript's built-in string operations, enhanced with Buffer support.
Executes regex against input and returns match results, similar to String.prototype.match().
/**
* Find matches in input string or Buffer
* @param str - String or Buffer to search
* @returns Match array or null if no match
*/
regex.match(str: string): RegExpMatchArray | null;
regex.match(buffer: Buffer): RE2BufferMatchArray | null;
// Return types
interface RegExpMatchArray extends Array<string> {
index?: number; // Match position (global: undefined)
input?: string; // Original input (global: undefined)
groups?: { // Named groups
[key: string]: string;
};
}
interface RE2BufferMatchArray extends Array<Buffer> {
index?: number; // Match position in bytes (global: undefined)
input?: Buffer; // Original input (global: undefined)
groups?: { // Named groups as Buffers
[key: string]: Buffer;
};
}Behavior:
String.prototype.match() via Symbol.matchUsage Examples:
const RE2 = require("re2");
// Non-global match (first match with details)
const phoneRegex = new RE2("(\\d{3})-(\\d{4})");
const phoneText = "Call 555-1234 or 555-5678";
const singleMatch = phoneRegex.match(phoneText);
console.log(singleMatch[0]); // "555-1234" (full match)
console.log(singleMatch[1]); // "555" (first group)
console.log(singleMatch[2]); // "1234" (second group)
console.log(singleMatch.index); // 5 (position)
// Global match (all matches, no groups)
const globalRegex = new RE2("\\d{3}-\\d{4}", "g");
const allMatches = globalRegex.match(phoneText);
console.log(allMatches); // ["555-1234", "555-5678"]
// Use with string method via Symbol.match
console.log(phoneText.match(phoneRegex)); // Same as phoneRegex.match(phoneText)
// Buffer matching
const bufferRegex = new RE2("\\w+");
const buffer = Buffer.from("hello world", "utf8");
const bufferMatch = bufferRegex.match(buffer);
console.log(bufferMatch[0]); // Buffer containing "hello"
// Named groups
const namedRegex = new RE2("(?<area>\\d{3})-(?<number>\\d{4})");
const namedMatch = namedRegex.match("555-1234");
console.log(namedMatch.groups.area); // "555"
console.log(namedMatch.groups.number); // "1234"Finds the index of the first match, similar to String.prototype.search().
/**
* Find index of first match
* @param str - String or Buffer to search
* @returns Index of first match, or -1 if no match
*/
regex.search(str: string | Buffer): number;Behavior:
String.prototype.search() via Symbol.searchUsage Examples:
const RE2 = require("re2");
// String search
const regex = new RE2("\\d+");
const text = "Page 123 of 456";
console.log(regex.search(text)); // 5 (position of "123")
const notFound = new RE2("xyz");
console.log(notFound.search(text)); // -1 (no match)
// Use with string method via Symbol.search
console.log(text.search(regex)); // Same as regex.search(text)
// Buffer search (byte positions)
const bufferRegex = new RE2("world");
const buffer = Buffer.from("hello world", "utf8");
console.log(bufferRegex.search(buffer)); // 6 (byte position)
// Unicode handling
const unicodeRegex = new RE2("世界");
const unicodeBuffer = Buffer.from("hello 世界", "utf8");
console.log(unicodeRegex.search(unicodeBuffer)); // 6 (byte position of 世界)Replaces matches with replacement text or function result, similar to String.prototype.replace().
/**
* Replace matches with replacement text or function result
* @param str - String or Buffer to process
* @param replacement - Replacement string/Buffer or function
* @returns New string/Buffer with replacements (same type as input)
*/
regex.replace<K extends String | Buffer>(
str: K,
replacement: string | Buffer
): K;
regex.replace<K extends String | Buffer>(
str: K,
replacer: (substring: string, ...args: any[]) => string | Buffer
): K;Replacement Patterns:
$& - Full match$1, $2, etc. - Numbered groups$<name> - Named groups$$ - Literal $Replacer Function Parameters:
substring - The matched text...groups - Captured groups (numbered)offset - Match positioninput - Original inputnamedGroups - Object with named groupsSpecial Property:
replacer.useBuffers = true to receive Buffer arguments in replacer functionUsage Examples:
const RE2 = require("re2");
// String replacement
const phoneRegex = new RE2("(\\d{3})-(\\d{4})");
const phoneText = "Call 555-1234";
const formatted = phoneRegex.replace(phoneText, "($1) $2");
console.log(formatted); // "Call (555) 1234"
// Global replacement
const globalRegex = new RE2("\\d+", "g");
const numbers = "1 and 2 and 3";
const doubled = globalRegex.replace(numbers, (match) => String(parseInt(match) * 2));
console.log(doubled); // "2 and 4 and 6"
// Named group replacement
const namedRegex = new RE2("(?<first>\\w+) (?<last>\\w+)");
const name = "John Doe";
const swapped = namedRegex.replace(name, "$<last>, $<first>");
console.log(swapped); // "Doe, John"
// Buffer replacement
const bufferRegex = new RE2("world");
const buffer = Buffer.from("hello world", "utf8");
const replaced = bufferRegex.replace(buffer, Buffer.from("universe", "utf8"));
console.log(replaced.toString()); // "hello universe"
// Replacer function with Buffer support
const bufferReplacer = (match, offset, input) => {
return Buffer.from(match.toUpperCase(), "utf8");
};
bufferReplacer.useBuffers = true; // Receive Buffer arguments
const upperRegex = new RE2("\\w+", "g");
const upperBuffer = Buffer.from("hello world", "utf8");
const upperResult = upperRegex.replace(upperBuffer, bufferReplacer);
console.log(upperResult.toString()); // "HELLO WORLD"
// Use with string method via Symbol.replace
console.log(phoneText.replace(phoneRegex, "($1) $2")); // Same resultSplits input by regex matches, similar to String.prototype.split().
/**
* Split input by regex matches
* @param str - String or Buffer to split
* @param limit - Optional maximum number of splits
* @returns Array of string/Buffer parts (same type as input)
*/
regex.split<K extends String | Buffer>(str: K, limit?: number): K[];Behavior:
String.prototype.split() via Symbol.splitUsage Examples:
const RE2 = require("re2");
// Basic string splitting
const commaRegex = new RE2(",\\s*");
const csv = "apple, banana, cherry";
const fruits = commaRegex.split(csv);
console.log(fruits); // ["apple", "banana", "cherry"]
// Splitting with capture groups (groups included in result)
const delimiterRegex = new RE2("(,)\\s*");
const withDelimiters = delimiterRegex.split(csv);
console.log(withDelimiters); // ["apple", ",", "banana", ",", "cherry"]
// With limit
const limited = commaRegex.split(csv, 2);
console.log(limited); // ["apple", "banana"]
// Buffer splitting
const spaceRegex = new RE2("\\s+");
const buffer = Buffer.from("hello world test", "utf8");
const parts = spaceRegex.split(buffer);
console.log(parts.map(b => b.toString())); // ["hello", "world", "test"]
// Use with string method via Symbol.split
console.log(csv.split(commaRegex)); // Same as commaRegex.split(csv)
// Complex splitting with multiple delimiters
const multiRegex = new RE2("[,;]\\s*");
const mixed = "a,b; c , d;e";
const mixedParts = multiRegex.split(mixed);
console.log(mixedParts); // ["a", "b", "c", "d", "e"]RE2 implements Symbol methods to enable seamless integration with JavaScript string methods:
/**
* Symbol methods for string integration
*/
regex[Symbol.match](str: string): RegExpMatchArray | null;
regex[Symbol.search](str: string): number;
regex[Symbol.replace](str: string, replacement: string | Function): string;
regex[Symbol.split](str: string, limit?: number): string[];
regex[Symbol.matchAll](str: string): Iterator<RegExpExecArray>;matchAll Method (requires global flag):
const RE2 = require("re2");
// matchAll requires global flag
const globalRegex = new RE2("\\d+", "g");
const text = "1 and 2 and 3";
// Use Symbol.matchAll
for (const match of text.matchAll(globalRegex)) {
console.log(match[0], "at position", match.index);
}
// Output:
// "1" at position 0
// "2" at position 6
// "3" at position 12
// Convert to array
const allMatches = Array.from(text.matchAll(globalRegex));
console.log(allMatches.length); // 3
// Non-global regex throws TypeError
const nonGlobal = new RE2("\\d+");
try {
Array.from(text.matchAll(nonGlobal)); // Throws TypeError
} catch (e) {
console.log(e.message); // String.prototype.matchAll called with non-global RE2
}Install with Tessl CLI
npx tessl i tessl/npm-re2