Symfony DomCrawler

A PHP component for navigating, filtering, and extracting data from HTML and XML documents.

Library
Composer
vv8.1.1
4,028stars
MIT License

Repository Health

Pre-computed score based on development activity, maintenance, community, maturity, and trend momentum.How we score it →
81/100Excellent
Development Activity80
Maintenance84
Community60
Maturity60
Momentum40

Technical Analysis

AI-assessed by reading the actual repository — architecture, code quality, innovation, and documentation.How we score it →
78/100Good
Architecture82
Code Quality85
Innovation68
Learning Curve75

The DomCrawler component wraps PHP’s native DOM extension with an ergonomic, chainable API for walking HTML and XML documents. Its Crawler class parses a document (or accepts an existing DOMDocument/DOMNodeList) and lets you filter nodes with CSS selectors (via the companion symfony/css-selector component) or raw XPath, then extract text, attributes, or navigate to parent/sibling/child nodes — all while returning a new Crawler instance so calls can be chained.

Beyond read-only traversal, it models HTML forms (Form, FormFieldRegistry) and links (Link, Image) as first-class objects, so a scraper or functional test can select a <form>, fill its fields, and read back the resulting request parameters without hand-parsing the markup. It’s a foundational piece of the Symfony ecosystem — used directly by symfony/browser-kit and Symfony’s functional-testing stack (WebTestCase), and widely reused standalone in scraping and HTML-processing tools outside of full Symfony applications.

What You Get

  • A Crawler class that parses HTML/XML strings (or wraps existing DOMDocument/DOMNodeList instances) and supports CSS-selector filtering (via symfony/css-selector) or raw XPath queries
  • Chainable traversal methods (filter(), filterXPath(), eq(), first(), last(), parents(), siblings(), children()) that each return a new Crawler
  • Extraction helpers (text(), attr(), extract(), html()) for pulling data out of matched nodes without manual DOM API calls
  • First-class Form and FormFieldRegistry objects that let you select a form, set field values, and read back submission data as an array
  • Link and Image value objects for extracting anchor/image URIs, plus UriResolver for resolving relative URIs against a base

Common Use Cases

  • Functional/integration testing of web applications — Symfony’s WebTestCase uses DomCrawler under the hood to let tests assert on rendered HTML and submit forms
  • Web scraping and HTML data extraction tools that need reliable CSS-selector/XPath querying without hand-rolling DOM traversal
  • Static site or content pipelines that need to parse and transform HTML fragments (e.g., extracting all links or images from a rendered page)
  • Browser-automation-adjacent tooling (paired with symfony/browser-kit) for headless HTTP-based crawling and form submission

Under The Hood

Architecture — The core Crawler class (Crawler.php, ~1,217 lines) implements \Countable and \IteratorAggregate over a collection of \DOMNode objects. Filtering methods (filter(), filterXPath()) translate CSS selectors into XPath via an injected CssSelectorConverter (from symfony/css-selector, an optional dev/runtime dependency) and run them against the wrapped nodes, always returning a fresh immutable-feeling Crawler instance rather than mutating in place. Form handling is split into Form (represents a single <form> and orchestrates its fields) and FormFieldRegistry (indexes fields by name, handling PHP’s array-style field naming like field[]), while Link/Image/AbstractUriElement model anchor and image elements with UriResolver handling relative-to-absolute URI resolution. Tech Stack — Pure PHP (>=8.4.1 for this HEAD version) built directly on ext-dom, with symfony/polyfill-ctype and symfony/polyfill-mbstring as the only hard runtime dependencies and symfony/css-selector as an optional dev dependency for CSS-selector support. No external HTTP client is bundled — DomCrawler only parses/traverses markup you hand it, leaving fetching to symfony/browser-kit or any HTTP client. Code Quality — 17 test files under Tests/ cover the Crawler, Form, FormFieldRegistry, Link, Image, and UriResolver classes; as a core Symfony component it follows Symfony’s strict internal coding standards, uses typed properties throughout, and carries a CHANGELOG documenting behavior changes release-over-release — commit activity of ~3.7/month reflects steady maintenance rather than heavy churn for a mature, feature-complete component. API Design — The fluent, chainable design ($crawler->filter('.item')->each(fn ($node) => $node->text())) mirrors jQuery-style DOM traversal, which makes it immediately familiar to anyone who has done client-side DOM work, and the form/link abstractions remove the need to hand-write markup parsing for the two most common scraping/testing needs (reading forms, following links).

Join founders buildingwith open source

Opinionated takes, migration guides, cost-saving tips, and insights from the open source ecosystem.

Subscribe on Substack
Join 750+ subscribers

Search