run 'go get -u; make revendor'
Signed-off-by: Stephan Renatus <srenatus@chef.io>
This commit is contained in:
4
vendor/github.com/beevik/etree/.travis.yml
generated
vendored
4
vendor/github.com/beevik/etree/.travis.yml
generated
vendored
@@ -2,9 +2,7 @@ language: go
|
||||
sudo: false
|
||||
|
||||
go:
|
||||
- 1.4.2
|
||||
- 1.5.1
|
||||
- 1.6
|
||||
- 1.11.x
|
||||
- tip
|
||||
|
||||
matrix:
|
||||
|
3
vendor/github.com/beevik/etree/CONTRIBUTORS
generated
vendored
3
vendor/github.com/beevik/etree/CONTRIBUTORS
generated
vendored
@@ -5,3 +5,6 @@ Graham King (grahamking)
|
||||
Matt Smith (ma314smith)
|
||||
Michal Jemala (michaljemala)
|
||||
Nicolas Piganeau (npiganeau)
|
||||
Chris Brown (ccbrown)
|
||||
Earncef Sequeira (earncef)
|
||||
Gabriel de Labachelerie (wuzuf)
|
||||
|
2
vendor/github.com/beevik/etree/LICENSE
generated
vendored
2
vendor/github.com/beevik/etree/LICENSE
generated
vendored
@@ -1,4 +1,4 @@
|
||||
Copyright 2015 Brett Vickers. All rights reserved.
|
||||
Copyright 2015-2019 Brett Vickers. All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions
|
||||
|
8
vendor/github.com/beevik/etree/README.md
generated
vendored
8
vendor/github.com/beevik/etree/README.md
generated
vendored
@@ -7,7 +7,9 @@ etree
|
||||
The etree package is a lightweight, pure go package that expresses XML in
|
||||
the form of an element tree. Its design was inspired by the Python
|
||||
[ElementTree](http://docs.python.org/2/library/xml.etree.elementtree.html)
|
||||
module. Some of the package's features include:
|
||||
module.
|
||||
|
||||
Some of the package's capabilities and features:
|
||||
|
||||
* Represents XML documents as trees of elements for easy traversal.
|
||||
* Imports, serializes, modifies or creates XML documents from scratch.
|
||||
@@ -191,13 +193,13 @@ Note that this example uses the FindElementsPath function, which takes as an
|
||||
argument a pre-compiled path object. Use precompiled paths when you plan to
|
||||
search with the same path more than once.
|
||||
|
||||
###Other features
|
||||
### Other features
|
||||
|
||||
These are just a few examples of the things the etree package can do. See the
|
||||
[documentation](http://godoc.org/github.com/beevik/etree) for a complete
|
||||
description of its capabilities.
|
||||
|
||||
###Contributing
|
||||
### Contributing
|
||||
|
||||
This project accepts contributions. Just fork the repo and submit a pull
|
||||
request!
|
||||
|
109
vendor/github.com/beevik/etree/RELEASE_NOTES.md
generated
vendored
Normal file
109
vendor/github.com/beevik/etree/RELEASE_NOTES.md
generated
vendored
Normal file
@@ -0,0 +1,109 @@
|
||||
Release v1.1.0
|
||||
==============
|
||||
|
||||
**New Features**
|
||||
|
||||
* New attribute helpers.
|
||||
* Added the `Element.SortAttrs` method, which lexicographically sorts an
|
||||
element's attributes by key.
|
||||
* New `ReadSettings` properties.
|
||||
* Added `Entity` for the support of custom entity maps.
|
||||
* New `WriteSettings` properties.
|
||||
* Added `UseCRLF` to allow the output of CR-LF newlines instead of the
|
||||
default LF newlines. This is useful on Windows systems.
|
||||
* Additional support for text and CDATA sections.
|
||||
* The `Element.Text` method now returns the concatenation of all consecutive
|
||||
character data tokens immediately following an element's opening tag.
|
||||
* Added `Element.SetCData` to replace the character data immediately
|
||||
following an element's opening tag with a CDATA section.
|
||||
* Added `Element.CreateCData` to create and add a CDATA section child
|
||||
`CharData` token to an element.
|
||||
* Added `Element.CreateText` to create and add a child text `CharData` token
|
||||
to an element.
|
||||
* Added `NewCData` to create a parentless CDATA section `CharData` token.
|
||||
* Added `NewText` to create a parentless text `CharData`
|
||||
token.
|
||||
* Added `CharData.IsCData` to detect if the token contains a CDATA section.
|
||||
* Added `CharData.IsWhitespace` to detect if the token contains whitespace
|
||||
inserted by one of the document Indent functions.
|
||||
* Modified `Element.SetText` so that it replaces a run of consecutive
|
||||
character data tokens following the element's opening tag (instead of just
|
||||
the first one).
|
||||
* New "tail text" support.
|
||||
* Added the `Element.Tail` method, which returns the text immediately
|
||||
following an element's closing tag.
|
||||
* Added the `Element.SetTail` method, which modifies the text immediately
|
||||
following an element's closing tag.
|
||||
* New element child insertion and removal methods.
|
||||
* Added the `Element.InsertChildAt` method, which inserts a new child token
|
||||
before the specified child token index.
|
||||
* Added the `Element.RemoveChildAt` method, which removes the child token at
|
||||
the specified child token index.
|
||||
* New element and attribute queries.
|
||||
* Added the `Element.Index` method, which returns the element's index within
|
||||
its parent element's child token list.
|
||||
* Added the `Element.NamespaceURI` method to return the namespace URI
|
||||
associated with an element.
|
||||
* Added the `Attr.NamespaceURI` method to return the namespace URI
|
||||
associated with an element.
|
||||
* Added the `Attr.Element` method to return the element that an attribute
|
||||
belongs to.
|
||||
* New Path filter functions.
|
||||
* Added `[local-name()='val']` to keep elements whose unprefixed tag matches
|
||||
the desired value.
|
||||
* Added `[name()='val']` to keep elements whose full tag matches the desired
|
||||
value.
|
||||
* Added `[namespace-prefix()='val']` to keep elements whose namespace prefix
|
||||
matches the desired value.
|
||||
* Added `[namespace-uri()='val']` to keep elements whose namespace URI
|
||||
matches the desired value.
|
||||
|
||||
**Bug Fixes**
|
||||
|
||||
* A default XML `CharSetReader` is now used to prevent failed parsing of XML
|
||||
documents using certain encodings.
|
||||
([Issue](https://github.com/beevik/etree/issues/53)).
|
||||
* All characters are now properly escaped according to XML parsing rules.
|
||||
([Issue](https://github.com/beevik/etree/issues/55)).
|
||||
* The `Document.Indent` and `Document.IndentTabs` functions no longer insert
|
||||
empty string `CharData` tokens.
|
||||
|
||||
**Deprecated**
|
||||
|
||||
* `Element`
|
||||
* The `InsertChild` method is deprecated. Use `InsertChildAt` instead.
|
||||
* The `CreateCharData` method is deprecated. Use `CreateText` instead.
|
||||
* `CharData`
|
||||
* The `NewCharData` method is deprecated. Use `NewText` instead.
|
||||
|
||||
|
||||
Release v1.0.1
|
||||
==============
|
||||
|
||||
**Changes**
|
||||
|
||||
* Added support for absolute etree Path queries. An absolute path begins with
|
||||
`/` or `//` and begins its search from the element's document root.
|
||||
* Added [`GetPath`](https://godoc.org/github.com/beevik/etree#Element.GetPath)
|
||||
and [`GetRelativePath`](https://godoc.org/github.com/beevik/etree#Element.GetRelativePath)
|
||||
functions to the [`Element`](https://godoc.org/github.com/beevik/etree#Element)
|
||||
type.
|
||||
|
||||
**Breaking changes**
|
||||
|
||||
* A path starting with `//` is now interpreted as an absolute path.
|
||||
Previously, it was interpreted as a relative path starting from the element
|
||||
whose
|
||||
[`FindElement`](https://godoc.org/github.com/beevik/etree#Element.FindElement)
|
||||
method was called. To remain compatible with this release, all paths
|
||||
prefixed with `//` should be prefixed with `.//` when called from any
|
||||
element other than the document's root.
|
||||
* [**edit 2/1/2019**]: Minor releases should not contain breaking changes.
|
||||
Even though this breaking change was very minor, it was a mistake to include
|
||||
it in this minor release. In the future, all breaking changes will be
|
||||
limited to major releases (e.g., version 2.0.0).
|
||||
|
||||
Release v1.0.0
|
||||
==============
|
||||
|
||||
Initial release.
|
815
vendor/github.com/beevik/etree/etree.go
generated
vendored
815
vendor/github.com/beevik/etree/etree.go
generated
vendored
File diff suppressed because it is too large
Load Diff
110
vendor/github.com/beevik/etree/helpers.go
generated
vendored
110
vendor/github.com/beevik/etree/helpers.go
generated
vendored
@@ -1,12 +1,14 @@
|
||||
// Copyright 2015 Brett Vickers.
|
||||
// Copyright 2015-2019 Brett Vickers.
|
||||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
package etree
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"io"
|
||||
"strings"
|
||||
"unicode/utf8"
|
||||
)
|
||||
|
||||
// A simple stack
|
||||
@@ -147,22 +149,35 @@ func spaceDecompose(str string) (space, key string) {
|
||||
return str[:colon], str[colon+1:]
|
||||
}
|
||||
|
||||
// Strings used by crIndent
|
||||
// Strings used by indentCRLF and indentLF
|
||||
const (
|
||||
crsp = "\n "
|
||||
crtab = "\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t"
|
||||
indentSpaces = "\r\n "
|
||||
indentTabs = "\r\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t"
|
||||
)
|
||||
|
||||
// crIndent returns a carriage return followed by n copies of the
|
||||
// first non-CR character in the source string.
|
||||
func crIndent(n int, source string) string {
|
||||
// indentCRLF returns a CRLF newline followed by n copies of the first
|
||||
// non-CRLF character in the source string.
|
||||
func indentCRLF(n int, source string) string {
|
||||
switch {
|
||||
case n < 0:
|
||||
return source[:1]
|
||||
case n < len(source):
|
||||
return source[:n+1]
|
||||
return source[:2]
|
||||
case n < len(source)-1:
|
||||
return source[:n+2]
|
||||
default:
|
||||
return source + strings.Repeat(source[1:2], n-len(source)+1)
|
||||
return source + strings.Repeat(source[2:3], n-len(source)+2)
|
||||
}
|
||||
}
|
||||
|
||||
// indentLF returns a LF newline followed by n copies of the first non-LF
|
||||
// character in the source string.
|
||||
func indentLF(n int, source string) string {
|
||||
switch {
|
||||
case n < 0:
|
||||
return source[1:2]
|
||||
case n < len(source)-1:
|
||||
return source[1 : n+2]
|
||||
default:
|
||||
return source[1:] + strings.Repeat(source[2:3], n-len(source)+2)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -186,3 +201,76 @@ func isInteger(s string) bool {
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
type escapeMode byte
|
||||
|
||||
const (
|
||||
escapeNormal escapeMode = iota
|
||||
escapeCanonicalText
|
||||
escapeCanonicalAttr
|
||||
)
|
||||
|
||||
// escapeString writes an escaped version of a string to the writer.
|
||||
func escapeString(w *bufio.Writer, s string, m escapeMode) {
|
||||
var esc []byte
|
||||
last := 0
|
||||
for i := 0; i < len(s); {
|
||||
r, width := utf8.DecodeRuneInString(s[i:])
|
||||
i += width
|
||||
switch r {
|
||||
case '&':
|
||||
esc = []byte("&")
|
||||
case '<':
|
||||
esc = []byte("<")
|
||||
case '>':
|
||||
if m == escapeCanonicalAttr {
|
||||
continue
|
||||
}
|
||||
esc = []byte(">")
|
||||
case '\'':
|
||||
if m != escapeNormal {
|
||||
continue
|
||||
}
|
||||
esc = []byte("'")
|
||||
case '"':
|
||||
if m == escapeCanonicalText {
|
||||
continue
|
||||
}
|
||||
esc = []byte(""")
|
||||
case '\t':
|
||||
if m != escapeCanonicalAttr {
|
||||
continue
|
||||
}
|
||||
esc = []byte("	")
|
||||
case '\n':
|
||||
if m != escapeCanonicalAttr {
|
||||
continue
|
||||
}
|
||||
esc = []byte("
")
|
||||
case '\r':
|
||||
if m == escapeNormal {
|
||||
continue
|
||||
}
|
||||
esc = []byte("
")
|
||||
default:
|
||||
if !isInCharacterRange(r) || (r == 0xFFFD && width == 1) {
|
||||
esc = []byte("\uFFFD")
|
||||
break
|
||||
}
|
||||
continue
|
||||
}
|
||||
w.WriteString(s[last : i-width])
|
||||
w.Write(esc)
|
||||
last = i
|
||||
}
|
||||
w.WriteString(s[last:])
|
||||
}
|
||||
|
||||
func isInCharacterRange(r rune) bool {
|
||||
return r == 0x09 ||
|
||||
r == 0x0A ||
|
||||
r == 0x0D ||
|
||||
r >= 0x20 && r <= 0xD7FF ||
|
||||
r >= 0xE000 && r <= 0xFFFD ||
|
||||
r >= 0x10000 && r <= 0x10FFFF
|
||||
}
|
||||
|
194
vendor/github.com/beevik/etree/path.go
generated
vendored
194
vendor/github.com/beevik/etree/path.go
generated
vendored
@@ -1,4 +1,4 @@
|
||||
// Copyright 2015 Brett Vickers.
|
||||
// Copyright 2015-2019 Brett Vickers.
|
||||
// Use of this source code is governed by a BSD-style
|
||||
// license that can be found in the LICENSE file.
|
||||
|
||||
@@ -10,40 +10,75 @@ import (
|
||||
)
|
||||
|
||||
/*
|
||||
A Path is an object that represents an optimized version of an
|
||||
XPath-like search string. Although path strings are XPath-like,
|
||||
only the following limited syntax is supported:
|
||||
A Path is a string that represents a search path through an etree starting
|
||||
from the document root or an arbitrary element. Paths are used with the
|
||||
Element object's Find* methods to locate and return desired elements.
|
||||
|
||||
. Selects the current element
|
||||
.. Selects the parent of the current element
|
||||
* Selects all child elements
|
||||
// Selects all descendants of the current element
|
||||
tag Selects all child elements with the given tag
|
||||
[#] Selects the element of the given index (1-based,
|
||||
negative starts from the end)
|
||||
[@attrib] Selects all elements with the given attribute
|
||||
[@attrib='val'] Selects all elements with the given attribute set to val
|
||||
[tag] Selects all elements with a child element named tag
|
||||
[tag='val'] Selects all elements with a child element named tag
|
||||
and text equal to val
|
||||
A Path consists of a series of slash-separated "selectors", each of which may
|
||||
be modified by one or more bracket-enclosed "filters". Selectors are used to
|
||||
traverse the etree from element to element, while filters are used to narrow
|
||||
the list of candidate elements at each node.
|
||||
|
||||
Examples:
|
||||
Although etree Path strings are similar to XPath strings
|
||||
(https://www.w3.org/TR/1999/REC-xpath-19991116/), they have a more limited set
|
||||
of selectors and filtering options.
|
||||
|
||||
Select the title elements of all descendant book elements having a
|
||||
'category' attribute of 'WEB':
|
||||
The following selectors are supported by etree Path strings:
|
||||
|
||||
. Select the current element.
|
||||
.. Select the parent of the current element.
|
||||
* Select all child elements of the current element.
|
||||
/ Select the root element when used at the start of a path.
|
||||
// Select all descendants of the current element.
|
||||
tag Select all child elements with a name matching the tag.
|
||||
|
||||
The following basic filters are supported by etree Path strings:
|
||||
|
||||
[@attrib] Keep elements with an attribute named attrib.
|
||||
[@attrib='val'] Keep elements with an attribute named attrib and value matching val.
|
||||
[tag] Keep elements with a child element named tag.
|
||||
[tag='val'] Keep elements with a child element named tag and text matching val.
|
||||
[n] Keep the n-th element, where n is a numeric index starting from 1.
|
||||
|
||||
The following function filters are also supported:
|
||||
|
||||
[text()] Keep elements with non-empty text.
|
||||
[text()='val'] Keep elements whose text matches val.
|
||||
[local-name()='val'] Keep elements whose un-prefixed tag matches val.
|
||||
[name()='val'] Keep elements whose full tag exactly matches val.
|
||||
[namespace-prefix()='val'] Keep elements whose namespace prefix matches val.
|
||||
[namespace-uri()='val'] Keep elements whose namespace URI matches val.
|
||||
|
||||
Here are some examples of Path strings:
|
||||
|
||||
- Select the bookstore child element of the root element:
|
||||
/bookstore
|
||||
|
||||
- Beginning from the root element, select the title elements of all
|
||||
descendant book elements having a 'category' attribute of 'WEB':
|
||||
//book[@category='WEB']/title
|
||||
|
||||
Select the first book element with a title child containing the text
|
||||
'Great Expectations':
|
||||
- Beginning from the current element, select the first descendant
|
||||
book element with a title child element containing the text 'Great
|
||||
Expectations':
|
||||
.//book[title='Great Expectations'][1]
|
||||
|
||||
Starting from the current element, select all children of book elements
|
||||
with an attribute 'language' set to 'english':
|
||||
- Beginning from the current element, select all child elements of
|
||||
book elements with an attribute 'language' set to 'english':
|
||||
./book/*[@language='english']
|
||||
|
||||
Select all descendant book elements whose title element has an attribute
|
||||
'language' set to 'french':
|
||||
//book/title[@language='french']/..
|
||||
- Beginning from the current element, select all child elements of
|
||||
book elements containing the text 'special':
|
||||
./book/*[text()='special']
|
||||
|
||||
- Beginning from the current element, select all descendant book
|
||||
elements whose title child element has a 'language' attribute of 'french':
|
||||
.//book/title[@language='french']/..
|
||||
|
||||
- Beginning from the current element, select all book elements
|
||||
belonging to the http://www.w3.org/TR/html4/ namespace:
|
||||
.//book[namespace-uri()='http://www.w3.org/TR/html4/']
|
||||
|
||||
*/
|
||||
type Path struct {
|
||||
segments []segment
|
||||
@@ -173,22 +208,20 @@ type compiler struct {
|
||||
// through an element tree and returns a slice of segment
|
||||
// descriptors.
|
||||
func (c *compiler) parsePath(path string) []segment {
|
||||
// If path starts or ends with //, fix it
|
||||
if strings.HasPrefix(path, "//") {
|
||||
path = "." + path
|
||||
}
|
||||
// If path ends with //, fix it
|
||||
if strings.HasSuffix(path, "//") {
|
||||
path = path + "*"
|
||||
}
|
||||
|
||||
// Paths cannot be absolute
|
||||
var segments []segment
|
||||
|
||||
// Check for an absolute path
|
||||
if strings.HasPrefix(path, "/") {
|
||||
c.err = ErrPath("paths cannot be absolute.")
|
||||
return nil
|
||||
segments = append(segments, segment{new(selectRoot), []filter{}})
|
||||
path = path[1:]
|
||||
}
|
||||
|
||||
// Split path into segment objects
|
||||
var segments []segment
|
||||
// Split path into segments
|
||||
for _, s := range splitPath(path) {
|
||||
segments = append(segments, c.parseSegment(s))
|
||||
if c.err != ErrPath("") {
|
||||
@@ -218,7 +251,7 @@ func (c *compiler) parseSegment(path string) segment {
|
||||
pieces := strings.Split(path, "[")
|
||||
seg := segment{
|
||||
sel: c.parseSelector(pieces[0]),
|
||||
filters: make([]filter, 0),
|
||||
filters: []filter{},
|
||||
}
|
||||
for i := 1; i < len(pieces); i++ {
|
||||
fpath := pieces[i]
|
||||
@@ -247,6 +280,17 @@ func (c *compiler) parseSelector(path string) selector {
|
||||
}
|
||||
}
|
||||
|
||||
var fnTable = map[string]struct {
|
||||
hasFn func(e *Element) bool
|
||||
getValFn func(e *Element) string
|
||||
}{
|
||||
"local-name": {nil, (*Element).name},
|
||||
"name": {nil, (*Element).FullTag},
|
||||
"namespace-prefix": {nil, (*Element).namespacePrefix},
|
||||
"namespace-uri": {nil, (*Element).NamespaceURI},
|
||||
"text": {(*Element).hasText, (*Element).Text},
|
||||
}
|
||||
|
||||
// parseFilter parses a path filter contained within [brackets].
|
||||
func (c *compiler) parseFilter(path string) filter {
|
||||
if len(path) == 0 {
|
||||
@@ -254,7 +298,7 @@ func (c *compiler) parseFilter(path string) filter {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Filter contains [@attr='val'] or [tag='val']?
|
||||
// Filter contains [@attr='val'], [fn()='val'], or [tag='val']?
|
||||
eqindex := strings.Index(path, "='")
|
||||
if eqindex >= 0 {
|
||||
rindex := nextIndex(path, "'", eqindex+2)
|
||||
@@ -262,18 +306,36 @@ func (c *compiler) parseFilter(path string) filter {
|
||||
c.err = ErrPath("path has mismatched filter quotes.")
|
||||
return nil
|
||||
}
|
||||
|
||||
key := path[:eqindex]
|
||||
value := path[eqindex+2 : rindex]
|
||||
|
||||
switch {
|
||||
case path[0] == '@':
|
||||
return newFilterAttrVal(path[1:eqindex], path[eqindex+2:rindex])
|
||||
case key[0] == '@':
|
||||
return newFilterAttrVal(key[1:], value)
|
||||
case strings.HasSuffix(key, "()"):
|
||||
fn := key[:len(key)-2]
|
||||
if t, ok := fnTable[fn]; ok && t.getValFn != nil {
|
||||
return newFilterFuncVal(t.getValFn, value)
|
||||
}
|
||||
c.err = ErrPath("path has unknown function " + fn)
|
||||
return nil
|
||||
default:
|
||||
return newFilterChildText(path[:eqindex], path[eqindex+2:rindex])
|
||||
return newFilterChildText(key, value)
|
||||
}
|
||||
}
|
||||
|
||||
// Filter contains [@attr], [N] or [tag]
|
||||
// Filter contains [@attr], [N], [tag] or [fn()]
|
||||
switch {
|
||||
case path[0] == '@':
|
||||
return newFilterAttr(path[1:])
|
||||
case strings.HasSuffix(path, "()"):
|
||||
fn := path[:len(path)-2]
|
||||
if t, ok := fnTable[fn]; ok && t.hasFn != nil {
|
||||
return newFilterFunc(t.hasFn)
|
||||
}
|
||||
c.err = ErrPath("path has unknown function " + fn)
|
||||
return nil
|
||||
case isInteger(path):
|
||||
pos, _ := strconv.Atoi(path)
|
||||
switch {
|
||||
@@ -294,6 +356,17 @@ func (s *selectSelf) apply(e *Element, p *pather) {
|
||||
p.candidates = append(p.candidates, e)
|
||||
}
|
||||
|
||||
// selectRoot selects the element's root node.
|
||||
type selectRoot struct{}
|
||||
|
||||
func (s *selectRoot) apply(e *Element, p *pather) {
|
||||
root := e
|
||||
for root.parent != nil {
|
||||
root = root.parent
|
||||
}
|
||||
p.candidates = append(p.candidates, root)
|
||||
}
|
||||
|
||||
// selectParent selects the element's parent into the candidate list.
|
||||
type selectParent struct{}
|
||||
|
||||
@@ -420,6 +493,45 @@ func (f *filterAttrVal) apply(p *pather) {
|
||||
p.candidates, p.scratch = p.scratch, p.candidates[0:0]
|
||||
}
|
||||
|
||||
// filterFunc filters the candidate list for elements satisfying a custom
|
||||
// boolean function.
|
||||
type filterFunc struct {
|
||||
fn func(e *Element) bool
|
||||
}
|
||||
|
||||
func newFilterFunc(fn func(e *Element) bool) *filterFunc {
|
||||
return &filterFunc{fn}
|
||||
}
|
||||
|
||||
func (f *filterFunc) apply(p *pather) {
|
||||
for _, c := range p.candidates {
|
||||
if f.fn(c) {
|
||||
p.scratch = append(p.scratch, c)
|
||||
}
|
||||
}
|
||||
p.candidates, p.scratch = p.scratch, p.candidates[0:0]
|
||||
}
|
||||
|
||||
// filterFuncVal filters the candidate list for elements containing a value
|
||||
// matching the result of a custom function.
|
||||
type filterFuncVal struct {
|
||||
fn func(e *Element) string
|
||||
val string
|
||||
}
|
||||
|
||||
func newFilterFuncVal(fn func(e *Element) string, value string) *filterFuncVal {
|
||||
return &filterFuncVal{fn, value}
|
||||
}
|
||||
|
||||
func (f *filterFuncVal) apply(p *pather) {
|
||||
for _, c := range p.candidates {
|
||||
if f.fn(c) == f.val {
|
||||
p.scratch = append(p.scratch, c)
|
||||
}
|
||||
}
|
||||
p.candidates, p.scratch = p.scratch, p.candidates[0:0]
|
||||
}
|
||||
|
||||
// filterChild filters the candidate list for elements having
|
||||
// a child element with the specified tag.
|
||||
type filterChild struct {
|
||||
|
Reference in New Issue
Block a user