htx 0.0.8 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b83c07872c223b61b939883d9f2f6bc45a1cecc380c4b21701d04a606e7ae381
4
- data.tar.gz: bfbf43071b20b13be3895bf4e358617765f39f276ed1d37c91c93f09c024b48a
3
+ metadata.gz: 83c2b45f8852d11b5faa35989c0552a4135c3270d20aaaa2af8d170e696ad840
4
+ data.tar.gz: dcbbb3aac2484f55b445a029c9916e282dc75b93197f630b40227110aba02c28
5
5
  SHA512:
6
- metadata.gz: 0dc4f9f8fad2b18266ca93a562fa1565361b330744e8f02134341c1a5982f0821a9b008975adcff7840626d85f05bca223dd433705799c227217584dab1f970c
7
- data.tar.gz: 58756df107105643831511c4faff3f7ccdc96fdcd318d7f65833cb642b4c08be60ab2e2f9cc6ffb999a9980a63a8a15a9b0b8b94c0aab8a4f8447ee61909c5a4
6
+ metadata.gz: 8a26b13b0f0cdddf7d9338f1876c23e59adaef4abd2d706cae4a984bd74ca207465e93d6c1d1f0877adf5f27999ddbfd59d93c703ffe098ea7cfc239bc8f391d
7
+ data.tar.gz: e6ace0fd8c2289e1b2062e6f9e976e017b3e639cfd0eb0777bf5e4bd9ded53d8774c843cfcb1cc55a1c491d0fe6d4f81e337455897ec471bebc0d333db202ba5
data/LICENSE CHANGED
@@ -1,4 +1,4 @@
1
- Copyright 2019-2022 Nate Pickens
1
+ Copyright 2019-2023 Nate Pickens
2
2
 
3
3
  Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated
4
4
  documentation files (the "Software"), to deal in the Software without restriction, including without
data/README.md CHANGED
@@ -29,7 +29,7 @@ template = File.read(File.join('some/asset/dir', path))
29
29
 
30
30
  HTX.compile(path, template)
31
31
 
32
- # window['/components/crew.htx'] = function(htx) {
32
+ # globalThis['/components/crew.htx'] = function(htx) {
33
33
  # // ...
34
34
  # }
35
35
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.8
1
+ 0.1.0
data/lib/htx/template.rb CHANGED
@@ -17,7 +17,6 @@ module HTX
17
17
  'svg' => 'http://www.w3.org/2000/svg',
18
18
  }.freeze
19
19
 
20
- INDENT_VALID = /^( +|\t+)$/.freeze
21
20
  INDENT_GUESS = /^( +|\t+)(?=\S)/.freeze
22
21
  INDENT_REGEX = /\n(?=[^\n])/.freeze
23
22
 
@@ -32,17 +31,14 @@ module HTX
32
31
  NON_WHITESPACE = /\S/.freeze
33
32
 
34
33
  ##
35
- # Returns false. In the near future when support for the <:> tag has been dropped (in favor of
36
- # <htx-content>), will return true if Nokogiri's HTML5 parser is available. To use it now, monkey patch
37
- # this method to return true.
34
+ # Returns true if Nokogiri's HTML5 parser is available.
38
35
  #
39
36
  def self.html5_parser?
40
- false # !!defined?(Nokogiri::HTML5)
37
+ defined?(Nokogiri::HTML5)
41
38
  end
42
39
 
43
40
  ##
44
- # Returns Nokogiri's HTML5 parser if available and enabled, and Nokogiri's regular HTML parser
45
- # otherwise.
41
+ # Returns Nokogiri's HTML5 parser if available or Nokogiri's default HTML (4) parser otherwise.
46
42
  #
47
43
  def self.nokogiri_parser
48
44
  html5_parser? ? Nokogiri::HTML5 : Nokogiri::HTML
@@ -62,24 +58,11 @@ module HTX
62
58
  ##
63
59
  # Compiles the HTX template.
64
60
  #
65
- # * +assign_to+ - JavaScript object to assign the template function to (default: <tt>window</tt>).
66
- # * +indent+ - DEPRECATED. Indentation amount (number) or string (must be only spaces or tabs but not
67
- # both) to use for indentation of compiled output (default: indentation of first indented line of
68
- # uncompiled template).
69
- #
70
- def compile(assign_to: nil, indent: (indent_omitted = true; nil))
71
- @assign_to = assign_to || 'window'
72
- @indent =
73
- if indent.kind_of?(Numeric)
74
- ' ' * indent
75
- elsif indent && !indent.match?(INDENT_VALID)
76
- raise("Invalid indent value #{indent.inspect}: only spaces and tabs (but not both) are allowed")
77
- else
78
- indent || @content[INDENT_GUESS] || INDENT_DEFAULT
79
- end
80
-
81
- warn('The indent: option for HTX template compilation is deprecated.') unless indent_omitted
82
-
61
+ # * +assign_to+ - JavaScript object to assign the template function to (default: +globalThis+).
62
+ #
63
+ def compile(assign_to: nil)
64
+ @assign_to = assign_to || 'globalThis'
65
+ @base_indent = @indent = @content[INDENT_GUESS] || INDENT_DEFAULT
83
66
  @static_key = 0
84
67
  @close_count = 0
85
68
  @whitespace_buff = nil
@@ -158,14 +141,35 @@ module HTX
158
141
  # * +node+ - Nokogiri node to process.
159
142
  #
160
143
  def process_fragment_node(node)
161
- append("#{@assign_to}['#{@name}'] = function(htx) {")
162
- @whitespace_buff = "\n"
144
+ append(
145
+ <<~JS
146
+ #{@assign_to}['#{@name}'] = ((HTX) => {
147
+ #{@indent}function render($rndr) {
148
+ JS
149
+ )
150
+
151
+ @indent = @base_indent * 2
163
152
 
164
153
  node.children.each do |child|
165
154
  process(child)
166
155
  end
167
156
 
168
- append("\n}\n",)
157
+ append("\n\n#{@indent}return $rndr.rootNode")
158
+
159
+ @indent = @base_indent
160
+
161
+ append(
162
+ +<<~JS
163
+
164
+ #{@indent}}
165
+
166
+ #{@indent}return function Template(context) {
167
+ #{@indent * 2}this.render = render.bind(context, new HTX.Renderer)
168
+ #{@indent}}
169
+ })(globalThis.HTX ||= {});
170
+ JS
171
+ )
172
+
169
173
  flush
170
174
  end
171
175
 
@@ -173,21 +177,16 @@ module HTX
173
177
  # Processes an element node.
174
178
  #
175
179
  # * +node+ - Nokogiri node to process.
176
- # * +xmlns+ - True if node is the descendent of a node with an xmlns attribute.
180
+ # * +xmlns+ - True if node is the descendant of a node with an xmlns attribute.
177
181
  #
178
182
  def process_element_node(node, xmlns: false)
179
183
  children = node.children
180
184
  childless = children.empty? || (children.size == 1 && self.class.formatting_node?(children.first))
181
185
  dynamic_key = self.class.attribute_value(node.attr(DYNAMIC_KEY_ATTR))
182
- attributes = self.class.process_attributes(node)
186
+ attributes = self.class.process_attributes(node, xmlns: xmlns)
183
187
  xmlns ||= !!self.class.namespace(node)
184
188
 
185
189
  if self.class.htx_content_node?(node)
186
- if node.name != CONTENT_TAG
187
- warn("#{@name}:#{node.line}: The <#{node.name}> tag has been deprecated. Use <#{CONTENT_TAG}> "\
188
- "for identical functionality.")
189
- end
190
-
191
190
  if attributes.size > 0
192
191
  raise(MalformedTemplateError.new("<#{node.name}> tags may not have attributes other than "\
193
192
  "#{DYNAMIC_KEY_ATTR}", @name, node))
@@ -263,13 +262,13 @@ module HTX
263
262
  # * +text+ - String to append to the compiled template string.
264
263
  #
265
264
  def append(text)
266
- return @compiled if text.nil? || text.empty?
265
+ return if text.nil? || text.empty?
267
266
 
268
267
  if @close_count > 0
269
268
  close_count = @close_count
270
269
  @close_count = 0
271
270
 
272
- append("htx.close(#{close_count unless close_count == 1})")
271
+ append("$rndr.close(#{close_count unless close_count == 1})")
273
272
  end
274
273
 
275
274
  if @whitespace_buff
@@ -286,8 +285,6 @@ module HTX
286
285
 
287
286
  flush if text.match?(NON_WHITESPACE)
288
287
  @statement_buff << text
289
-
290
- @compiled
291
288
  end
292
289
 
293
290
  ##
@@ -302,7 +299,7 @@ module HTX
302
299
  args << 0 unless args.last.kind_of?(Integer)
303
300
  args[-1] |= (@static_key += 1) << FLAG_BITS
304
301
 
305
- append("htx.node(#{args.join(', ')})")
302
+ append("$rndr.node(#{args.join(', ')})")
306
303
  end
307
304
 
308
305
  ##
@@ -311,8 +308,6 @@ module HTX
311
308
  def flush
312
309
  @compiled << @statement_buff
313
310
  @statement_buff.clear
314
-
315
- @compiled
316
311
  end
317
312
 
318
313
  ##
@@ -340,7 +335,7 @@ module HTX
340
335
  # * +node+ - Nokogiri node to check.
341
336
  #
342
337
  def self.htx_content_node?(node)
343
- node && (node.name == CONTENT_TAG || node.name == 'htx-text' || node.name == ':')
338
+ node&.name == CONTENT_TAG
344
339
  end
345
340
 
346
341
  ##
@@ -348,10 +343,10 @@ module HTX
348
343
  #
349
344
  # * +node+ - Nokogiri node to process the attributes of.
350
345
  #
351
- def self.process_attributes(node)
346
+ def self.process_attributes(node, xmlns:)
352
347
  attributes = []
353
348
 
354
- if !node.attribute('xmlns') && (xmlns = namespace(node))
349
+ if !xmlns && !node.attribute('xmlns') && (xmlns = namespace(node))
355
350
  attributes.push(
356
351
  attribute_name('xmlns'),
357
352
  attribute_value(xmlns)
@@ -369,7 +364,9 @@ module HTX
369
364
  end
370
365
 
371
366
  ##
367
+ # Returns namespace URL of a Nokogiri node.
372
368
  #
369
+ # * +node+ - Nokogiri node to get the namespace of.
373
370
  #
374
371
  def self.namespace(node)
375
372
  node.namespace&.href || DEFAULT_XMLNS[node.name]
@@ -404,15 +401,10 @@ module HTX
404
401
  text ? TextParser.new(text, statement_allowed: false).parse : nil
405
402
  end
406
403
 
407
- # The Nokogiri HTML parser downcases all tag and attribute names, but SVG tags and attributes are case
408
- # sensitive and often mix cased. These maps are used to restore the correct case of such tags and
409
- # attributes.
410
- #
411
- # Note: Nokogiri's newer HTML5 parser resulting from the Nokogumbo merge fixes this issue, but it is
412
- # currently not available for JRuby. It also does not parse <:> as a tag, which is why it's been
413
- # deprecated in favor of <htx-content>. Once support for <:> has been completely removed, the HTML5
414
- # parser will be used for regular Ruby and this tag and attribute mapping hack reserved for JRuby (and
415
- # any other potential environments where the HTML5 parser is not available).
404
+ # The Nokogiri::HTML5 parser is used whenever possible, which correctly handles mix-cased SVG tag and
405
+ # attribute names. But when falling back to the Nokogiri::HTML parser (e.g. in JRuby environments where
406
+ # Nokogiri::HTML5 is not available), all tag and attribute names get downcased. These maps are used to
407
+ # restore the correct case.
416
408
 
417
409
  # Source: https://developer.mozilla.org/en-US/docs/Web/SVG/Element
418
410
  TAG_MAP = %w[
@@ -216,6 +216,8 @@ module HTX
216
216
  ##
217
217
  # Flushes buffer during parsing and performs statement detection if appropriate.
218
218
  #
219
+ # * +state+ - Last state that was parsed.
220
+ #
219
221
  def flush(state = nil)
220
222
  return if @buffer.empty?
221
223
 
data/lib/htx/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module HTX
4
- VERSION = '0.0.8'
4
+ VERSION = '0.1.0'
5
5
  end
data/lib/htx.rb CHANGED
@@ -21,18 +21,4 @@ module HTX
21
21
  def self.compile(name, content, options = EMPTY_HASH)
22
22
  Template.new(name, content).compile(**options)
23
23
  end
24
-
25
- ##
26
- # DEPRECATED. Use HTX::Template.new instead. HTX was formerly a class that would be instantiated for
27
- # compilation. This method allows HTX.new calls to continue working (but support will be removed in the
28
- # near future).
29
- #
30
- # * +name+ - Template name. Conventionally the path of the template file.
31
- # * +content+ - Template content.
32
- #
33
- def self.new(name, content)
34
- warn('HTX.new is deprecated. Please use HTX::Template.new instead.')
35
-
36
- Template.new(name, content)
37
- end
38
24
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: htx
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.8
4
+ version: 0.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nate Pickens
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2022-03-31 00:00:00.000000000 Z
11
+ date: 2023-07-07 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: nokogiri
@@ -96,7 +96,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
96
96
  - !ruby/object:Gem::Version
97
97
  version: '0'
98
98
  requirements: []
99
- rubygems_version: 3.2.32
99
+ rubygems_version: 3.4.6
100
100
  signing_key:
101
101
  specification_version: 4
102
102
  summary: A Ruby compiler for HTX templates.