sass-embedded 1.58.0-x86_64-linux-musl

Sign up to get free protection for your applications and to get access to all the features.
Files changed (43) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE +20 -0
  3. data/README.md +42 -0
  4. data/ext/sass/embedded.rb +12 -0
  5. data/ext/sass/embedded_sass_pb.rb +349 -0
  6. data/ext/sass/sass_embedded/dart-sass-embedded +20 -0
  7. data/ext/sass/sass_embedded/src/LICENSE +1434 -0
  8. data/ext/sass/sass_embedded/src/dart +0 -0
  9. data/ext/sass/sass_embedded/src/dart-sass-embedded.snapshot +0 -0
  10. data/lib/sass/compile_error.rb +28 -0
  11. data/lib/sass/compile_result.rb +23 -0
  12. data/lib/sass/embedded/async.rb +58 -0
  13. data/lib/sass/embedded/channel.rb +61 -0
  14. data/lib/sass/embedded/compiler.rb +60 -0
  15. data/lib/sass/embedded/dispatcher.rb +98 -0
  16. data/lib/sass/embedded/host/function_registry.rb +89 -0
  17. data/lib/sass/embedded/host/importer_registry.rb +104 -0
  18. data/lib/sass/embedded/host/logger_registry.rb +50 -0
  19. data/lib/sass/embedded/host/value_protofier.rb +241 -0
  20. data/lib/sass/embedded/host.rb +141 -0
  21. data/lib/sass/embedded/protofier.rb +78 -0
  22. data/lib/sass/embedded/structifier.rb +39 -0
  23. data/lib/sass/embedded/varint.rb +35 -0
  24. data/lib/sass/embedded/version.rb +7 -0
  25. data/lib/sass/embedded.rb +251 -0
  26. data/lib/sass/logger/silent.rb +26 -0
  27. data/lib/sass/logger/source_location.rb +21 -0
  28. data/lib/sass/logger/source_span.rb +27 -0
  29. data/lib/sass/script_error.rb +10 -0
  30. data/lib/sass/value/argument_list.rb +37 -0
  31. data/lib/sass/value/boolean.rb +52 -0
  32. data/lib/sass/value/color.rb +253 -0
  33. data/lib/sass/value/function.rb +54 -0
  34. data/lib/sass/value/fuzzy_math.rb +80 -0
  35. data/lib/sass/value/list.rb +79 -0
  36. data/lib/sass/value/map.rb +71 -0
  37. data/lib/sass/value/null.rb +48 -0
  38. data/lib/sass/value/number/unit.rb +186 -0
  39. data/lib/sass/value/number.rb +365 -0
  40. data/lib/sass/value/string.rb +55 -0
  41. data/lib/sass/value.rb +128 -0
  42. data/lib/sass-embedded.rb +4 -0
  43. metadata +186 -0
@@ -0,0 +1,365 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'number/unit'
4
+
5
+ module Sass
6
+ module Value
7
+ # Sass's number type.
8
+ #
9
+ # @see https://sass-lang.com/documentation/js-api/classes/SassNumber
10
+ class Number
11
+ include Value
12
+
13
+ # @param value [Numeric]
14
+ # @param unit [::String, Hash]
15
+ # @option unit [Array<::String>] :numerator_units
16
+ # @option unit [Array<::String>] :denominator_units
17
+ def initialize(value, unit = nil)
18
+ case unit
19
+ when nil
20
+ numerator_units = []
21
+ denominator_units = []
22
+ when ::String
23
+ numerator_units = [unit]
24
+ denominator_units = []
25
+ when ::Hash
26
+ numerator_units = unit.fetch(:numerator_units, [])
27
+ unless numerator_units.is_a? Array
28
+ raise Sass::ScriptError, "invalid numerator_units #{numerator_units.inspect}"
29
+ end
30
+
31
+ denominator_units = unit.fetch(:denominator_units, [])
32
+ unless denominator_units.is_a? Array
33
+ raise Sass::ScriptError, "invalid denominator_units #{denominator_units.inspect}"
34
+ end
35
+ else
36
+ raise Sass::ScriptError, "invalid unit #{unit.inspect}"
37
+ end
38
+
39
+ unless denominator_units.empty? && numerator_units.empty?
40
+ value = value.dup
41
+ numerator_units = numerator_units.dup
42
+ new_denominator_units = []
43
+
44
+ denominator_units.each do |denominator_unit|
45
+ index = numerator_units.find_index do |numerator_unit|
46
+ factor = Unit.conversion_factor(denominator_unit, numerator_unit)
47
+ if factor.nil?
48
+ false
49
+ else
50
+ value *= factor
51
+ true
52
+ end
53
+ end
54
+ if index.nil?
55
+ new_denominator_units.push(denominator_unit)
56
+ else
57
+ numerator_units.delete_at(index)
58
+ end
59
+ end
60
+
61
+ denominator_units = new_denominator_units
62
+ end
63
+
64
+ @value = value.freeze
65
+ @numerator_units = numerator_units.freeze
66
+ @denominator_units = denominator_units.freeze
67
+ end
68
+
69
+ # @return [Numeric]
70
+ attr_reader :value
71
+
72
+ # @return [Array<::String>]
73
+ attr_reader :numerator_units, :denominator_units
74
+
75
+ # @return [::Boolean]
76
+ def ==(other)
77
+ return false unless other.is_a? Sass::Value::Number
78
+
79
+ return false if numerator_units.length != other.numerator_units.length ||
80
+ denominator_units.length != other.denominator_units.length
81
+
82
+ return FuzzyMath.equals(value, other.value) if unitless?
83
+
84
+ if Unit.canonicalize_units(numerator_units) != Unit.canonicalize_units(other.numerator_units) &&
85
+ Unit.canonicalize_units(denominator_units) != Unit.canonicalize_units(other.denominator_units)
86
+ return false
87
+ end
88
+
89
+ FuzzyMath.equals(
90
+ (value *
91
+ Unit.canonical_multiplier(numerator_units) /
92
+ Unit.canonical_multiplier(denominator_units)),
93
+ (other.value *
94
+ Unit.canonical_multiplier(other.numerator_units) /
95
+ Unit.canonical_multiplier(other.denominator_units))
96
+ )
97
+ end
98
+
99
+ # @return [Integer]
100
+ def hash
101
+ @hash ||= FuzzyMath.hash(canonical_units_value)
102
+ end
103
+
104
+ # @return [::Boolean]
105
+ def unitless?
106
+ numerator_units.empty? && denominator_units.empty?
107
+ end
108
+
109
+ # @return [Number]
110
+ # @raise [ScriptError]
111
+ def assert_unitless(name = nil)
112
+ raise Sass::ScriptError.new("Expected #{self} to have no units", name) unless unitless?
113
+
114
+ self
115
+ end
116
+
117
+ # @return [::Boolean]
118
+ def units?
119
+ !unitless?
120
+ end
121
+
122
+ # @param unit [::String]
123
+ # @return [::Boolean]
124
+ def unit?(unit)
125
+ single_unit? && numerator_units.first == unit
126
+ end
127
+
128
+ # @param unit [::String]
129
+ # @return [Number]
130
+ # @raise [ScriptError]
131
+ def assert_unit(unit, name = nil)
132
+ raise Sass::ScriptError.new("Expected #{self} to have unit #{unit.inspect}", name) unless unit?(unit)
133
+
134
+ self
135
+ end
136
+
137
+ # @return [::Boolean]
138
+ def integer?
139
+ FuzzyMath.integer?(value)
140
+ end
141
+
142
+ # @return [Integer]
143
+ # @raise [ScriptError]
144
+ def assert_integer(name = nil)
145
+ raise Sass::ScriptError.new("#{self} is not an integer", name) unless integer?
146
+
147
+ to_i
148
+ end
149
+
150
+ # @return [Integer]
151
+ def to_i
152
+ FuzzyMath.to_i(value)
153
+ end
154
+
155
+ # @param min [Numeric]
156
+ # @param max [Numeric]
157
+ # @return [Numeric]
158
+ # @raise [ScriptError]
159
+ def assert_between(min, max, name = nil)
160
+ FuzzyMath.assert_between(value, min, max, name)
161
+ end
162
+
163
+ # @param unit [::String]
164
+ # @return [::Boolean]
165
+ def compatible_with_unit?(unit)
166
+ single_unit? && !Unit.conversion_factor(numerator_units.first, unit).nil?
167
+ end
168
+
169
+ # @param new_numerator_units [Array<::String>]
170
+ # @param new_denominator_units [Array<::String>]
171
+ # @return [Number]
172
+ def convert(new_numerator_units, new_denominator_units, name = nil)
173
+ Number.new(convert_value(new_numerator_units, new_denominator_units, name), {
174
+ numerator_units: new_numerator_units,
175
+ denominator_units: new_denominator_units
176
+ })
177
+ end
178
+
179
+ # @param new_numerator_units [Array<::String>]
180
+ # @param new_denominator_units [Array<::String>]
181
+ # @return [Numeric]
182
+ def convert_value(new_numerator_units, new_denominator_units, name = nil)
183
+ coerce_or_convert_value(new_numerator_units, new_denominator_units,
184
+ coerce_unitless: false,
185
+ name: name)
186
+ end
187
+
188
+ # @param other [Number]
189
+ # @return [Number]
190
+ def convert_to_match(other, name = nil, other_name = nil)
191
+ Number.new(convert_value_to_match(other, name, other_name), {
192
+ numerator_units: other.numerator_units,
193
+ denominator_units: other.denominator_units
194
+ })
195
+ end
196
+
197
+ # @param other [Number]
198
+ # @return [Numeric]
199
+ def convert_value_to_match(other, name = nil, other_name = nil)
200
+ coerce_or_convert_value(other.numerator_units, other.denominator_units,
201
+ coerce_unitless: false,
202
+ name: name,
203
+ other: other,
204
+ other_name: other_name)
205
+ end
206
+
207
+ # @param new_numerator_units [Array<::String>]
208
+ # @param new_denominator_units [Array<::String>]
209
+ # @return [Number]
210
+ def coerce(new_numerator_units, new_denominator_units, name = nil)
211
+ Number.new(coerce_value(new_numerator_units, new_denominator_units, name), {
212
+ numerator_units: new_numerator_units,
213
+ denominator_units: new_denominator_units
214
+ })
215
+ end
216
+
217
+ # @param new_numerator_units [Array<::String>]
218
+ # @param new_denominator_units [Array<::String>]
219
+ # @return [Numeric]
220
+ def coerce_value(new_numerator_units, new_denominator_units, name = nil)
221
+ coerce_or_convert_value(new_numerator_units, new_denominator_units,
222
+ coerce_unitless: true,
223
+ name: name)
224
+ end
225
+
226
+ # @param unit [::String]
227
+ # @return [Numeric]
228
+ def coerce_value_to_unit(unit, name = nil)
229
+ coerce_value([unit], [], name)
230
+ end
231
+
232
+ # @param other [Number]
233
+ # @return [Number]
234
+ def coerce_to_match(other, name = nil, other_name = nil)
235
+ Number.new(coerce_value_to_match(other, name, other_name), {
236
+ numerator_units: other.numerator_units,
237
+ denominator_units: other.denominator_units
238
+ })
239
+ end
240
+
241
+ # @param other [Number]
242
+ # @return [Numeric]
243
+ def coerce_value_to_match(other, name = nil, other_name = nil)
244
+ coerce_or_convert_value(other.numerator_units, other.denominator_units,
245
+ coerce_unitless: true,
246
+ name: name,
247
+ other: other,
248
+ other_name: other_name)
249
+ end
250
+
251
+ # @return [Number]
252
+ def assert_number(_name = nil)
253
+ self
254
+ end
255
+
256
+ private
257
+
258
+ def single_unit?
259
+ numerator_units.length == 1 && denominator_units.empty?
260
+ end
261
+
262
+ def canonical_units_value
263
+ if unitless?
264
+ value
265
+ elsif single_unit?
266
+ value * Unit.canonical_multiplier_for_unit(numerator_units.first)
267
+ else
268
+ value * Unit.canonical_multiplier(numerator_units) / Unit.canonical_multiplier(denominator_units)
269
+ end
270
+ end
271
+
272
+ def coerce_or_convert_value(new_numerator_units, new_denominator_units,
273
+ coerce_unitless:,
274
+ name: nil,
275
+ other: nil,
276
+ other_name: nil)
277
+ if other && (other.numerator_units != new_denominator_units && other.denominator_units != new_denominator_units)
278
+ raise Sass::ScriptError, "Expect #{other} to have units #{unit_string(new_numerator_units,
279
+ new_denominator_units).inspect}"
280
+ end
281
+
282
+ return value if numerator_units == new_numerator_units && denominator_units == new_denominator_units
283
+
284
+ return value if numerator_units == new_numerator_units && denominator_units == new_denominator_units
285
+
286
+ other_unitless = new_numerator_units.empty? && new_denominator_units.empty?
287
+
288
+ return value if coerce_unitless && (unitless? || other_unitless)
289
+
290
+ compatibility_error = lambda {
291
+ unless other.nil?
292
+ message = +"#{self} and"
293
+ message << " $#{other_name}:" unless other_name.nil?
294
+ message << " #{other} have incompatible units"
295
+ message << " (one has units and the other doesn't)" if unitless? || other_unitless
296
+ return Sass::ScriptError.new(message, name)
297
+ end
298
+
299
+ return Sass::ScriptError.new("Expected #{self} to have no units", name) unless other_unitless
300
+
301
+ if new_numerator_units.length == 1 && new_denominator_units.empty?
302
+ type = Unit::TYPES_BY_UNIT[new_numerator_units.first]
303
+ return Sass::ScriptError.new(
304
+ "Expected #{self} to have a #{type} unit (#{Unit::UNITS_BY_TYPE[type].join(', ')})", name
305
+ )
306
+ end
307
+
308
+ unit_length = new_numerator_units.length + new_denominator_units.length
309
+ units = unit_string(new_numerator_units, new_denominator_units)
310
+ Sass::ScriptError.new("Expected #{self} to have unit#{unit_length > 1 ? 's' : ''} #{units}", name)
311
+ }
312
+
313
+ result = value
314
+
315
+ old_numerator_units = numerator_units.dup
316
+ new_numerator_units.each do |new_numerator_unit|
317
+ index = old_numerator_units.find_index do |old_numerator_unit|
318
+ factor = Unit.conversion_factor(new_numerator_unit, old_numerator_unit)
319
+ if factor.nil?
320
+ false
321
+ else
322
+ result *= factor
323
+ true
324
+ end
325
+ end
326
+ raise compatibility_error.call if index.nil?
327
+
328
+ old_numerator_units.delete_at(index)
329
+ end
330
+
331
+ old_denominator_units = denominator_units.dup
332
+ new_denominator_units.each do |new_denominator_unit|
333
+ index = old_denominator_units.find_index do |old_denominator_unit|
334
+ factor = Unit.conversion_factor(new_denominator_unit, old_denominator_unit)
335
+ if factor.nil?
336
+ false
337
+ else
338
+ result /= factor
339
+ true
340
+ end
341
+ end
342
+ raise compatibility_error.call if index.nil?
343
+
344
+ old_denominator_units.delete_at(index)
345
+ end
346
+
347
+ raise compatibility_error.call unless old_numerator_units.empty? && old_denominator_units.empty?
348
+
349
+ result
350
+ end
351
+
352
+ def unit_string(numerator_units, denominator_units)
353
+ if numerator_units.empty?
354
+ return 'no units' if denominator_units.empty?
355
+
356
+ return denominator_units.length == 1 ? "#{denominator_units.first}^-1" : "(#{denominator_units.join('*')})^-1"
357
+ end
358
+
359
+ return numerator_units.join('*') if denominator_units.empty?
360
+
361
+ "#{numerator_units.join('*')}/#{denominator_units.join('*')}"
362
+ end
363
+ end
364
+ end
365
+ end
@@ -0,0 +1,55 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Sass
4
+ module Value
5
+ # Sass's string type.
6
+ #
7
+ # @see https://sass-lang.com/documentation/js-api/classes/SassString
8
+ class String
9
+ include Value
10
+
11
+ # @param text [::String]
12
+ # @param quoted [::Boolean]
13
+ def initialize(text = '', quoted: true)
14
+ @text = text.freeze
15
+ @quoted = quoted
16
+ end
17
+
18
+ # @return [::String]
19
+ attr_reader :text
20
+
21
+ # @return [::Boolean]
22
+ def quoted?
23
+ @quoted
24
+ end
25
+
26
+ # @return [::Boolean]
27
+ def ==(other)
28
+ other.is_a?(Sass::Value::String) && other.text == text
29
+ end
30
+
31
+ # @return [Integer]
32
+ def hash
33
+ @hash ||= text.hash
34
+ end
35
+
36
+ # @return [String]
37
+ def assert_string(_name = nil)
38
+ self
39
+ end
40
+
41
+ # @param sass_index [Number]
42
+ # @return [Integer]
43
+ def sass_index_to_string_index(sass_index, name = nil)
44
+ index = sass_index.assert_number(name).assert_integer(name)
45
+ raise Sass::ScriptError.new('String index may not be 0', name) if index.zero?
46
+
47
+ if index.abs > text.length
48
+ raise Sass::ScriptError.new("Invalid index #{sass_index} for a string with #{text.length} characters", name)
49
+ end
50
+
51
+ index.negative? ? text.length + index : index - 1
52
+ end
53
+ end
54
+ end
55
+ end
data/lib/sass/value.rb ADDED
@@ -0,0 +1,128 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative 'script_error'
4
+
5
+ module Sass
6
+ # The abstract base class of Sass's value types.
7
+ #
8
+ # @see https://sass-lang.com/documentation/js-api/classes/Value
9
+ module Value
10
+ # @return [::String, nil]
11
+ def separator
12
+ nil
13
+ end
14
+
15
+ # @return [::Boolean]
16
+ def bracketed?
17
+ false
18
+ end
19
+
20
+ # @return [::Boolean]
21
+ def eql?(other)
22
+ self == other
23
+ end
24
+
25
+ # @param index [Numeric]
26
+ # @return [Value]
27
+ def [](index)
28
+ at(index)
29
+ end
30
+
31
+ # @param index [Numeric]
32
+ # @return [Value]
33
+ def at(index)
34
+ index < 1 && index >= -1 ? self : nil
35
+ end
36
+
37
+ # @return [Array<Value>]
38
+ def to_a
39
+ [self]
40
+ end
41
+
42
+ # @return [::Boolean]
43
+ def to_bool
44
+ true
45
+ end
46
+
47
+ # @return [Map, nil]
48
+ def to_map
49
+ nil
50
+ end
51
+
52
+ # @return [Value, nil]
53
+ def to_nil
54
+ self
55
+ end
56
+
57
+ # @return [Boolean]
58
+ # @raise [ScriptError]
59
+ def assert_boolean(name = nil)
60
+ raise Sass::ScriptError.new("#{self} is not a boolean", name)
61
+ end
62
+
63
+ # @raise [ScriptError]
64
+ def assert_calculation(name = nil)
65
+ raise Sass::ScriptError.new("#{self} is not a calculation", name)
66
+ end
67
+
68
+ # @return [Color]
69
+ # @raise [ScriptError]
70
+ def assert_color(name = nil)
71
+ raise Sass::ScriptError.new("#{self} is not a color", name)
72
+ end
73
+
74
+ # @return [Function]
75
+ # @raise [ScriptError]
76
+ def assert_function(name = nil)
77
+ raise Sass::ScriptError.new("#{self} is not a function", name)
78
+ end
79
+
80
+ # @return [Map]
81
+ # @raise [ScriptError]
82
+ def assert_map(name = nil)
83
+ raise Sass::ScriptError.new("#{self} is not a map", name)
84
+ end
85
+
86
+ # @return [Number]
87
+ # @raise [ScriptError]
88
+ def assert_number(name = nil)
89
+ raise Sass::ScriptError.new("#{self} is not a number", name)
90
+ end
91
+
92
+ # @return [String]
93
+ # @raise [ScriptError]
94
+ def assert_string(name = nil)
95
+ raise Sass::ScriptError.new("#{self} is not a string", name)
96
+ end
97
+
98
+ # @param sass_index [Number]
99
+ # @return [Integer]
100
+ def sass_index_to_array_index(sass_index, name = nil)
101
+ index = sass_index.assert_number(name).assert_integer(name)
102
+ raise Sass::ScriptError.new('List index may not be 0', name) if index.zero?
103
+
104
+ if index.abs > to_a_length
105
+ raise Sass::ScriptError.new("Invalid index #{sass_index} for a list with #{to_a_length} elements", name)
106
+ end
107
+
108
+ index.negative? ? to_a_length + index : index - 1
109
+ end
110
+
111
+ private
112
+
113
+ def to_a_length
114
+ 1
115
+ end
116
+ end
117
+ end
118
+
119
+ require_relative 'value/list'
120
+ require_relative 'value/argument_list'
121
+ require_relative 'value/boolean'
122
+ require_relative 'value/color'
123
+ require_relative 'value/function'
124
+ require_relative 'value/fuzzy_math'
125
+ require_relative 'value/map'
126
+ require_relative 'value/null'
127
+ require_relative 'value/number'
128
+ require_relative 'value/string'
@@ -0,0 +1,4 @@
1
+ #!/usr/bin/env ruby
2
+ # frozen_string_literal: true
3
+
4
+ require_relative 'sass/embedded'