nokolexbor 0.7.0-aarch64-linux

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,293 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Nokolexbor
4
+ class NodeSet < Nokolexbor::Node
5
+ include Enumerable
6
+
7
+ # Create a NodeSet with +document+ defaulting to +list+.
8
+ #
9
+ # @yield [Document]
10
+ #
11
+ # @return [Document]
12
+ def self.new(document, list = [])
13
+ obj = allocate
14
+ if document.is_a?(Document) || document.nil?
15
+ obj.instance_variable_set(:@document, document)
16
+ elsif document.is_a?(Node)
17
+ obj.instance_variable_set(:@document, document.document)
18
+ else
19
+ raise ArgumentError, "Expected a Document or Node, got #{document.class}"
20
+ end
21
+ list.each { |x| obj << x }
22
+ yield obj if block_given?
23
+ obj
24
+ end
25
+
26
+ # Iterate over each node.
27
+ #
28
+ # @yield [Node]
29
+ def each
30
+ return to_enum unless block_given?
31
+
32
+ 0.upto(length - 1) do |x|
33
+ yield self[x]
34
+ end
35
+ self
36
+ end
37
+
38
+ # Get the first +n+ elements of the NodeSet.
39
+ #
40
+ # @param n [Numeric,nil]
41
+ #
42
+ # @return [Node,Array<Node>] {Node} if +n+ is nil, otherwise {Array<Node>}
43
+ def first(n = nil)
44
+ return self[0] unless n
45
+
46
+ list = []
47
+ [n, length].min.times { |i| list << self[i] }
48
+ list
49
+ end
50
+
51
+ # Get the last element of the NodeSet.
52
+ #
53
+ # @return [Node,nil]
54
+ def last
55
+ self[-1]
56
+ end
57
+
58
+ # @return [Boolean] true if this NodeSet is empty.
59
+ def empty?
60
+ length == 0
61
+ end
62
+
63
+ # Insert +node+ before the first Node in this NodeSet
64
+ def before(node)
65
+ first.before(node)
66
+ end
67
+
68
+ # Insert +node+ after the last Node in this NodeSet
69
+ def after(node)
70
+ last.after(node)
71
+ end
72
+
73
+ # @return [Integer] The index of the first node in this NodeSet that is equal to +node+ or meets the given block. Returns nil if no match is found.
74
+ def index(node = nil)
75
+ if node
76
+ each_with_index { |member, j| return j if member == node }
77
+ elsif block_given?
78
+ each_with_index { |member, j| return j if yield(member) }
79
+ end
80
+ nil
81
+ end
82
+
83
+ # Get the content of all contained Nodes.
84
+ #
85
+ # @return [String]
86
+ def content
87
+ self.map(&:content).join
88
+ end
89
+
90
+ alias_method :text, :content
91
+ alias_method :inner_text, :content
92
+ alias_method :to_str, :content
93
+
94
+ # Get the inner html of all contained Nodes.
95
+ #
96
+ # @return [String]
97
+ def inner_html(*args)
98
+ self.map { |n| n.inner_html(*args) }.join
99
+ end
100
+
101
+ # Convert this NodeSet to HTML.
102
+ #
103
+ # @return [String]
104
+ def outer_html(*args)
105
+ self.map { |n| n.outer_html(*args) }.join
106
+ end
107
+
108
+ alias_method :to_s, :outer_html
109
+ alias_method :to_html, :outer_html
110
+ alias_method :serialize, :outer_html
111
+
112
+ # Remove all nodes in this NodeSet.
113
+ #
114
+ # @see Node#remove
115
+ def remove
116
+ self.each(&:remove)
117
+ end
118
+
119
+ alias_method :unlink, :remove
120
+ alias_method :to_ary, :to_a
121
+
122
+ # Destroy all nodes in the NodeSet.
123
+ #
124
+ # @see Node#destroy
125
+ def destroy
126
+ self.each(&:destroy)
127
+ end
128
+
129
+ # @return [Node,nil] The last element of this NodeSet and removes it. Returns
130
+ # +nil+ if the set is empty.
131
+ def pop
132
+ return nil if length == 0
133
+
134
+ delete(last)
135
+ end
136
+
137
+ # @return [Node,nil] The first element of this NodeSet and removes it. Returns
138
+ # +nil+ if the set is empty.
139
+ def shift
140
+ return nil if length == 0
141
+
142
+ delete(first)
143
+ end
144
+
145
+ # @return [Boolean] true if two NodeSets contain the same number
146
+ # of elements and each element is equal to the corresponding
147
+ # element in the other NodeSet.
148
+ def ==(other)
149
+ return false unless other.is_a?(NodeSet)
150
+ return false unless length == other.length
151
+
152
+ each_with_index do |node, i|
153
+ return false unless node == other[i]
154
+ end
155
+ true
156
+ end
157
+
158
+ # @return [NodeSet] A new NodeSet containing all the children of all the nodes in
159
+ # the NodeSet.
160
+ def children
161
+ node_set = NodeSet.new(@document)
162
+ each do |node|
163
+ node.children.each { |n| node_set.push(n) }
164
+ end
165
+ node_set
166
+ end
167
+
168
+ # @return [NodeSet] A new NodeSet containing all the nodes in the NodeSet
169
+ # in reverse order.
170
+ def reverse
171
+ node_set = NodeSet.new(@document)
172
+ (length - 1).downto(0) do |x|
173
+ node_set.push(self[x])
174
+ end
175
+ node_set
176
+ end
177
+
178
+ # Wrap all nodes of this NodeSet with +node_or_tags+.
179
+ #
180
+ # @see Node#wrap
181
+ #
182
+ # @return [NodeSet] +self+, to support chaining.
183
+ def wrap(node_or_tags)
184
+ map { |node| node.wrap(node_or_tags) }
185
+ self
186
+ end
187
+
188
+ # Add the class attribute +name+ to all containing nodes.
189
+ #
190
+ # @see Node#add_class
191
+ def add_class(name)
192
+ each do |el|
193
+ el.add_class(name)
194
+ end
195
+ self
196
+ end
197
+
198
+ # Append the class attribute +name+ to all containing nodes.
199
+ #
200
+ # @see Node#append_class
201
+ def append_class(name)
202
+ each do |el|
203
+ el.append_class(name)
204
+ end
205
+ self
206
+ end
207
+
208
+ # Remove the class attribute +name+ from all containing nodes.
209
+ #
210
+ # @see Node#remove_class
211
+ def remove_class(name = nil)
212
+ each do |el|
213
+ el.remove_class(name)
214
+ end
215
+ self
216
+ end
217
+
218
+ # Remove the attributed named +name+ from all containing nodes.
219
+ #
220
+ # @see Node#remove_attr
221
+ def remove_attr(name)
222
+ each { |el| el.delete(name) }
223
+ self
224
+ end
225
+ alias_method :remove_attribute, :remove_attr
226
+
227
+ # Set attributes on each Node in the NodeSet, or get an
228
+ # attribute from the first Node in the NodeSet.
229
+ #
230
+ # @example Get an attribute from the first Node in a NodeSet.
231
+ # node_set.attr("href")
232
+ #
233
+ # @example Set attributes on each node.
234
+ # node_set.attr("href" => "http://example.com", "class" => "a")
235
+ # node_set.attr("href", "http://example.com")
236
+ # node_set.attr("href") { |node| "http://example.com" }
237
+ #
238
+ # @return [NodeSet] +self+, to support chaining of calls.
239
+ def attr(key, value = nil, &block)
240
+ unless key.is_a?(Hash) || (key && (value || block))
241
+ return first&.attribute(key)
242
+ end
243
+
244
+ hash = key.is_a?(Hash) ? key : { key => value }
245
+
246
+ hash.each do |k, v|
247
+ each do |node|
248
+ node[k] = v || yield(node)
249
+ end
250
+ end
251
+
252
+ self
253
+ end
254
+ alias_method :set, :attr
255
+ alias_method :attribute, :attr
256
+
257
+ # (see Node#xpath)
258
+ def xpath(*args)
259
+ paths, handler, ns, binds = extract_params(args)
260
+
261
+ NodeSet.new(@document) do |set|
262
+ each do |node|
263
+ node.send(:xpath_internal, node, paths, handler, ns, binds).each do |inner_node|
264
+ set << inner_node
265
+ end
266
+ end
267
+ end
268
+ end
269
+
270
+ # (see Node#nokogiri_css)
271
+ def nokogiri_css(*args)
272
+ rules, handler, ns, _ = extract_params(args)
273
+ paths = css_rules_to_xpath(rules, ns)
274
+
275
+ NodeSet.new(@document) do |set|
276
+ each do |node|
277
+ node.send(:xpath_internal, node, paths, handler, ns, nil).each do |inner_node|
278
+ set << inner_node
279
+ end
280
+ end
281
+ end
282
+ end
283
+
284
+ def inspect
285
+ "[#{map(&:inspect).join(', ')}]"
286
+ end
287
+
288
+ private
289
+
290
+ IMPLIED_XPATH_CONTEXTS = [".//", "self::"].freeze # :nodoc:
291
+
292
+ end
293
+ end
@@ -0,0 +1,5 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Nokolexbor
4
+ VERSION = '0.7.0'
5
+ end
@@ -0,0 +1,69 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Nokolexbor
4
+ module XPath
5
+ class SyntaxError < StandardError
6
+ attr_reader :domain
7
+ attr_reader :code
8
+ attr_reader :level
9
+ attr_reader :file
10
+ attr_reader :line
11
+ attr_reader :str1
12
+ attr_reader :str2
13
+ attr_reader :str3
14
+ attr_reader :int1
15
+ attr_reader :column
16
+
17
+ ###
18
+ # return true if this is a non error
19
+ def none?
20
+ level == 0
21
+ end
22
+
23
+ ###
24
+ # return true if this is a warning
25
+ def warning?
26
+ level == 1
27
+ end
28
+
29
+ ###
30
+ # return true if this is an error
31
+ def error?
32
+ level == 2
33
+ end
34
+
35
+ ###
36
+ # return true if this error is fatal
37
+ def fatal?
38
+ level == 3
39
+ end
40
+
41
+ def to_s
42
+ message = super.chomp
43
+ [location_to_s, level_to_s, message]
44
+ .compact.join(": ")
45
+ .force_encoding(message.encoding)
46
+ end
47
+
48
+ private
49
+
50
+ def level_to_s
51
+ case level
52
+ when 3 then "FATAL"
53
+ when 2 then "ERROR"
54
+ when 1 then "WARNING"
55
+ end
56
+ end
57
+
58
+ def nil_or_zero?(attribute)
59
+ attribute.nil? || attribute.zero?
60
+ end
61
+
62
+ def location_to_s
63
+ return nil if nil_or_zero?(line) && nil_or_zero?(column)
64
+
65
+ "#{line}:#{column}"
66
+ end
67
+ end
68
+ end
69
+ end
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Nokolexbor
4
+ class XPathContext
5
+ ###
6
+ # Register namespaces in +namespaces+
7
+ def register_namespaces(namespaces)
8
+ namespaces.each do |k, v|
9
+ k = k.to_s.gsub(/.*:/, "") # strip off 'xmlns:' or 'xml:'
10
+ register_ns(k, v)
11
+ end
12
+ end
13
+ end
14
+ end
data/lib/nokolexbor.rb ADDED
@@ -0,0 +1,50 @@
1
+ # frozen_string_literal: true
2
+
3
+ begin
4
+ # pre-compiled extension by rake-compiler is located inside lib/nokolexbor/<ruby_version>/
5
+ RUBY_VERSION =~ /(\d+\.\d+)/
6
+ require "nokolexbor/#{Regexp.last_match(1)}/nokolexbor"
7
+ rescue LoadError => e
8
+ if /GLIBC/.match?(e.message)
9
+ warn(<<~EOM)
10
+ ERROR: It looks like you're trying to use Nokolexbor as a precompiled native gem on a system
11
+ with an unsupported version of glibc.
12
+ #{e.message}
13
+ If that's the case, then please install Nokolexbor via the `ruby` platform gem:
14
+ gem install nokolexbor --platform=ruby
15
+ or:
16
+ bundle config set force_ruby_platform true
17
+ EOM
18
+ raise e
19
+ end
20
+
21
+ require 'nokolexbor/nokolexbor'
22
+ end
23
+
24
+ require 'nokolexbor/version'
25
+ require 'nokolexbor/node'
26
+ require 'nokolexbor/document'
27
+ require 'nokolexbor/node_set'
28
+ require 'nokolexbor/document_fragment'
29
+ require 'nokolexbor/xpath'
30
+ require 'nokolexbor/xpath_context'
31
+ require 'nokolexbor/builder'
32
+
33
+ module Nokolexbor
34
+ class << self
35
+ def parse(*args)
36
+ Document.parse(*args)
37
+ end
38
+
39
+ alias_method :HTML, :parse
40
+ end
41
+ end
42
+
43
+ # Parse an HTML document, or build one with the DSL when a block is given.
44
+ def Nokolexbor(string_or_io = nil, &block)
45
+ if block
46
+ Nokolexbor::Builder.new(&block).parent
47
+ else
48
+ Nokolexbor.parse(string_or_io)
49
+ end
50
+ end
metadata ADDED
@@ -0,0 +1,85 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: nokolexbor
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.7.0
5
+ platform: aarch64-linux
6
+ authors:
7
+ - Yicheng Zhou
8
+ bindir: bin
9
+ cert_chain: []
10
+ date: 2026-03-25 00:00:00.000000000 Z
11
+ dependencies:
12
+ - !ruby/object:Gem::Dependency
13
+ name: rake-compiler
14
+ requirement: !ruby/object:Gem::Requirement
15
+ requirements:
16
+ - - "~>"
17
+ - !ruby/object:Gem::Version
18
+ version: '1.0'
19
+ type: :development
20
+ prerelease: false
21
+ version_requirements: !ruby/object:Gem::Requirement
22
+ requirements:
23
+ - - "~>"
24
+ - !ruby/object:Gem::Version
25
+ version: '1.0'
26
+ - !ruby/object:Gem::Dependency
27
+ name: minitest
28
+ requirement: !ruby/object:Gem::Requirement
29
+ requirements:
30
+ - - "~>"
31
+ - !ruby/object:Gem::Version
32
+ version: '5.0'
33
+ type: :development
34
+ prerelease: false
35
+ version_requirements: !ruby/object:Gem::Requirement
36
+ requirements:
37
+ - - "~>"
38
+ - !ruby/object:Gem::Version
39
+ version: '5.0'
40
+ description: Nokolexbor is a high-performance HTML5 parser, with support for both
41
+ CSS selectors and XPath. It's API is designed to be compatible with Nokogiri.
42
+ email: zyc9012@gmail.com
43
+ executables: []
44
+ extensions: []
45
+ extra_rdoc_files: []
46
+ files:
47
+ - lib/nokolexbor.rb
48
+ - lib/nokolexbor/3.1/nokolexbor.so
49
+ - lib/nokolexbor/3.2/nokolexbor.so
50
+ - lib/nokolexbor/3.3/nokolexbor.so
51
+ - lib/nokolexbor/3.4/nokolexbor.so
52
+ - lib/nokolexbor/4.0/nokolexbor.so
53
+ - lib/nokolexbor/builder.rb
54
+ - lib/nokolexbor/document.rb
55
+ - lib/nokolexbor/document_fragment.rb
56
+ - lib/nokolexbor/node.rb
57
+ - lib/nokolexbor/node_set.rb
58
+ - lib/nokolexbor/version.rb
59
+ - lib/nokolexbor/xpath.rb
60
+ - lib/nokolexbor/xpath_context.rb
61
+ homepage: https://github.com/serpapi/nokolexbor
62
+ licenses:
63
+ - MIT
64
+ metadata: {}
65
+ rdoc_options: []
66
+ require_paths:
67
+ - lib
68
+ required_ruby_version: !ruby/object:Gem::Requirement
69
+ requirements:
70
+ - - ">="
71
+ - !ruby/object:Gem::Version
72
+ version: '3.1'
73
+ - - "<"
74
+ - !ruby/object:Gem::Version
75
+ version: 4.1.dev
76
+ required_rubygems_version: !ruby/object:Gem::Requirement
77
+ requirements:
78
+ - - ">="
79
+ - !ruby/object:Gem::Version
80
+ version: '0'
81
+ requirements: []
82
+ rubygems_version: 4.0.3
83
+ specification_version: 4
84
+ summary: High-performance HTML5 parser, with support for both CSS selectors and XPath.
85
+ test_files: []