---
title: Regex
description: Match, extract and replace text with a regular expression
---

Pull a price, an id or any other fragment out of text, rewrite text, or check whether it contains a pattern.

## Try it

## What it does

Regex runs a regular expression on the text of each incoming item and does one of four things, set by **Operation**:

* **Match**: finds the first match.
* **Match all**: finds every match and sends one item per match.
* **Replace**: puts **Replacement** in place of the match.
* **Test**: answers `true` or `false`.

Named groups do most of the work. A group such as `(?<amount>[\d.,]+)` becomes a field called `amount` on the outgoing item, so one Regex node can split a sentence into clean fields.

Matching runs with a 2-second time limit. A pattern that would take too long is stopped with an error instead of freezing the browser. The text can be up to 2,000,000 characters and the pattern up to 2,000.

## When to use it

* Extract a price, order number or date from text you scraped from a page.
* Split one text field into several fields with named groups.
* Clean text, for example remove every non-digit from a phone number.
* Branch on whether text contains something: run **Test**, then an [IF](/nodes/builtin/flow/if/) on the result. For a simple "contains" check, IF alone is enough.

## Inputs and settings

* **Where the text comes from.** **Text** wins if it is filled, for example with `{{ $input.description }}`. Otherwise the node reads the field named in **Source Field** (dots reach nested fields, such as `product.title`).
* **Replace changes only the first match** unless you turn on the **All matches (g)** flag. **Match all** always finds every match, with or without the flag.
* **Replacement** can reuse groups: `$1` for the first group, `$<amount>` for a named group.
* **Maximum Matches** can be raised to 10,000 at most.

## Outputs

The result goes in **Put Result In Field** (`match` by default). With **Include Input Fields** on, the incoming fields stay on the item too.

* **Test**: the result field is `true` or `false`.
* **Replace**: the result field holds the new text.
* **Match**: the result field holds the first match, or `null`. The item also gets `matched` (`true` or `false`), `groups` (a list of the numbered groups) and one field per named group. `(?<currency>[£$€])(?<amount>[\d.,]+)` on `"Now $19.99"` gives `match: "$19.99"`, `currency: "$"`, `amount: "19.99"`.
* **Match all**: one item per match, each with the same fields plus `index`, the match's position in the text. If the match count hit **Maximum Matches**, each item also has `truncated: true`. If nothing matched, one item comes out with `matched: false`.

## Dependencies and credentials

None. This node needs no connection and has no slots for other nodes.

## Example workflow

1. [Get HTML from Link](/nodes/builtin/core/gethtmlfromlink/) loads a product page, and [HTML Extract](/nodes/builtin/datatransformation/html-extract/) reads the price text into a `price` field.
2. Regex with **Operation** *Match*, **Source Field** `price` and **Pattern** `(?<currency>[£$€])(?<amount>[\d.,]+)`.
3. An [IF](/nodes/builtin/flow/if/) checks whether `{{ $input.amount }}` is below your budget, as a number.
4. On the true branch, a [Browser Notification](/nodes/extension/browsernotification/) shows `Now {{ $input.currency }}{{ $input.amount }}`.

## Common issues

* **"This is not a valid regular expression: …".** The pattern has a syntax error, often an unclosed bracket or group. Write it without surrounding slashes: `\d+`, not `/\d+/`.
* **"This pattern took longer than 2000ms against this text and was stopped."** Nested repeats such as `(a+)+` can take forever on some text. Make the pattern more specific, or match against less text.
* **"No text to match against. Fill in the Text field, or name the field holding it."** Both **Text** and **Source Field** are empty. Fill one of them.
* **"Field "…" does not exist on the incoming item."** **Source Field** names a field the item does not have, or it is empty. Check the spelling.
* **`matched` is `false` but the text looks right.** Matching is case sensitive by default: add the **Ignore case (i)** flag. For `^` and `$` to work on every line, add **Multiline anchors (m)**.

## Recipes with this node

## Related nodes

* [Text / Formatter](/nodes/builtin/datatransformation/text-formatter/): ready-made text changes without writing a pattern.
* [HTML Extract](/nodes/builtin/datatransformation/html-extract/): read values from a page by CSS selector.
* [Edit Fields](/nodes/builtin/datatransformation/editfields/): reshape the item after extraction.
* [Code](/nodes/builtin/core/code/): for logic a pattern cannot express.