Skip to content

Trim Whitespace Regex (Leading and Trailing)

Strip spaces and tabs from both ends of every line in one replace, leaving the spaces between words and the line breaks themselves alone.

JavaScript
132 characters

$1 or $<name> inserts a group, $& the whole match, $$ a dollar sign.

Link optionspattern only

The address bar holds the pattern, flags and replacement, so Copy link shares them. Your test text stays out of it unless you include it (up to 2,000 characters), because it may be private. Nothing is sent to a server.

Replacements

5replacements

Every match swapped for the replacement. Copy the result below.

Result
Leading spaces on this line Trailing spaces on this one A tab before this line Both ends padded This line is already clean

Groups
none
Characters matched
10 of 132
What the pattern meansHover or tap a part to see it in the pattern and what it matched
How this works: Method, 5 sources, Checked against 1 worked example,

How this works

Method

Your pattern runs in your own browser’s JavaScript engine, in a background worker that is stopped after 1.5 seconds, so a pattern that backtracks catastrophically can’t freeze the page. The explanation comes from our own parser of the ECMAScript pattern grammar, checked against the engine; what each part matched is found by wrapping that part in one more group and running the pattern again. Conversions to other flavours only rewrite the syntax and list what their documentation says works differently.

How it’s tested

One worked example for this page is checked by automated tests before every release: given the inputs, the tool must show the expected answer.

Changes

  • First published, with a library of 19 common patterns and their test cases.

How we make toolsReport a mistake

Worked example

Take hello, the first case in the tester. Reading the pattern left to right, each part takes its share of the text:

  1. ^[ \t]+Option 1: matches
  2. [ \t]+$Or option 2:

How the trim regex works

The pattern is two alternatives joined by \|\. \^[ \t]+\ is one or more spaces or tabs right after the start of a line, and the second branch is one or more spaces or tabs right before the end of a line. With the g flag, \replace\ removes every run it finds; with the m flag, the caret and the dollar sign mean the start and end of each line, not just of the whole text. Both together trim every line of a pasted list in a single call.

Why \[ \t]\ and not \\s\? Because \\s\ also matches line breaks. With the m flag, \\s+\ before a line end would swallow the newline and the indentation of the next line, joining the lines together, and \^\s+\ would delete blank lines. Listing just the space and the tab keeps the line structure exactly as it was. Swap in \[^\S\r\n]\ (whitespace that isn't a line break) if you also want to catch non-breaking and other Unicode spaces.

For a single string, you don't need a regex at all: \str.trim()\ removes whitespace and line terminators from both ends, and \trimStart()\ and \trimEnd()\ do one side. Use the regex when you want every line trimmed, when only spaces and tabs should go, or when you need the same behaviour in a language whose trim differs.

  • String.prototype.trim() removes whitespace and line terminators from both ends of a string and returns a new string. Source: MDN: String.prototype.trim().
  • JavaScript’s whitespace includes the tab, vertical tab, form feed, space, no-break space (U+00A0), U+FEFF and every Unicode space separator; line terminators are LF, CR, U+2028 and U+2029. Source: MDN: Lexical grammar, white space.

Test cases

What the pattern finds in each line, and why.

Test cases for the Trim whitespace regex
TextFindsWhy
hello two leading spaces
hello two trailing spaces
indented line a leading tab
both sides · one match at each end
mixed a space and a tab together
one two · the m flag trims each line, and the line break stays
hellonothingnothing to trim
inner spaces staynothingspaces between words aren’t at an end
tab insidenothinga tab in the middle
 non-breakingnothinga non-breaking space isn’t in the class; trim() would remove it
xnothinga single character

What it doesn’t check

  • It leaves non-breaking spaces (U+00A0) and other Unicode spaces in place; trim() and \s remove them.
  • Windows line endings leave a \r before each \n, which this class doesn’t treat as a trailing space; add \r to the class or normalise line endings first.
  • Without the m flag it only trims the start and end of the whole text, like trim() for spaces and tabs.
  • It doesn’t collapse runs of spaces inside a line; replace two or more spaces with one in a second step if you need that.

The same pattern in other languages

Converted automatically from the JavaScript version; the tester above always runs JavaScript.

The pattern in Python, PCRE, Go, Java and .NET
FlavourPatternNotes
Python(?m)^[ \t]+|[ \t]+$In Python, pass re.MULTILINE for per-line anchors and use re.sub with an empty replacement; note that Python’s end anchor also matches just before a final newline.
PCRE(?m)^[ \t]+|[ \t]+$
Go(?m)^[ \t]+|[ \t]+$In Go, put (?m) at the start of the pattern for per-line anchors and call ReplaceAllString with an empty string.
Java(?m)^[ \t]+|[ \t]+$
.NET(?m)^[ \t]+|[ \t]+$

Sources

Frequently Asked Questions

How do I trim whitespace with a regex in JavaScript?

Replace the pattern with an empty string, using the g flag so both ends are trimmed and the m flag to do it on every line. For one string, the built-in trim method does the same job without a regex.

Why does trimming with \s join my lines together?

Because \s includes the newline. With the multi-line flag, a run of whitespace at a line end can include the line break and the next line’s indentation. Matching only spaces and tabs avoids that.

How do I also collapse double spaces inside the text?

Run a second replace that turns two or more spaces into one. Keeping it separate from the trim makes each step easy to read and test.