PHPackages                             edwinhuish/domquery - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Parsing &amp; Serialization](/categories/parsing)
4. /
5. edwinhuish/domquery

ActiveLibrary[Parsing &amp; Serialization](/categories/parsing)

edwinhuish/domquery
===================

DomQuery is a PHP library that allows easy 'jQuery like' DOM traversing and manipulation

v1.1.3(5y ago)712711MITPHPPHP ^7.0.0

Since Oct 6Pushed 5y agoCompare

[ Source](https://github.com/edwinhuish/DomQuery)[ Packagist](https://packagist.org/packages/edwinhuish/domquery)[ RSS](/packages/edwinhuish-domquery/feed)WikiDiscussions master Synced 4d ago

READMEChangelogDependencies (6)Versions (51)Used By (1)

DomQuery
========

[](#domquery)

[English](README.md) | [中文说明](README-ZH.md)

DomQuery is a PHP library that allows you to easily traverse and modify the DOM (HTML/XML). As a library it aims to provide 'jQuery like' access to the [PHP DOMDocument class](http://php.net/manual/en/book.dom.php).

Installation
------------

[](#installation)

Install the latest version with

```
$ composer require edwinhuish/domquery
```

Basic Usage
-----------

[](#basic-usage)

### Read attributes and properties:

[](#read-attributes-and-properties)

```
$dom = new DomQuery('Hello');

echo $dom->find('h1')->text(); // output: Hello
echo $dom->find('div')->prop('outerHTML'); // output: Hello
echo $dom->find('div')->html(); // output: Hello
echo $dom->find('div > h1')->class; // output: title
echo $dom->find('div > h1')->attr('class'); // output: title
echo $dom->find('div > h1')->prop('tagName'); // output: h1
echo $dom->find('div')->children('h1')->prop('tagName'); // output: h1
echo (string) $dom->find('div > h1'); // output: Hello
echo count($dom->find('div, h1')); // output: 2
```

### Traversing nodes (result set):

[](#traversing-nodes-result-set)

```
$dom = new DomQuery('1 2 3');
$links = $dom->children('a');

// foreach
$texts = [];
foreach($links as $key => $dq) { // $dq is DomQuery object
    $texts[] = $dq->text();
}
print_r($texts); // array('1','2','3')

// map
$result = $links->map(function(DomQuery $dq, int $idx){
    return $dq->text();
});
// map method return Collection object
print_r($result->toArray()); // array('1','2','3')

// each, same as Collection's each method, break traversing if return false.
$links->each(function(DomQuery $dq, int $idx){
    if($idx === 1){
        return false;
    }
    $dq->text('changed');
});
print_r($links->texts()); // array('changed', '2', '3')

echo $links->text(); // output 1, return text of first child, if you need the result of all childs please use texts() or foreach, each, map method
echo $links[0]->text(); // output 1
echo $links->last()->text(); // output 3
echo $links->first()->next()->text(); // output 2
echo $links->last()->prev()->text(); // output 2
echo $links->get(0)->textContent; // output 1
echo $links->get(-1)->textContent; // output 3
```

### Factory method (create instance alternative):

[](#factory-method-create-instance-alternative)

```
DomQuery::create('')->attr('title') // hello
```

Jquery methods available
------------------------

[](#jquery-methods-available)

#### Traversing &gt; Tree Traversal

[](#traversing--tree-traversal)

- `.find( selector )`
- `.children( [selector] )`
- `.parent( [selector] )`
- `.closest( [selector] )`
- `.next( [selector] )`
- `.prev( [selector] )`
- `.nextAll( [selector] )`
- `.prevAll( [selector] )`
- `.siblings( [selector] )`

#### Traversing &gt; Miscellaneous Traversing

[](#traversing--miscellaneous-traversing)

- `.contents()` get children including text nodes
- `.add( selector, [context] )` new result with added elements that match selector

#### Traversing &gt; Filtering

[](#traversing--filtering)

- `.is( selector )`
- `.filter ( selector )` reduce to those that match the selector
- `.not( selector )` remove elements from the set of matched elements
- `.has( selector )` reduce to those that have a descendant that matches the selector
- `.first( [selector] )`
- `.last( [selector] )`
- `.slice( [offset] [, length])` like [array\_slice in php](http://php.net/manual/en/function.array-slice.php), not js/jquery
- `.eq( index )`
- `.map( callable(elm,i) )`

\* **\[selector\]** can be a css selector or an instance of DomQuery|DOMNodeList|DOMNode

#### Manipulation &gt; DOM Insertion &amp; removal

[](#manipulation--dom-insertion--removal)

- `.text( [text] )`
- `.html( [html_string] )`
- `.append( [content],... )`
- `.prepend( [content],... )`
- `.after( [content],... )`
- `.before( [content],... )`
- `.appendTo( [target] )`
- `.prependTo( [target] )`
- `.replaceWith( [content] )`
- `.wrap( [content] )`
- `.wrapAll( [content] )`
- `.wrapInner( [content] )`
- `.remove( [selector] )`
- `.unwrap()`
- `.first()`
- `.last()`
- `.gt( int $index )`
- `.lt( int $index )`

\* **\[content\]** can be html or an instance of DomQuery|DOMNodeList|DOMNode

#### Attributes | Manipulation

[](#attributes--manipulation)

- `.attr( name [, val] )`
- `.prop( name [, val] )`
- `.css( name [, val] )`
- `.removeAttr( name )`
- `.addClass( name )`
- `.hasClass( name )`
- `.toggleClass ( name )`
- `.removeClass( [name] )`

\* addClass, removeClass, toggleClass and removeAttr also accepts an array or space-separated **names**

#### Miscellaneous &gt; DOM Element Methods | Traversing | Storage

[](#miscellaneous--dom-element-methods--traversing--storage)

- `.get( index )`
- `.each ( callable(elm,i) )`
- `.data ( key [, val] )`
- `.removeData ( [name] )`
- `.index ( [selector] )`
- `.toArray()`
- `.clone()`

Supported selectors
-------------------

[](#supported-selectors)

- `.class`
- `#foo`
- `parent > child`
- `foo, bar` multiple selectors
- `prev + next` elements matching "next" that are immediately preceded by a sibling "prev"
- `prev ~ siblings` elements matching "siblings" that are preceded by "prev"
- `*` all selector
- `[name="foo"]` attribute value equal foo
- `[name*="foo"]` attribute value contains foo
- `[name~="foo"]` attribute value contains word foo
- `[name^="foo"]` attribute value starts with foo
- `[name$="foo"]` attribute value ends with foo
- `[name|="foo"]` attribute value equal to foo, or starting foo followed by a hyphen (-)

### Pseudo selectors

[](#pseudo-selectors)

- `:empty`
- `:even`
- `:odd`
- `:first-child`
- `:last-child`
- `:only-child`
- `:parent` elements that have at least one child node
- `:first`
- `:last`
- `:header` selects h1, h2, h3 etc.
- `:not(foo)` elements that do not match selector foo
- `:has(foo)` elements containing at least one element that matches foo selector
- `:contains(foo)` elements that contain text foo
- `:root` element that is the root of the document
- `:nth-child(n)`
- `:nth-child(even)`
- `:nth-child(odd)`
- `:nth-child(3n+8)`
- `:nth-child(2n+1)`
- `:nth-child(n+4)` same as `:gt(2)`
- `:nth-child(-n+4)` same as `:lt(4)`
- `:nth-child(3)`
- `:nth-child(-2)`
- `:nth-child(4n)`
- `:eq(0)`
- `:eq(-1)`
- `:lt(3)`
- `:gt(2)`

Other (non jQuery) methods
--------------------------

[](#other-non-jquery-methods)

- `findOrFail( selector )` find descendants of each element in the current set of matched elements, or throw an exception
- `loadContent(content, encoding='UTF-8')` load html/xml content
- `xpath(xpath_query)` Use xpath to find descendants of each element in the current set of matched elements
- `getOuterHtml()` get resulting html describing all the elements (same as `(string) $dom`, or `$elm->prop('outerHTML')`)
- `getRoot()` get the root node

XML support
-----------

[](#xml-support)

- XML content will automatically be loaded '[as XML](http://php.net/manual/en/domdocument.loadxml.php)' if a [XML declaration](http://xmlwriter.net/xml_guide/xml_declaration.shtml) is found (property `xml_mode` will be set to true)
- This in turn will also make saving (rendering) happen '[as XML](http://php.net/manual/en/domdocument.savexml.php)'. You can set property `xml_mode` to false to prevent this.
- To prevent content with a XML declaration loading 'as XML' you can set property `xml_mode` to false and then use the `loadContent($content)` method.
- Namespaces are automatically registered (no need to do it [manually](http://php.net/manual/en/domxpath.registernamespace.php))

Escaping meta chars in selector to find elements with namespace:

```
$dom->find('namespace\\:h1')->text();
```

About
-----

[](#about)

### Requirements

[](#requirements)

- Works with PHP 7.0 or above
- Requires libxml PHP extension (enabled by default)

### Fork from

[](#fork-from)

-

###  Health Score

33

—

LowBetter than 75% of packages

Maintenance20

Infrequent updates — may be unmaintained

Popularity16

Limited adoption so far

Community11

Small or concentrated contributor base

Maturity71

Established project with proven stability

 Bus Factor1

Top contributor holds 89.7% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~22 days

Recently: every ~46 days

Total

50

Last Release

2038d ago

Major Versions

v0.8 → v1.0.02020-04-02

### Community

Maintainers

![](https://www.gravatar.com/avatar/d4ac26d4cd6e8516f3bec4cf57850c4d7c54ede8e26495c7bb0691b3ed254149?d=identicon)[edwinhuish](/maintainers/edwinhuish)

---

Top Contributors

[![Rct567](https://avatars.githubusercontent.com/u/1885003?v=4)](https://github.com/Rct567 "Rct567 (280 commits)")[![edwinhuish](https://avatars.githubusercontent.com/u/5207925?v=4)](https://github.com/edwinhuish "edwinhuish (32 commits)")

---

Tags

domdomqueryjqueryphpquerysimple-html-domxmlcsshtmldomjqueryselector

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan

Code StylePHP\_CodeSniffer

Type Coverage Yes

### Embed Badge

![Health badge](/badges/edwinhuish-domquery/health.svg)

```
[![Health](https://phpackages.com/badges/edwinhuish-domquery/health.svg)](https://phpackages.com/packages/edwinhuish-domquery)
```

###  Alternatives

[rct567/dom-query

DomQuery is a PHP library that allows easy 'jQuery like' DOM traversing and manipulation

134261.0k4](/packages/rct567-dom-query)[masterminds/html5

An HTML5 parser and serializer.

1.8k242.8M229](/packages/masterminds-html5)[querypath/querypath

HTML/XML querying and processing (like jQuery)

8197.0M27](/packages/querypath-querypath)[gravitypdf/querypath

PHP library for HTML(5)/XML querying (CSS 4 or XPath) and processing (like jQuery) with PHP 7.1 to 8.5 support

281.2M1](/packages/gravitypdf-querypath)[scotteh/php-dom-wrapper

Simple DOM wrapper to select nodes using either CSS or XPath expressions and manipulate results quickly and easily.

1471.9M10](/packages/scotteh-php-dom-wrapper)[fluentdom/fluentdom

A fluent api for the php dom extension.

337306.9k17](/packages/fluentdom-fluentdom)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
