sass 3.2.0.alpha.278 → 3.2.0.alpha.291
Sign up to get free protection for your applications and to get access to all the features.
- data/REVISION +1 -1
- data/VERSION +1 -1
- data/VERSION_DATE +1 -1
- data/lib/sass/engine.rb +15 -9
- data/lib/sass/script/arg_list.rb +52 -0
- data/lib/sass/script/funcall.rb +45 -38
- data/lib/sass/script/lexer.rb +1 -0
- data/lib/sass/script/list.rb +1 -1
- data/lib/sass/script/literal.rb +1 -0
- data/lib/sass/script/number.rb +7 -6
- data/lib/sass/script/parser.rb +32 -34
- data/lib/sass/scss/parser.rb +6 -6
- data/lib/sass/tree/function_node.rb +8 -1
- data/lib/sass/tree/mixin_def_node.rb +8 -1
- data/lib/sass/tree/mixin_node.rb +8 -1
- data/lib/sass/tree/visitors/convert.rb +22 -6
- data/lib/sass/tree/visitors/perform.rb +88 -33
- data/test/sass/conversion_test.rb +54 -0
- data/test/sass/engine_test.rb +15 -13
- data/test/sass/functions_test.rb +3 -2
- data/test/sass/results/script.css +1 -1
- data/test/sass/results/units.css +2 -2
- data/test/sass/script_conversion_test.rb +1 -1
- data/test/sass/script_test.rb +2 -1
- data/test/sass/scss/scss_test.rb +359 -1
- metadata +21 -20
data/lib/sass/scss/parser.rb
CHANGED
@@ -170,16 +170,16 @@ module Sass
|
|
170
170
|
|
171
171
|
def mixin_directive
|
172
172
|
name = tok! IDENT
|
173
|
-
args = sass_script(:parse_mixin_definition_arglist)
|
173
|
+
args, splat = sass_script(:parse_mixin_definition_arglist)
|
174
174
|
ss
|
175
|
-
block(node(Sass::Tree::MixinDefNode.new(name, args)), :directive)
|
175
|
+
block(node(Sass::Tree::MixinDefNode.new(name, args, splat)), :directive)
|
176
176
|
end
|
177
177
|
|
178
178
|
def include_directive
|
179
179
|
name = tok! IDENT
|
180
|
-
args, keywords = sass_script(:parse_mixin_include_arglist)
|
180
|
+
args, keywords, splat = sass_script(:parse_mixin_include_arglist)
|
181
181
|
ss
|
182
|
-
include_node = node(Sass::Tree::MixinNode.new(name, args, keywords))
|
182
|
+
include_node = node(Sass::Tree::MixinNode.new(name, args, keywords, splat))
|
183
183
|
if tok?(/\{/)
|
184
184
|
include_node.has_children = true
|
185
185
|
block(include_node, :directive)
|
@@ -195,9 +195,9 @@ module Sass
|
|
195
195
|
|
196
196
|
def function_directive
|
197
197
|
name = tok! IDENT
|
198
|
-
args = sass_script(:parse_function_definition_arglist)
|
198
|
+
args, splat = sass_script(:parse_function_definition_arglist)
|
199
199
|
ss
|
200
|
-
block(node(Sass::Tree::FunctionNode.new(name, args)), :function)
|
200
|
+
block(node(Sass::Tree::FunctionNode.new(name, args, splat)), :function)
|
201
201
|
end
|
202
202
|
|
203
203
|
def return_directive
|
@@ -15,11 +15,18 @@ module Sass
|
|
15
15
|
# @return [Array<Script::Node>]
|
16
16
|
attr_accessor :args
|
17
17
|
|
18
|
+
# The splat argument for this function, if one exists.
|
19
|
+
#
|
20
|
+
# @return [Script::Node?]
|
21
|
+
attr_accessor :splat
|
22
|
+
|
18
23
|
# @param name [String] The function name
|
19
24
|
# @param args [Array<(Script::Node, Script::Node)>] The arguments for the function.
|
20
|
-
|
25
|
+
# @param splat [Script::Node] See \{#splat}
|
26
|
+
def initialize(name, args, splat)
|
21
27
|
@name = name
|
22
28
|
@args = args
|
29
|
+
@splat = splat
|
23
30
|
super()
|
24
31
|
end
|
25
32
|
end
|
@@ -15,15 +15,22 @@ module Sass
|
|
15
15
|
# @return [Array<(Script::Node, Script::Node)>]
|
16
16
|
attr_accessor :args
|
17
17
|
|
18
|
+
# The splat argument for this mixin, if one exists.
|
19
|
+
#
|
20
|
+
# @return [Script::Node?]
|
21
|
+
attr_accessor :splat
|
22
|
+
|
18
23
|
# Whether the mixin uses `@content`. Set during the nesting check phase.
|
19
24
|
# @return [Boolean]
|
20
25
|
attr_accessor :has_content
|
21
26
|
|
22
27
|
# @param name [String] The mixin name
|
23
28
|
# @param args [Array<(Script::Node, Script::Node)>] See \{#args}
|
24
|
-
|
29
|
+
# @param splat [Script::Node] See \{#splat}
|
30
|
+
def initialize(name, args, splat)
|
25
31
|
@name = name
|
26
32
|
@args = args
|
33
|
+
@splat = splat
|
27
34
|
super()
|
28
35
|
end
|
29
36
|
end
|
data/lib/sass/tree/mixin_node.rb
CHANGED
@@ -19,13 +19,20 @@ module Sass::Tree
|
|
19
19
|
# @return [{String => Script::Node}]
|
20
20
|
attr_accessor :keywords
|
21
21
|
|
22
|
+
# The splat argument for this mixin, if one exists.
|
23
|
+
#
|
24
|
+
# @return [Script::Node?]
|
25
|
+
attr_accessor :splat
|
26
|
+
|
22
27
|
# @param name [String] The name of the mixin
|
23
28
|
# @param args [Array<Script::Node>] See \{#args}
|
29
|
+
# @param splat [Script::Node] See \{#splat}
|
24
30
|
# @param keywords [{String => Script::Node}] See \{#keywords}
|
25
|
-
def initialize(name, args, keywords)
|
31
|
+
def initialize(name, args, keywords, splat)
|
26
32
|
@name = name
|
27
33
|
@args = args
|
28
34
|
@keywords = keywords
|
35
|
+
@splat = splat
|
29
36
|
super()
|
30
37
|
end
|
31
38
|
end
|
@@ -121,6 +121,10 @@ class Sass::Tree::Visitors::Convert < Sass::Tree::Visitors::Base
|
|
121
121
|
args = node.args.map do |v, d|
|
122
122
|
d ? "#{v.to_sass(@options)}: #{d.to_sass(@options)}" : v.to_sass(@options)
|
123
123
|
end.join(", ")
|
124
|
+
if node.splat
|
125
|
+
args << ", " unless node.args.empty?
|
126
|
+
args << node.splat.to_sass(@options) << "..."
|
127
|
+
end
|
124
128
|
|
125
129
|
"#{tab_str}@function #{dasherize(node.name)}(#{args})#{yield}"
|
126
130
|
end
|
@@ -167,27 +171,39 @@ class Sass::Tree::Visitors::Convert < Sass::Tree::Visitors::Base
|
|
167
171
|
|
168
172
|
def visit_mixindef(node)
|
169
173
|
args =
|
170
|
-
if node.args.empty?
|
174
|
+
if node.args.empty? && node.splat.nil?
|
171
175
|
""
|
172
176
|
else
|
173
|
-
'('
|
177
|
+
str = '('
|
178
|
+
str << node.args.map do |v, d|
|
174
179
|
if d
|
175
180
|
"#{v.to_sass(@options)}: #{d.to_sass(@options)}"
|
176
181
|
else
|
177
182
|
v.to_sass(@options)
|
178
183
|
end
|
179
|
-
end.join(", ")
|
184
|
+
end.join(", ")
|
185
|
+
|
186
|
+
if node.splat
|
187
|
+
str << ", " unless node.args.empty?
|
188
|
+
str << node.splat.to_sass(@options) << '...'
|
189
|
+
end
|
190
|
+
|
191
|
+
str << ')'
|
180
192
|
end
|
181
|
-
|
193
|
+
|
182
194
|
"#{tab_str}#{@format == :sass ? '=' : '@mixin '}#{dasherize(node.name)}#{args}#{yield}"
|
183
195
|
end
|
184
196
|
|
185
197
|
def visit_mixin(node)
|
186
|
-
unless node.args.empty? && node.keywords.empty?
|
198
|
+
unless node.args.empty? && node.keywords.empty? && node.splat.nil?
|
187
199
|
args = node.args.map {|a| a.to_sass(@options)}.join(", ")
|
188
200
|
keywords = Sass::Util.hash_to_a(node.keywords).
|
189
201
|
map {|k, v| "$#{dasherize(k)}: #{v.to_sass(@options)}"}.join(', ')
|
190
|
-
|
202
|
+
if node.splat
|
203
|
+
splat = (args.empty? && keywords.empty?) ? "" : ", "
|
204
|
+
splat = "#{splat}#{node.splat.to_sass(@options)}..."
|
205
|
+
end
|
206
|
+
arglist = "(#{args}#{', ' unless args.empty? || keywords.empty?}#{keywords}#{splat})"
|
191
207
|
end
|
192
208
|
"#{tab_str}#{@format == :sass ? '+' : '@include '}#{dasherize(node.name)}#{arglist}#{node.has_children ? yield : semi}\n"
|
193
209
|
end
|
@@ -7,6 +7,83 @@ class Sass::Tree::Visitors::Perform < Sass::Tree::Visitors::Base
|
|
7
7
|
new(environment).send(:visit, root)
|
8
8
|
end
|
9
9
|
|
10
|
+
# @api private
|
11
|
+
def self.perform_arguments(callable, args, keywords, splat)
|
12
|
+
desc = "#{callable.type.capitalize} #{callable.name}"
|
13
|
+
downcase_desc = "#{callable.type} #{callable.name}"
|
14
|
+
|
15
|
+
begin
|
16
|
+
unless keywords.empty?
|
17
|
+
unknown_args = keywords.keys - callable.args.map {|var| var.first.underscored_name}
|
18
|
+
if callable.splat && unknown_args.include?(callable.splat.underscored_name)
|
19
|
+
raise Sass::SyntaxError.new("Argument $#{callable.splat.name} of #{downcase_desc} cannot be used as a named argument.")
|
20
|
+
elsif unknown_args.any?
|
21
|
+
raise Sass::SyntaxError.new("#{desc} doesn't have #{unknown_args.length > 1 ? 'the following arguments:' : 'an argument named'} #{unknown_args.map{|name| "$#{name}"}.join ', '}.")
|
22
|
+
end
|
23
|
+
end
|
24
|
+
rescue Sass::SyntaxError => keyword_exception
|
25
|
+
end
|
26
|
+
|
27
|
+
# If there's no splat, raise the keyword exception immediately. The actual
|
28
|
+
# raising happens in the ensure clause at the end of this function.
|
29
|
+
return if keyword_exception && !callable.splat
|
30
|
+
|
31
|
+
if args.size > callable.args.size && !callable.splat
|
32
|
+
takes = callable.args.size
|
33
|
+
passed = args.size
|
34
|
+
raise Sass::SyntaxError.new(
|
35
|
+
"#{desc} takes #{takes} argument#{'s' unless takes == 1} " +
|
36
|
+
"but #{passed} #{passed == 1 ? 'was' : 'were'} passed.")
|
37
|
+
end
|
38
|
+
|
39
|
+
splat_sep = :comma
|
40
|
+
if splat
|
41
|
+
args += splat.to_a
|
42
|
+
splat_sep = splat.separator if splat.is_a?(Sass::Script::List)
|
43
|
+
# If the splat argument exists, there won't be any keywords passed in
|
44
|
+
# manually, so we can safely overwrite rather than merge here.
|
45
|
+
keywords = splat.keywords if splat.is_a?(Sass::Script::ArgList)
|
46
|
+
end
|
47
|
+
|
48
|
+
keywords = keywords.dup
|
49
|
+
env = Sass::Environment.new(callable.environment)
|
50
|
+
callable.args.zip(args[0...callable.args.length]) do |(var, default), value|
|
51
|
+
if value && keywords.include?(var.underscored_name)
|
52
|
+
raise Sass::SyntaxError.new("#{desc} was passed argument $#{var.name} both by position and by name.")
|
53
|
+
end
|
54
|
+
|
55
|
+
value ||= keywords.delete(var.underscored_name)
|
56
|
+
value ||= default && default.perform(env)
|
57
|
+
raise Sass::SyntaxError.new("#{desc} is missing argument #{var.inspect}.") unless value
|
58
|
+
env.set_local_var(var.name, value)
|
59
|
+
end
|
60
|
+
|
61
|
+
if callable.splat
|
62
|
+
rest = args[callable.args.length..-1]
|
63
|
+
arg_list = Sass::Script::ArgList.new(rest, keywords.dup, splat_sep)
|
64
|
+
arg_list.options = env.options
|
65
|
+
env.set_local_var(callable.splat.name, arg_list)
|
66
|
+
end
|
67
|
+
|
68
|
+
yield env
|
69
|
+
ensure
|
70
|
+
# If there's a keyword exception, we don't want to throw it immediately,
|
71
|
+
# because the invalid keywords may be part of a glob argument that should be
|
72
|
+
# passed on to another function. So we only raise it if we reach the end of
|
73
|
+
# this function *and* the keywords attached to the argument list glob object
|
74
|
+
# haven't been accessed.
|
75
|
+
#
|
76
|
+
# The keyword exception takes precedence over any Sass errors, but not over
|
77
|
+
# non-Sass exceptions.
|
78
|
+
if keyword_exception &&
|
79
|
+
!(arg_list && arg_list.keywords_accessed) &&
|
80
|
+
($!.nil? || $!.is_a?(Sass::SyntaxError))
|
81
|
+
raise keyword_exception
|
82
|
+
elsif $!
|
83
|
+
raise $!
|
84
|
+
end
|
85
|
+
end
|
86
|
+
|
10
87
|
protected
|
11
88
|
|
12
89
|
def initialize(env)
|
@@ -114,7 +191,7 @@ class Sass::Tree::Visitors::Perform < Sass::Tree::Visitors::Base
|
|
114
191
|
def visit_function(node)
|
115
192
|
env = Sass::Environment.new(@environment, node.options)
|
116
193
|
@environment.set_local_function(node.name,
|
117
|
-
Sass::Callable.new(node.name, node.args, env, node.children, !:has_content))
|
194
|
+
Sass::Callable.new(node.name, node.args, node.splat, env, node.children, !:has_content, "function"))
|
118
195
|
[]
|
119
196
|
end
|
120
197
|
|
@@ -157,7 +234,7 @@ class Sass::Tree::Visitors::Perform < Sass::Tree::Visitors::Base
|
|
157
234
|
def visit_mixindef(node)
|
158
235
|
env = Sass::Environment.new(@environment, node.options)
|
159
236
|
@environment.set_local_mixin(node.name,
|
160
|
-
Sass::Callable.new(node.name, node.args, env, node.children, node.has_content))
|
237
|
+
Sass::Callable.new(node.name, node.args, node.splat, env, node.children, node.has_content, "mixin"))
|
161
238
|
[]
|
162
239
|
end
|
163
240
|
|
@@ -174,40 +251,18 @@ class Sass::Tree::Visitors::Perform < Sass::Tree::Visitors::Base
|
|
174
251
|
raise Sass::SyntaxError.new(%Q{Mixin "#{node.name}" does not accept a content block.})
|
175
252
|
end
|
176
253
|
|
177
|
-
|
178
|
-
|
254
|
+
args = node.args.map {|a| a.perform(@environment)}
|
255
|
+
keywords = Sass::Util.map_hash(node.keywords) {|k, v| [k, v.perform(@environment)]}
|
256
|
+
splat = node.splat.perform(@environment) if node.splat
|
179
257
|
|
180
|
-
|
181
|
-
|
182
|
-
|
183
|
-
END
|
258
|
+
self.class.perform_arguments(mixin, args, keywords, splat) do |env|
|
259
|
+
env.caller = Sass::Environment.new(@environment)
|
260
|
+
env.content = node.children if node.has_children
|
184
261
|
|
185
|
-
|
186
|
-
|
187
|
-
|
188
|
-
raise Sass::SyntaxError.new("Mixin #{node.name} doesn't have an argument named $#{name}")
|
189
|
-
end
|
190
|
-
end
|
191
|
-
|
192
|
-
environment = mixin.args.zip(passed_args).
|
193
|
-
inject(Sass::Environment.new(mixin.environment)) do |env, ((var, default), value)|
|
194
|
-
env.set_local_var(var.name,
|
195
|
-
if value
|
196
|
-
value.perform(@environment)
|
197
|
-
elsif kv = passed_keywords[var.underscored_name]
|
198
|
-
kv.perform(@environment)
|
199
|
-
elsif default
|
200
|
-
default.perform(env)
|
201
|
-
end)
|
202
|
-
raise Sass::SyntaxError.new("Mixin #{node.name} is missing argument #{var.inspect}.") unless env.var(var.name)
|
203
|
-
env
|
262
|
+
trace_node = Sass::Tree::TraceNode.from_node(node.name, node)
|
263
|
+
with_environment(env) {trace_node.children = mixin.tree.map {|c| visit(c)}.flatten}
|
264
|
+
trace_node
|
204
265
|
end
|
205
|
-
environment.caller = Sass::Environment.new(@environment)
|
206
|
-
environment.content = node.children if node.has_children
|
207
|
-
|
208
|
-
trace_node = Sass::Tree::TraceNode.from_node(node.name, node)
|
209
|
-
with_environment(environment) {trace_node.children = mixin.tree.map {|c| visit(c)}.flatten}
|
210
|
-
trace_node
|
211
266
|
rescue Sass::SyntaxError => e
|
212
267
|
unless include_loop
|
213
268
|
e.modify_backtrace(:mixin => node.name, :line => node.line)
|
@@ -1562,6 +1562,60 @@ foo {
|
|
1562
1562
|
SCSS
|
1563
1563
|
end
|
1564
1564
|
|
1565
|
+
def test_mixin_var_args
|
1566
|
+
assert_scss_to_sass <<SASS, <<SCSS
|
1567
|
+
=foo($args...)
|
1568
|
+
a: b
|
1569
|
+
|
1570
|
+
=bar($a, $args...)
|
1571
|
+
a: b
|
1572
|
+
|
1573
|
+
.foo
|
1574
|
+
+foo($list...)
|
1575
|
+
+bar(1, $list...)
|
1576
|
+
SASS
|
1577
|
+
@mixin foo($args...) {
|
1578
|
+
a: b;
|
1579
|
+
}
|
1580
|
+
|
1581
|
+
@mixin bar($a, $args...) {
|
1582
|
+
a: b;
|
1583
|
+
}
|
1584
|
+
|
1585
|
+
.foo {
|
1586
|
+
@include foo($list...);
|
1587
|
+
@include bar(1, $list...);
|
1588
|
+
}
|
1589
|
+
SCSS
|
1590
|
+
end
|
1591
|
+
|
1592
|
+
def test_function_var_args
|
1593
|
+
assert_scss_to_sass <<SASS, <<SCSS
|
1594
|
+
@function foo($args...)
|
1595
|
+
@return foo
|
1596
|
+
|
1597
|
+
@function bar($a, $args...)
|
1598
|
+
@return bar
|
1599
|
+
|
1600
|
+
.foo
|
1601
|
+
a: foo($list...)
|
1602
|
+
b: bar(1, $list...)
|
1603
|
+
SASS
|
1604
|
+
@function foo($args...) {
|
1605
|
+
@return foo;
|
1606
|
+
}
|
1607
|
+
|
1608
|
+
@function bar($a, $args...) {
|
1609
|
+
@return bar;
|
1610
|
+
}
|
1611
|
+
|
1612
|
+
.foo {
|
1613
|
+
a: foo($list...);
|
1614
|
+
b: bar(1, $list...);
|
1615
|
+
}
|
1616
|
+
SCSS
|
1617
|
+
end
|
1618
|
+
|
1565
1619
|
## Regression Tests
|
1566
1620
|
|
1567
1621
|
def test_media_query_with_expr
|
data/test/sass/engine_test.rb
CHANGED
@@ -93,7 +93,7 @@ MSG
|
|
93
93
|
"a-\#{$b\n c: d" => ['Invalid CSS after "a-#{$b": expected "}", was ""', 1],
|
94
94
|
"=a($b: 1, $c)" => "Required argument $c must come before any optional arguments.",
|
95
95
|
"=a($b: 1)\n a: $b\ndiv\n +a(1,2)" => "Mixin a takes 1 argument but 2 were passed.",
|
96
|
-
"=a($b: 1)\n a: $b\ndiv\n +a(1,$c: 3)" => "Mixin a doesn't have an argument named $c",
|
96
|
+
"=a($b: 1)\n a: $b\ndiv\n +a(1,$c: 3)" => "Mixin a doesn't have an argument named $c.",
|
97
97
|
"=a($b)\n a: $b\ndiv\n +a" => "Mixin a is missing argument $b.",
|
98
98
|
"@function foo()\n 1 + 2" => "Functions can only contain variable declarations and control directives.",
|
99
99
|
"@function foo()\n foo: bar" => "Functions can only contain variable declarations and control directives.",
|
@@ -105,10 +105,10 @@ MSG
|
|
105
105
|
"@function foo($)\n @return 1" => ['Invalid CSS after "(": expected variable (e.g. $foo), was "$)"', 1],
|
106
106
|
"@function foo()\n @return" => 'Invalid @return: expected expression.',
|
107
107
|
"@function foo()\n @return 1\n $var: val" => 'Illegal nesting: Nothing may be nested beneath return directives.',
|
108
|
-
"@function foo($a)\n @return 1\na\n b: foo()" => 'Function foo is missing argument $a',
|
109
|
-
"@function foo()\n @return 1\na\n b: foo(2)" => '
|
110
|
-
"@function foo()\n @return 1\na\n b: foo($a: 1)" => "Function foo doesn't have an argument named $a",
|
111
|
-
"@function foo()\n @return 1\na\n b: foo($a: 1, $b: 2)" => "Function foo doesn't have the following arguments: $a, $b",
|
108
|
+
"@function foo($a)\n @return 1\na\n b: foo()" => 'Function foo is missing argument $a.',
|
109
|
+
"@function foo()\n @return 1\na\n b: foo(2)" => 'Function foo takes 0 arguments but 1 was passed.',
|
110
|
+
"@function foo()\n @return 1\na\n b: foo($a: 1)" => "Function foo doesn't have an argument named $a.",
|
111
|
+
"@function foo()\n @return 1\na\n b: foo($a: 1, $b: 2)" => "Function foo doesn't have the following arguments: $a, $b.",
|
112
112
|
"@return 1" => '@return may only be used within a function.',
|
113
113
|
"@if true\n @return 1" => '@return may only be used within a function.',
|
114
114
|
"@mixin foo\n @return 1\n@include foo" => ['@return may only be used within a function.', 2],
|
@@ -122,7 +122,7 @@ MSG
|
|
122
122
|
'@for $a from "foo" to 1' => '"foo" is not an integer.',
|
123
123
|
'@for $a from 1 to "2"' => '"2" is not an integer.',
|
124
124
|
'@for $a from 1 to "foo"' => '"foo" is not an integer.',
|
125
|
-
'@for $a from 1 to 1.232323' => '1.
|
125
|
+
'@for $a from 1 to 1.232323' => '1.23232 is not an integer.',
|
126
126
|
'@for $a from 1px to 3em' => "Incompatible units: 'em' and 'px'.",
|
127
127
|
'@if' => "Invalid if directive '@if': expected expression.",
|
128
128
|
'@while' => "Invalid while directive '@while': expected expression.",
|
@@ -1294,7 +1294,7 @@ bar
|
|
1294
1294
|
SASS
|
1295
1295
|
flunk("Expected exception")
|
1296
1296
|
rescue Sass::SyntaxError => e
|
1297
|
-
assert_equal("Function plus is missing argument $var1", e.message)
|
1297
|
+
assert_equal("Function plus is missing argument $var1.", e.message)
|
1298
1298
|
end
|
1299
1299
|
|
1300
1300
|
def test_function_with_extra_argument
|
@@ -1307,7 +1307,7 @@ bar
|
|
1307
1307
|
SASS
|
1308
1308
|
flunk("Expected exception")
|
1309
1309
|
rescue Sass::SyntaxError => e
|
1310
|
-
assert_equal("Function plus doesn't have an argument named $var3", e.message)
|
1310
|
+
assert_equal("Function plus doesn't have an argument named $var3.", e.message)
|
1311
1311
|
end
|
1312
1312
|
|
1313
1313
|
def test_function_with_positional_and_keyword_argument
|
@@ -1320,7 +1320,7 @@ bar
|
|
1320
1320
|
SASS
|
1321
1321
|
flunk("Expected exception")
|
1322
1322
|
rescue Sass::SyntaxError => e
|
1323
|
-
assert_equal("Function plus was passed argument $var2 both by position and by name", e.message)
|
1323
|
+
assert_equal("Function plus was passed argument $var2 both by position and by name.", e.message)
|
1324
1324
|
end
|
1325
1325
|
|
1326
1326
|
def test_function_with_keyword_before_positional_argument
|
@@ -1333,7 +1333,7 @@ bar
|
|
1333
1333
|
SASS
|
1334
1334
|
flunk("Expected exception")
|
1335
1335
|
rescue Sass::SyntaxError => e
|
1336
|
-
assert_equal("Positional arguments must come before keyword arguments", e.message)
|
1336
|
+
assert_equal("Positional arguments must come before keyword arguments.", e.message)
|
1337
1337
|
end
|
1338
1338
|
|
1339
1339
|
def test_function_with_if
|
@@ -1759,7 +1759,7 @@ SASS
|
|
1759
1759
|
|
1760
1760
|
def test_loud_comment_is_evaluated
|
1761
1761
|
assert_equal <<CSS, render(<<SASS)
|
1762
|
-
/* Hue: 327.
|
1762
|
+
/* Hue: 327.21649deg */
|
1763
1763
|
CSS
|
1764
1764
|
/*!
|
1765
1765
|
Hue: \#{hue(#f836a0)}
|
@@ -2872,11 +2872,13 @@ SCSS
|
|
2872
2872
|
end
|
2873
2873
|
|
2874
2874
|
def test_deprecated_PRECISION
|
2875
|
-
assert_warning(<<END) {assert_equal
|
2875
|
+
assert_warning(<<END) {assert_equal 100_000.0, Sass::Script::Number::PRECISION}
|
2876
2876
|
Sass::Script::Number::PRECISION is deprecated and will be removed in a future release. Use Sass::Script::Number.precision_factor instead.
|
2877
2877
|
END
|
2878
2878
|
end
|
2879
|
+
|
2879
2880
|
def test_changing_precision
|
2881
|
+
old_precision = Sass::Script::Number.precision
|
2880
2882
|
begin
|
2881
2883
|
Sass::Script::Number.precision = 8
|
2882
2884
|
assert_equal <<CSS, render(<<SASS)
|
@@ -2889,7 +2891,7 @@ div
|
|
2889
2891
|
too-much: 1.000000001
|
2890
2892
|
SASS
|
2891
2893
|
ensure
|
2892
|
-
Sass::Script::Number.precision =
|
2894
|
+
Sass::Script::Number.precision = old_precision
|
2893
2895
|
end
|
2894
2896
|
end
|
2895
2897
|
|