parsanol 1.3.30-aarch64-linux → 1.3.32-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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 4ed7c53cc9ff8168c9a6a08bbc33f2f6aaa007302eac69e9739b593431714841
4
- data.tar.gz: ba708d8cbc56bf73854fb1d7477779d7d38fce07e1195cebb65bf614a35bf97a
3
+ metadata.gz: 376b3aefed6052988b85cd2f404078eaacca3165844da1be040512fa923aaca7
4
+ data.tar.gz: 4bd78d928a42920ae6c1463711cc33723693acf423eaa9ed239a50a5f884abad
5
5
  SHA512:
6
- metadata.gz: be07b715e5c3cd4b23d05be9b6e17bb5f6fc9f9d8b1972af660b49aec037760e3f1e03ec0068427dda89bb40d546200b4a2c43eec1583c3fe9869e616410a075
7
- data.tar.gz: 77a109bbf72496a646975bd9b421ed35a319dfa130acfce05d1ffd22df22045832082d5fb9d04b87ebf285a144bd5a1a89cadb9919102e225144860c73a9e444
6
+ metadata.gz: 1cceac3f060e40e7b09f8cf838b129b3bdd7116454ff223c648ac49f2258a8231de23afb8f1041924c767ba3157aa7764d2b794c135c6c50225ea0c8af63be2e
7
+ data.tar.gz: 3b1a447ff4f97a46fc1c0976da40e82242508aea75b733163ddb9f124bd2af7b7880bb5b349279c828e2c47ce957ed5bb5d3bf6cfce58389979755a88194055c
data/README.adoc CHANGED
@@ -156,6 +156,24 @@ Run your own benchmarks with:
156
156
  bundle exec ruby examples/benchmark_examples.rb
157
157
  ----
158
158
 
159
+ [[engine-posture]]
160
+ ==== Engine roles
161
+
162
+ Parsanol ships two engines with one semantic contract (identical parse
163
+ trees and error messages):
164
+
165
+ * **Native (default)** — the Rust extension. It handles every parsing
166
+ mode, including error cause trees, `prefix:` and `reporter:`, with no
167
+ Ruby fallback during parsing. Prebuilt platform gems cover the common
168
+ triples; `bundle exec rake compile` builds it locally otherwise.
169
+ * **Ruby (`mode: :ruby`)** — the pure-Ruby engine. Its role is
170
+ portability (no prebuilt gem, no Rust toolchain, non-MRI rubies) and
171
+ serving as the semantic reference implementation for differential
172
+ testing against Parslet.
173
+
174
+ When both are available, the native engine is always used unless
175
+ `mode: :ruby` is requested explicitly.
176
+
159
177
  [[slice-support]]
160
178
  === Slice Support
161
179
 
Binary file
Binary file
Binary file
Binary file
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Parsanol
4
- VERSION = "1.3.30"
4
+ VERSION = "1.3.32"
5
5
  end
data/lib/parsanol.rb CHANGED
@@ -129,10 +129,60 @@ module Parsanol
129
129
  def match(pattern = nil)
130
130
  return CharacterClassBuilder.new unless pattern
131
131
 
132
+ match_quantifier_warning(pattern)
132
133
  Atoms::Re.new(pattern)
133
134
  end
134
135
  module_function :match
135
136
 
137
+ # `match` consumes exactly one character (Parslet parity), so a regex
138
+ # quantifier is silently truncated: match(/[0-9]+/) matches a single
139
+ # digit. Warn once per offending pattern — the intended spelling is
140
+ # `match("[0-9]").repeat(1)`.
141
+ # Deliberately mutable: it accumulates warned patterns per process.
142
+ QUANTIFIER_WARNED = {} # rubocop:disable Style/MutableConstant
143
+ private_constant :QUANTIFIER_WARNED
144
+
145
+ def match_quantifier_warning(pattern)
146
+ return if QUANTIFIER_WARNED.key?(pattern)
147
+ return unless pattern.is_a?(String)
148
+ return unless quantified_pattern?(pattern)
149
+
150
+ QUANTIFIER_WARNED[pattern] = true
151
+ warn "Parsanol: match(#{pattern.inspect}) matches exactly one character " \
152
+ "(Parslet parity); the quantifier is ignored. " \
153
+ "Use match(...).repeat(1) to match repeatedly."
154
+ end
155
+ module_function :match_quantifier_warning
156
+
157
+ # True when the pattern carries a top-level quantifier (+, *, ?, or
158
+ # {n,m}) outside a character class.
159
+ def quantified_pattern?(pattern)
160
+ in_class = false
161
+ escaped = false
162
+ previous = nil
163
+
164
+ pattern.each_char.with_index do |ch, idx|
165
+ if escaped
166
+ escaped = false
167
+ elsif ch == "\\"
168
+ escaped = true
169
+ elsif in_class
170
+ in_class = false if ch == "]"
171
+ elsif ch == "["
172
+ in_class = true
173
+ elsif %w[+ * ?].include?(ch) || (ch == "{" && idx + 1 < pattern.length && pattern[idx + 1] =~ /\d/)
174
+ # A leading quantifier applies to nothing and cannot truncate a
175
+ # character match; any other quantifier does.
176
+ return true if idx.positive? && !previous.nil? && previous != "("
177
+ end
178
+
179
+ previous = ch
180
+ end
181
+
182
+ false
183
+ end
184
+ module_function :quantified_pattern?
185
+
136
186
  # Creates a literal string matcher.
137
187
  #
138
188
  # @param literal [String] the string to match
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: parsanol
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.3.30
4
+ version: 1.3.32
5
5
  platform: aarch64-linux
6
6
  authors:
7
7
  - Ribose Inc.
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2026-09-17 00:00:00.000000000 Z
11
+ date: 2026-09-18 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: A small Ruby library for constructing parsers in the PEG (Parsing Expression
14
14
  Grammar) fashion. Parsanol provides Parslet-compatible API with additional features