strip_tags

Removes HTML, XML and PHP tags from a string, optionally keeping a list of allowed tags.

Signature
strip_tags(string $string, array|string|null $allowed_tags = null): string
  • Added in PHP 4.0

Parameters

ParameterTypeDescription
$stringstringThe input string.
$allowed_tagsoptionalarray|string|null= nullTags that should not be stripped, either as an array of names like ['p','a'] or a string like '<p><a>'.

Return value

stringThe input string with tags removed.

Changelog

  • PHP 8.0.0allowed_tags is nullable.
  • PHP 7.4.0allowed_tags also accepts an array of tag names, which avoids the fiddly '<p><a>' string format.

Two more surprises. Text containing a bare < that is immediately followed by a non-space character, such as 5 <10 and up, loses everything from the < onwards because it looks like an unterminated tag. A < followed by whitespace is left alone, so 5 < 10 and up survives unchanged — but do not rely on that spacing quirk; encode literal angle brackets as &lt; instead. And stripping tags glues words together — <li>a</li><li>b</li> becomes ab, so replace block tags with spaces or newlines first if you care about readability.

Example

Try it yourself
Loading editor…
Press Run to execute the code.

When to use it

  • Generate a plain-text email body or meta description from stored HTML
  • Build a short preview snippet for a blog listing page
  • Reduce user-submitted rich text to a small allowed subset such as <p><b><i>

Frequently asked questions

Is strip_tags enough to prevent XSS?

No. It keeps attributes on allowed tags, so an allowed <a> or <img> can still carry onclick, onerror or a javascript: URL. Use htmlspecialchars() to display untrusted text, or a dedicated HTML sanitiser if you must keep real markup.

How do I keep some tags with strip_tags?

Pass them as the second argument, either as an array like ['p','a','br'] (PHP 7.4+) or as a string like '<p><a><br>'. List only the non-self-closing form: self-closing XHTML tags are ignored, so '<br>' already allows both <br> and <br/>, while writing '<br/>' in the allowed list does not work.

Why does strip_tags delete text after a less-than sign?

A < that is immediately followed by a non-space character looks like the start of a tag, so everything from there to the next > (or the end of the string) is removed — 'a <b c' loses the tail. A < followed by whitespace is treated as a literal character and is left alone, so 'a < b' comes back unchanged. Do not depend on that distinction: encode literal angle brackets as &lt; and &gt; before stripping.

More examples

Words running together

The first line prints "onetwothree" because the tags carried the visual separation. Inserting a space before stripping restores readable text, which matters for previews and search indexes.

Example · php
<?php
$html = '<li>one</li><li>two</li><li>three</li>';
echo strip_tags($html), "\n";                        // onetwothree
$spaced = str_replace('</li>', "</li> ", $html);
echo trim(strip_tags($spaced)), "\n";                // one two three

Stray angle brackets eat text

The first line prints just "5 " because the < is immediately followed by a digit, so everything from there on is treated as an unterminated tag and discarded. The second line survives unchanged: strip_tags treats a < that is followed by whitespace as a literal character, which is why var_dump(strip_tags('a < b')) returns string(5) "a < b". Encoding literal angle brackets as &lt; before stripping keeps the sentence intact in either case.

Example · php
<?php
echo strip_tags('5 <10 and rising'), "\n";   // "5 " - no space after <
echo strip_tags('5 < 10 and rising'), "\n";  // "5 < 10 and rising" - kept intact
echo strip_tags('<p>5 &lt; 10 and rising</p>'), "\n";
var_dump(strip_tags('a < b'));               // string(5) "a < b"

Safe display of untrusted input

Allowing <img> lets the onerror attribute through untouched, which is a live XSS vector. htmlspecialchars escapes the angle brackets so the browser shows the markup as text instead of running it.

Example · php
<?php
$input = '<img src=x onerror="alert(1)">';
echo strip_tags($input), "\n";                     // (empty - tag removed)
echo strip_tags($input, '<img>'), "\n";            // handler survives!
echo htmlspecialchars($input, ENT_QUOTES), "\n";   // rendered as text

Discussion

  • Be the first to comment on this lesson.