Commit Graph
573 Commits
Author SHA1 Message Date
AdamMagued 43d43df867 fix: account for form ancestor context in HTML fragment cache
golang.org/x/net/html.ParseFragmentWithOptions initializes its form
pointer based on whether the context element or any of its ancestors
is a form element. If the context has a form ancestor, nested form tags
are discarded per HTML parsing rules.

Previously, cachedParseHtmlWithContext keyed cached fragments strictly
by context tag name. When a selection contained targets both inside and
outside forms sharing the same tag name, the first visited target cached
its parsed fragment, leading to incorrect parsing for subsequent targets
under the other form-ancestor state.

Differentiate the fragment cache key by appending a form-ancestor
indicator when context or any of its ancestors is a form element.

Fixes #614
2026-10-02 15:22:07 +00:00
Martin Angers 0ac714270a Small tweak to the new constructor documentation 2026-09-30 13:43:55 -04:00
Martin Angers 21bd64ed78 Merge pull request #602 from dualfroz/dualfroz/parse-options
Expose html parse options (addresses #139, noscript)
2026-09-30 13:41:03 -04:00
Martin Angers 73a43325a0 Merge pull request #610 from x0Lazarus/fix/class-operations-non-element-nodes
Fix class and attribute updates on non-element nodes
2026-09-27 13:08:25 -04:00
x0Lazarus 98874176d7 Skip non-element nodes in SetAttr 2026-09-27 09:16:28 -07:00
x0Lazarus 4d595fbf01 Avoid class-operation panics on non-element nodes 2026-09-26 18:02:21 -07:00
DualFroz 0a624966d3 Apply the document's parse options to HTML added to it later 2026-09-23 07:01:09 +02:00
Martin Angers bcca4a34f8 Merge pull request #609 from agammann/fix-clone-node-namespaces
Preserve SVG and MathML namespaces when cloning nodes
2026-09-22 11:23:20 -04:00
agammann d205b43042 Preserve SVG and MathML namespaces when cloning nodes 2026-09-20 15:01:12 -07:00
Martin Angers 5ee0843df1 Merge pull request #604 from PuerkitoBio/dependabot/go_modules/github.com/andybalholm/cascadia-1.3.5
build(deps): bump github.com/andybalholm/cascadia from 1.3.4 to 1.3.5
2026-09-08 11:15:24 -04:00
dependabot[bot] dd800704d1 build(deps): bump github.com/andybalholm/cascadia from 1.3.4 to 1.3.5
Bumps [github.com/andybalholm/cascadia](https://github.com/andybalholm/cascadia) from 1.3.4 to 1.3.5.
- [Release notes](https://github.com/andybalholm/cascadia/releases)
- [Commits](https://github.com/andybalholm/cascadia/compare/v1.3.4...v1.3.5)

---
updated-dependencies:
- dependency-name: github.com/andybalholm/cascadia
  dependency-version: 1.3.5
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-09-08 05:52:20 +00:00
Martin Angers ef5f2ddf71 Merge pull request #600 from udf2457/manipulateNodes
Clone and reverse nodes slice for safe manipulation
2026-09-07 11:13:08 -04:00
Martin Angers 3d22a4dd10 Merge pull request #603 from dualfroz/dualfroz/fix-removeclass-duplicates
RemoveClass leaves a class behind when the source repeats it
2026-09-07 10:29:11 -04:00
dualfroz 81f35db25a feat: add NewDocumentFromReaderWithOptions
goquery calls html.Parse, so callers cannot reach the parse options that
golang.org/x/net/html has since grown. The one that matters is
ParseOptionEnableScripting(false): with scripting assumed enabled the
contents of a noscript element are parsed as raw text and no selector
can reach inside it.

Add a constructor taking html.ParseOption values. Existing constructors
are untouched.

Refs #139
2026-09-06 01:24:56 +02:00
dualfroz b4ef68dec8 fix: remove every occurrence of a repeated class
RemoveClass deleted each class with one strings.ReplaceAll pass over the
space-wrapped class list. Two adjacent occurrences share the space
between them, so " a a " holds only one non-overlapping " a " and the
second survived: RemoveClass("a") on class="a a" returned with
HasClass("a") still true. ToggleClass used the same expression and so
toggled such a class the wrong way.

Replace one occurrence at a time, re-scanning from the start, in a helper
shared by both call sites. Whitespace between the remaining classes is
untouched.
2026-09-06 00:44:19 +02:00
Martin Angers 738783cbc3 Merge pull request #597 from udf2457/master
Refactor IsMatcher to use slices.ContainsFunc
2026-09-04 11:11:08 -04:00
udf2457 a80a922806 Clone and reverse nodes slice for safe manipulation
Clone the slice before reversing to avoid modifying the caller's slice.
2026-09-04 16:08:58 +01:00
udf2457 8cb3ddf6e3 Refactor IsMatcher to use slices.ContainsFunc 2026-09-04 15:38:40 +01:00
Martin Angers 4a4f1326fa Linkify github usernames v1.13.0 2026-08-27 09:17:53 -04:00
Martin Angers e47f3848de Add new version to readme to prepare 1.13 release 2026-08-27 09:15:43 -04:00
Martin Angers 80a9b7fb55 Run CI on go1.27 (+1.26) 2026-08-27 09:09:59 -04:00
Martin Angers ad18e5a957 Merge pull request #596 from ChrisJr404/text-toplevel-func
Add top-level Text function for BeautifulSoup-style text extraction
2026-08-27 09:08:42 -04:00
Chris (ChrisJr404) 4e49d09e18 add tests for empty and fully-filtered selections 2026-08-24 14:00:20 -04:00
Chris (ChrisJr404) 91ed06d7c5 Add top-level Text function for BeautifulSoup-style text extraction
Adds goquery.Text(s, *TextOptions), a package-level counterpart to the
Selection.Text method that gives control over how the text of distinct
text nodes is joined (Separator), whether each node is trimmed of
surrounding whitespace (Trim), and which text nodes are included (Keep).
This covers the common need to extract clean, readable text from a
document - for example joining fragments with a space and dropping the
text of script/style elements - without hand-rolling a node walk.

Passing a nil TextOptions keeps the behaviour identical to Selection.Text.
Includes tests and a runnable example.
2026-08-18 08:54:59 -04:00
Martin Angers 105f3990ac Merge pull request #595 from PuerkitoBio/dependabot/go_modules/golang.org/x/net-0.58.0
build(deps): bump golang.org/x/net from 0.57.0 to 0.58.0
2026-08-17 09:17:03 -04:00
dependabot[bot] d329e294ad build(deps): bump golang.org/x/net from 0.57.0 to 0.58.0
Bumps [golang.org/x/net](https://github.com/golang/net) from 0.57.0 to 0.58.0.
- [Commits](https://github.com/golang/net/compare/v0.57.0...v0.58.0)

---
updated-dependencies:
- dependency-name: golang.org/x/net
  dependency-version: 0.58.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-08-17 05:52:35 +00:00
Martin Angers 53a9b37ea8 Merge pull request #586 from jvoisin/cachephwc
cleanup: extract cachedParse helper for parse-result reuse
2026-07-31 10:27:25 -04:00
Martin Angers 50e9856dda Merge pull request #593 from PuerkitoBio/dependabot/go_modules/golang.org/x/net-0.57.0
build(deps): bump golang.org/x/net from 0.56.0 to 0.57.0
2026-07-17 16:17:28 -04:00
Martin Angers 3a8dfd5b5f Merge pull request #592 from PuerkitoBio/dependabot/github_actions/actions/checkout-7
build(deps): bump actions/checkout from 6 to 7
2026-07-16 13:44:18 -04:00
dependabot[bot] a92dca932b build(deps): bump actions/checkout from 6 to 7
Bumps [actions/checkout](https://github.com/actions/checkout) from 6 to 7.
- [Release notes](https://github.com/actions/checkout/releases)
- [Changelog](https://github.com/actions/checkout/blob/main/CHANGELOG.md)
- [Commits](https://github.com/actions/checkout/compare/v6...v7)

---
updated-dependencies:
- dependency-name: actions/checkout
  dependency-version: '7'
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-07-16 17:32:11 +00:00
Martin Angers 91fa5c4527 Merge pull request #594 from PuerkitoBio/dependabot/github_actions/actions/setup-go-7
build(deps): bump actions/setup-go from 6 to 7
2026-07-16 13:30:13 -04:00
dependabot[bot] a72ee866ea build(deps): bump actions/setup-go from 6 to 7
Bumps [actions/setup-go](https://github.com/actions/setup-go) from 6 to 7.
- [Release notes](https://github.com/actions/setup-go/releases)
- [Commits](https://github.com/actions/setup-go/compare/v6...v7)

---
updated-dependencies:
- dependency-name: actions/setup-go
  dependency-version: '7'
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-07-16 05:52:38 +00:00
dependabot[bot] 5b72b928dc build(deps): bump golang.org/x/net from 0.56.0 to 0.57.0
Bumps [golang.org/x/net](https://github.com/golang/net) from 0.56.0 to 0.57.0.
- [Commits](https://github.com/golang/net/compare/v0.56.0...v0.57.0)

---
updated-dependencies:
- dependency-name: golang.org/x/net
  dependency-version: 0.57.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-07-09 05:52:36 +00:00
Martin Angers a81d5bb195 Merge pull request #590 from PuerkitoBio/dependabot/go_modules/golang.org/x/net-0.56.0
build(deps): bump golang.org/x/net from 0.55.0 to 0.56.0
2026-06-11 08:58:19 -04:00
dependabot[bot] 5facb40e7c build(deps): bump golang.org/x/net from 0.55.0 to 0.56.0
Bumps [golang.org/x/net](https://github.com/golang/net) from 0.55.0 to 0.56.0.
- [Commits](https://github.com/golang/net/compare/v0.55.0...v0.56.0)

---
updated-dependencies:
- dependency-name: golang.org/x/net
  dependency-version: 0.56.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-06-11 05:52:36 +00:00
Martin Angers 2bab3fcead Merge pull request #589 from jvoisin/attror
cleanup: inline getAttributeValue into Attr, delegate AttrOr
2026-06-10 09:00:51 -04:00
Martin Angers ad7e3a5a32 Merge pull request #588 from jvoisin/deadparam
refactor: remove a dead param in getClassesAndAttr
2026-06-10 08:58:14 -04:00
Martin Angers e66583975d Merge pull request #585 from jvoisin/winnow_cleanup
cleanup: thread []*html.Node through winnow, drop temp Selection
2026-06-10 08:56:49 -04:00
Martin Angers dfcd45f03f Merge pull request #584 from jvoisin/phwc
cleanup: factor parseHtml through parseHtmlWithContext
2026-06-10 08:53:27 -04:00
Martin Angers 6a3f1a4508 Merge pull request #583 from jvoisin/nocon
cleanup: drop redundant FirstChild nil-check in textHelper
2026-06-10 08:51:31 -04:00
jvoisin 3d73db28d1 cleanup: inline getAttributeValue into Attr, delegate AttrOr
Attr was a 4-line wrapper around getAttributeValue, which itself was
a 6-line wrapper around getAttributePtr.

This commit inlines getAttributeValue into Attr and
have AttrOr delegate to Attr. Drops a layer of indirection and one
helper function; both methods get shorter and the empty-selection
check lives in one place.
2026-06-05 23:48:33 +02:00
jvoisin ab25b2a2f9 refactor: remove a dead param in getClassesAndAttr
Every caller of getClassesAndAttr is passing `true` as second parameter, so
let's get rid of it.
2026-06-05 23:23:26 +02:00
jvoisin a7a9c2dced cleanup: extract cachedParse helper for parse-result reuse
WrapHtml, WrapInnerHtml, and eachNodeHtml each open-coded the same
lookup-or-parse-and-store sequence against a map[string][]*html.Node
keyed by the context node's name. Extract that 4-line sequence into
a tiny cachedParseHtmlWithContext(cache, htmlStr, context) helper; each call
site becomes a linear, closure-free loop and the only duplicated bit (the cache
lookup) lives in one place.
2026-06-05 22:51:00 +02:00
jvoisin 36f7b3b68e cleanup: thread []*html.Node through winnow, drop temp Selection
winnow only ever reads sel.Nodes; the *Selection parameter was
incidental. Change its signature to winnow(nodes []*html.Node, ...)
and update its three callers (FilterMatcher, NotMatcher,
filterAndPush). filterAndPush no longer needs to fabricate a
throwaway Selection to satisfy the call.

While this change has o measurable runtime effect, it simplifies the code a bit,
by making winnow's signature clearer, and removes a now-useless line and its
associated comment in filterAndPush
2026-06-05 22:35:48 +02:00
jvoisin e96c2a87e6 cleanup: factor parseHtml through parseHtmlWithContext
parseHtml and parseHtmlWithContext duplicated the ParseFragment call,
the error check, and the panic message. parseHtml only differed by
passing a synthetic ElementNode as the context.

This commit simply delegates parseHtml to parseHtmlWithContext.
2026-06-05 22:29:08 +02:00
jvoisin a202b87b3b cleanup: drop redundant FirstChild nil-check in textHelper
The `for c := n.FirstChild; c != nil; c = c.NextSibling` loop already
handles the nil-FirstChild case.
2026-06-05 22:26:30 +02:00
Martin Angers 88920eaad4 Merge pull request #569 from jvoisin/specialized
perf: probe with MatchFirst in HasMatcher to avoid slice allocation
2026-06-04 10:23:08 -04:00
Martin Angers 65a48d3886 Merge pull request #575 from jvoisin/nodedup
test: cover children traversals with duplicate source nodes
2026-06-04 10:17:21 -04:00
Martin Angers b8d1127ab1 Merge pull request #574 from jvoisin/preact
perf: presize the result slice in Empty()
2026-06-04 09:57:10 -04:00
Martin Angers 939767f12c Merge pull request #582 from PuerkitoBio/dependabot/go_modules/github.com/andybalholm/cascadia-1.3.4
build(deps): bump github.com/andybalholm/cascadia from 1.3.3 to 1.3.4
2026-06-04 09:41:47 -04:00