sass 3.3.14 → 3.4.0.rc.1
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 +4 -4
- data/MIT-LICENSE +1 -1
- data/README.md +5 -5
- data/VERSION +1 -1
- data/VERSION_DATE +1 -1
- data/VERSION_NAME +1 -1
- data/bin/sass +1 -1
- data/bin/scss +1 -1
- data/lib/sass.rb +0 -5
- data/lib/sass/css.rb +1 -3
- data/lib/sass/engine.rb +28 -39
- data/lib/sass/environment.rb +13 -17
- data/lib/sass/error.rb +6 -9
- data/lib/sass/exec.rb +5 -771
- data/lib/sass/exec/base.rb +187 -0
- data/lib/sass/exec/sass_convert.rb +264 -0
- data/lib/sass/exec/sass_scss.rb +419 -0
- data/lib/sass/features.rb +6 -0
- data/lib/sass/importers.rb +0 -1
- data/lib/sass/importers/base.rb +5 -1
- data/lib/sass/importers/filesystem.rb +4 -21
- data/lib/sass/media.rb +1 -4
- data/lib/sass/plugin/compiler.rb +32 -136
- data/lib/sass/script/css_lexer.rb +1 -1
- data/lib/sass/script/functions.rb +363 -39
- data/lib/sass/script/lexer.rb +68 -50
- data/lib/sass/script/parser.rb +29 -14
- data/lib/sass/script/tree.rb +1 -0
- data/lib/sass/script/tree/funcall.rb +1 -1
- data/lib/sass/script/tree/interpolation.rb +19 -1
- data/lib/sass/script/tree/selector.rb +26 -0
- data/lib/sass/script/value.rb +0 -1
- data/lib/sass/script/value/bool.rb +0 -5
- data/lib/sass/script/value/color.rb +32 -12
- data/lib/sass/script/value/helpers.rb +107 -0
- data/lib/sass/script/value/list.rb +0 -15
- data/lib/sass/script/value/null.rb +0 -5
- data/lib/sass/script/value/number.rb +60 -14
- data/lib/sass/script/value/string.rb +53 -9
- data/lib/sass/scss/css_parser.rb +8 -2
- data/lib/sass/scss/parser.rb +175 -319
- data/lib/sass/scss/rx.rb +14 -5
- data/lib/sass/scss/static_parser.rb +298 -1
- data/lib/sass/selector.rb +56 -193
- data/lib/sass/selector/abstract_sequence.rb +28 -13
- data/lib/sass/selector/comma_sequence.rb +91 -12
- data/lib/sass/selector/pseudo.rb +256 -0
- data/lib/sass/selector/sequence.rb +99 -31
- data/lib/sass/selector/simple.rb +14 -25
- data/lib/sass/selector/simple_sequence.rb +101 -37
- data/lib/sass/shared.rb +1 -1
- data/lib/sass/source/map.rb +23 -9
- data/lib/sass/stack.rb +0 -6
- data/lib/sass/supports.rb +1 -1
- data/lib/sass/tree/at_root_node.rb +1 -0
- data/lib/sass/tree/directive_node.rb +7 -1
- data/lib/sass/tree/error_node.rb +18 -0
- data/lib/sass/tree/keyframe_rule_node.rb +15 -0
- data/lib/sass/tree/prop_node.rb +1 -1
- data/lib/sass/tree/rule_node.rb +11 -6
- data/lib/sass/tree/visitors/check_nesting.rb +3 -4
- data/lib/sass/tree/visitors/convert.rb +8 -17
- data/lib/sass/tree/visitors/cssize.rb +12 -24
- data/lib/sass/tree/visitors/deep_copy.rb +5 -0
- data/lib/sass/tree/visitors/perform.rb +43 -28
- data/lib/sass/tree/visitors/set_options.rb +5 -0
- data/lib/sass/tree/visitors/to_css.rb +14 -13
- data/lib/sass/util.rb +94 -90
- data/test/sass/cache_test.rb +1 -1
- data/test/sass/callbacks_test.rb +1 -1
- data/test/sass/compiler_test.rb +5 -14
- data/test/sass/conversion_test.rb +47 -1
- data/test/sass/css2sass_test.rb +3 -3
- data/test/sass/encoding_test.rb +219 -0
- data/test/sass/engine_test.rb +128 -191
- data/test/sass/exec_test.rb +2 -2
- data/test/sass/extend_test.rb +234 -17
- data/test/sass/functions_test.rb +268 -213
- data/test/sass/importer_test.rb +31 -21
- data/test/sass/logger_test.rb +1 -1
- data/test/sass/more_results/more_import.css +1 -1
- data/test/sass/plugin_test.rb +12 -11
- data/test/sass/results/compact.css +1 -1
- data/test/sass/results/complex.css +4 -4
- data/test/sass/results/expanded.css +1 -1
- data/test/sass/results/import.css +1 -1
- data/test/sass/results/import_charset_ibm866.css +2 -2
- data/test/sass/results/mixins.css +17 -17
- data/test/sass/results/nested.css +1 -1
- data/test/sass/results/parent_ref.css +2 -2
- data/test/sass/results/script.css +3 -3
- data/test/sass/results/scss_import.css +1 -1
- data/test/sass/script_conversion_test.rb +7 -4
- data/test/sass/script_test.rb +202 -79
- data/test/sass/scss/css_test.rb +95 -25
- data/test/sass/scss/rx_test.rb +4 -4
- data/test/sass/scss/scss_test.rb +363 -19
- data/test/sass/source_map_test.rb +48 -41
- data/test/sass/superselector_test.rb +191 -0
- data/test/sass/templates/scss_import.scss +2 -1
- data/test/sass/test_helper.rb +1 -1
- data/test/sass/util/multibyte_string_scanner_test.rb +1 -1
- data/test/sass/util/normalized_map_test.rb +1 -1
- data/test/sass/util/subset_map_test.rb +2 -2
- data/test/sass/util_test.rb +1 -1
- data/test/sass/value_helpers_test.rb +3 -3
- data/test/test_helper.rb +2 -2
- metadata +30 -7
- data/lib/sass/importers/deprecated_path.rb +0 -51
- data/lib/sass/script/value/deprecated_false.rb +0 -55
data/test/sass/importer_test.rb
CHANGED
@@ -4,7 +4,7 @@ require File.dirname(__FILE__) + '/test_helper'
|
|
4
4
|
require 'mock_importer'
|
5
5
|
require 'sass/plugin'
|
6
6
|
|
7
|
-
class ImporterTest < Test
|
7
|
+
class ImporterTest < MiniTest::Test
|
8
8
|
|
9
9
|
class FruitImporter < Sass::Importers::Base
|
10
10
|
def find(name, context = nil)
|
@@ -225,11 +225,11 @@ SCSS
|
|
225
225
|
JSON
|
226
226
|
end
|
227
227
|
|
228
|
-
def
|
228
|
+
def test_source_map_with_only_css_uri_can_have_no_public_url
|
229
229
|
ephemeral_importer = NoPublicUrlImporter.new
|
230
230
|
mock_importer = MockImporter.new
|
231
231
|
def mock_importer.public_url(name, sourcemap_directory = nil)
|
232
|
-
"
|
232
|
+
"source_uri"
|
233
233
|
end
|
234
234
|
|
235
235
|
options = {
|
@@ -248,28 +248,26 @@ JSON
|
|
248
248
|
}
|
249
249
|
SCSS
|
250
250
|
|
251
|
-
|
252
|
-
|
253
|
-
assert_equal <<CSS.strip, css_output.strip
|
251
|
+
css_output, sourcemap = engine.render_with_sourcemap('sourcemap_uri')
|
252
|
+
assert_equal <<CSS.strip, css_output.strip
|
254
253
|
.orange {
|
255
254
|
color: orange; }
|
256
255
|
|
257
256
|
/*# sourceMappingURL=sourcemap_uri */
|
258
257
|
CSS
|
259
|
-
|
260
|
-
|
258
|
+
map = sourcemap.to_json(:css_uri => 'css_uri')
|
259
|
+
assert_equal <<JSON.strip, map
|
261
260
|
{
|
262
261
|
"version": 3,
|
263
262
|
"mappings": "AACA,OAAQ",
|
264
|
-
"sources": ["
|
263
|
+
"sources": ["source_uri"],
|
265
264
|
"names": [],
|
266
265
|
"file": "css_uri"
|
267
266
|
}
|
268
267
|
JSON
|
269
|
-
end
|
270
268
|
end
|
271
269
|
|
272
|
-
def
|
270
|
+
def test_source_map_with_only_css_uri_falls_back_to_file_uris
|
273
271
|
file_system_importer = Sass::Importers::Filesystem.new('.')
|
274
272
|
options = {
|
275
273
|
:filename => filename_for_test(:scss),
|
@@ -284,13 +282,19 @@ SCSS
|
|
284
282
|
|
285
283
|
_, sourcemap = engine.render_with_sourcemap('http://1.example.com/style.map')
|
286
284
|
|
287
|
-
|
288
|
-
|
289
|
-
|
290
|
-
|
285
|
+
uri = Sass::Util.file_uri_from_path(Sass::Util.absolute_path(filename_for_test(:scss)))
|
286
|
+
assert_equal <<JSON.strip, sourcemap.to_json(:css_uri => 'css_uri')
|
287
|
+
{
|
288
|
+
"version": 3,
|
289
|
+
"mappings": "AAAA,IAAK;EAAC,CAAC,EAAE,CAAC",
|
290
|
+
"sources": ["#{uri}"],
|
291
|
+
"names": [],
|
292
|
+
"file": "css_uri"
|
293
|
+
}
|
294
|
+
JSON
|
291
295
|
end
|
292
296
|
|
293
|
-
def
|
297
|
+
def test_source_map_with_css_uri_and_css_path_falls_back_to_file_uris
|
294
298
|
file_system_importer = Sass::Importers::Filesystem.new('.')
|
295
299
|
options = {
|
296
300
|
:filename => filename_for_test(:scss),
|
@@ -305,10 +309,16 @@ SCSS
|
|
305
309
|
|
306
310
|
_, sourcemap = engine.render_with_sourcemap('http://1.example.com/style.map')
|
307
311
|
|
308
|
-
|
309
|
-
|
310
|
-
|
311
|
-
|
312
|
+
uri = Sass::Util.file_uri_from_path(Sass::Util.absolute_path(filename_for_test(:scss)))
|
313
|
+
assert_equal <<JSON.strip, sourcemap.to_json(:css_uri => 'css_uri', :css_path => 'css_path')
|
314
|
+
{
|
315
|
+
"version": 3,
|
316
|
+
"mappings": "AAAA,IAAK;EAAC,CAAC,EAAE,CAAC",
|
317
|
+
"sources": ["#{uri}"],
|
318
|
+
"names": [],
|
319
|
+
"file": "css_uri"
|
320
|
+
}
|
321
|
+
JSON
|
312
322
|
end
|
313
323
|
|
314
324
|
def test_source_map_with_css_uri_and_sourcemap_path_supports_filesystem_importer
|
@@ -397,6 +407,6 @@ MESSAGE
|
|
397
407
|
|
398
408
|
def test_absolute_files_across_template_locations
|
399
409
|
importer = Sass::Importers::Filesystem.new(absolutize 'templates')
|
400
|
-
|
410
|
+
refute_nil importer.mtime(absolutize('more_templates/more1.sass'), {})
|
401
411
|
end
|
402
412
|
end
|
data/test/sass/logger_test.rb
CHANGED
@@ -24,6 +24,6 @@ body { font: Arial; background: blue; }
|
|
24
24
|
#content.user.show #container.top #column.right { width: 600px; }
|
25
25
|
#content.user.show #container.bottom { background: brown; }
|
26
26
|
|
27
|
-
#foo { background-color: #
|
27
|
+
#foo { background-color: #baf; }
|
28
28
|
|
29
29
|
nonimported { myconst: hello; otherconst: goodbye; post-mixin: here; }
|
data/test/sass/plugin_test.rb
CHANGED
@@ -17,7 +17,7 @@ module Sass::Script::Functions
|
|
17
17
|
end
|
18
18
|
end
|
19
19
|
|
20
|
-
class SassPluginTest < Test
|
20
|
+
class SassPluginTest < MiniTest::Test
|
21
21
|
@@templates = %w{
|
22
22
|
complex script parent_ref import scss_import alt
|
23
23
|
subdir/subdir subdir/nested_subdir/nested_subdir
|
@@ -113,7 +113,7 @@ class SassPluginTest < Test::Unit::TestCase
|
|
113
113
|
File.open(tempfile_loc('bork1')) do |file|
|
114
114
|
assert_equal(<<CSS.strip, file.read.split("\n")[0...6].join("\n"))
|
115
115
|
/*
|
116
|
-
|
116
|
+
Error: Undefined variable: "$bork".
|
117
117
|
on line 2 of #{template_loc('bork1')}
|
118
118
|
|
119
119
|
1: bork
|
@@ -129,7 +129,7 @@ CSS
|
|
129
129
|
File.open(tempfile_loc('bork5')) do |file|
|
130
130
|
assert_equal(<<CSS.strip, file.read.split("\n")[0...7].join("\n"))
|
131
131
|
/*
|
132
|
-
|
132
|
+
Error: Undefined variable: "$bork".
|
133
133
|
on line 3 of #{template_loc('bork5')}
|
134
134
|
|
135
135
|
1: bork
|
@@ -146,7 +146,7 @@ CSS
|
|
146
146
|
File.open(tempfile_loc('single_import_loop')) do |file|
|
147
147
|
assert_equal(<<CSS.strip, file.read.split("\n")[0...2].join("\n"))
|
148
148
|
/*
|
149
|
-
|
149
|
+
Error: An @import loop has been found: #{template_loc('single_import_loop')} imports itself
|
150
150
|
CSS
|
151
151
|
end
|
152
152
|
end
|
@@ -157,9 +157,9 @@ CSS
|
|
157
157
|
File.open(tempfile_loc('double_import_loop1')) do |file|
|
158
158
|
assert_equal(<<CSS.strip, file.read.split("\n")[0...4].join("\n"))
|
159
159
|
/*
|
160
|
-
|
161
|
-
|
162
|
-
|
160
|
+
Error: An @import loop has been found:
|
161
|
+
#{template_loc('double_import_loop1')} imports #{template_loc('_double_import_loop2')}
|
162
|
+
#{template_loc('_double_import_loop2')} imports #{template_loc('double_import_loop1')}
|
163
163
|
CSS
|
164
164
|
end
|
165
165
|
end
|
@@ -170,8 +170,8 @@ CSS
|
|
170
170
|
File.open(tempfile_loc('subdir/import_up1')) do |file|
|
171
171
|
assert_equal(<<CSS.strip, file.read.split("\n")[0...5].join("\n"))
|
172
172
|
/*
|
173
|
-
|
174
|
-
|
173
|
+
Error: File to import not found or unreadable: ../subdir/import_up3.scss.
|
174
|
+
Load path: #{template_loc}
|
175
175
|
on line 1 of #{template_loc 'subdir/import_up2'}
|
176
176
|
from line 1 of #{template_loc 'subdir/import_up1'}
|
177
177
|
CSS
|
@@ -183,7 +183,7 @@ CSS
|
|
183
183
|
Sass::Plugin.options[:full_exception] = false
|
184
184
|
|
185
185
|
File.delete(tempfile_loc('bork1'))
|
186
|
-
|
186
|
+
assert_raises(Sass::SyntaxError) {check_for_updates!}
|
187
187
|
ensure
|
188
188
|
Sass::Plugin.options[:full_exception] = old_full_exception
|
189
189
|
end
|
@@ -537,7 +537,8 @@ WARNING
|
|
537
537
|
:always_update => true,
|
538
538
|
:never_update => false,
|
539
539
|
:full_exception => true,
|
540
|
-
:cache_store => @@cache_store
|
540
|
+
:cache_store => @@cache_store,
|
541
|
+
:sourcemap => :none
|
541
542
|
)
|
542
543
|
Sass::Plugin.options.merge!(overrides)
|
543
544
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
body { margin: 0; font: 0.85em "Lucida Grande", "Trebuchet MS", Verdana, sans-serif; color:
|
1
|
+
body { margin: 0; font: 0.85em "Lucida Grande", "Trebuchet MS", Verdana, sans-serif; color: #fff; background: url(/images/global_bg.gif); }
|
2
2
|
|
3
3
|
#page { width: 900px; margin: 0 auto; background: #440008; border-top-width: 5px; border-top-style: solid; border-top-color: #ff8500; }
|
4
4
|
|
@@ -16,8 +16,8 @@ body { margin: 0; font: 0.85em "Lucida Grande", "Trebuchet MS", Verdana, sans-se
|
|
16
16
|
|
17
17
|
#menu { clear: both; text-align: right; height: 20px; border-bottom: 5px solid #006b95; background: #00a4e4; }
|
18
18
|
#menu .contests ul { margin: 0 5px 0 0; padding: 0; }
|
19
|
-
#menu .contests ul li { list-style-type: none; margin: 0 5px; padding: 5px 5px 0 5px; display: inline; font-size: 1.1em; color:
|
20
|
-
#menu .contests a:link, #menu .contests a:visited { color:
|
19
|
+
#menu .contests ul li { list-style-type: none; margin: 0 5px; padding: 5px 5px 0 5px; display: inline; font-size: 1.1em; color: #fff; background: #00a4e4; }
|
20
|
+
#menu .contests a:link, #menu .contests a:visited { color: #fff; text-decoration: none; font-weight: bold; }
|
21
21
|
#menu .contests a:hover { text-decoration: underline; }
|
22
22
|
|
23
23
|
#content { clear: both; }
|
@@ -81,6 +81,6 @@ body { margin: 0; font: 0.85em "Lucida Grande", "Trebuchet MS", Verdana, sans-se
|
|
81
81
|
|
82
82
|
img { border: none; }
|
83
83
|
|
84
|
-
button.short { width: 60px; height: 22px; padding: 0 0 2px 0; color:
|
84
|
+
button.short { width: 60px; height: 22px; padding: 0 0 2px 0; color: #fff; border: none; background: url(/images/btn_short.gif) no-repeat; }
|
85
85
|
|
86
86
|
table { border-collapse: collapse; }
|
@@ -26,6 +26,6 @@ body { font: Arial; background: blue; }
|
|
26
26
|
#content.user.show #container.top #column.right { width: 600px; }
|
27
27
|
#content.user.show #container.bottom { background: brown; }
|
28
28
|
|
29
|
-
#foo { background-color: #
|
29
|
+
#foo { background-color: #baf; }
|
30
30
|
|
31
31
|
nonimported { myconst: hello; otherconst: goodbye; post-mixin: here; }
|
@@ -1,12 +1,12 @@
|
|
1
1
|
#main {
|
2
2
|
width: 15em;
|
3
|
-
color:
|
3
|
+
color: #0000ff;
|
4
4
|
}
|
5
5
|
#main p {
|
6
6
|
border-top-width: 2px;
|
7
|
-
border-top-color: #
|
7
|
+
border-top-color: #fc0;
|
8
8
|
border-left-width: 1px;
|
9
|
-
border-left-color:
|
9
|
+
border-left-color: #000;
|
10
10
|
-moz-border-radius: 10px;
|
11
11
|
border-style: dotted;
|
12
12
|
border-width: 2px;
|
@@ -17,9 +17,9 @@
|
|
17
17
|
|
18
18
|
#left {
|
19
19
|
border-top-width: 2px;
|
20
|
-
border-top-color: #
|
20
|
+
border-top-color: #fc0;
|
21
21
|
border-left-width: 1px;
|
22
|
-
border-left-color:
|
22
|
+
border-left-color: #000;
|
23
23
|
-moz-border-radius: 10px;
|
24
24
|
font-size: 2em;
|
25
25
|
font-weight: bold;
|
@@ -28,25 +28,25 @@
|
|
28
28
|
|
29
29
|
#right {
|
30
30
|
border-top-width: 2px;
|
31
|
-
border-top-color: #
|
31
|
+
border-top-color: #fc0;
|
32
32
|
border-left-width: 1px;
|
33
|
-
border-left-color:
|
33
|
+
border-left-color: #000;
|
34
34
|
-moz-border-radius: 10px;
|
35
|
-
color:
|
35
|
+
color: #f00;
|
36
36
|
font-size: 20px;
|
37
37
|
float: right;
|
38
38
|
}
|
39
39
|
|
40
40
|
.bordered {
|
41
41
|
border-top-width: 2px;
|
42
|
-
border-top-color: #
|
42
|
+
border-top-color: #fc0;
|
43
43
|
border-left-width: 1px;
|
44
|
-
border-left-color:
|
44
|
+
border-left-color: #000;
|
45
45
|
-moz-border-radius: 10px;
|
46
46
|
}
|
47
47
|
|
48
48
|
.complex {
|
49
|
-
color:
|
49
|
+
color: #f00;
|
50
50
|
font-size: 20px;
|
51
51
|
text-decoration: none;
|
52
52
|
}
|
@@ -59,12 +59,12 @@
|
|
59
59
|
}
|
60
60
|
* html .complex {
|
61
61
|
height: 1px;
|
62
|
-
color:
|
62
|
+
color: #f00;
|
63
63
|
font-size: 20px;
|
64
64
|
}
|
65
65
|
|
66
66
|
.more-complex {
|
67
|
-
color:
|
67
|
+
color: #f00;
|
68
68
|
font-size: 20px;
|
69
69
|
text-decoration: none;
|
70
70
|
display: inline;
|
@@ -80,16 +80,16 @@
|
|
80
80
|
}
|
81
81
|
* html .more-complex {
|
82
82
|
height: 1px;
|
83
|
-
color:
|
83
|
+
color: #f00;
|
84
84
|
font-size: 20px;
|
85
85
|
}
|
86
86
|
.more-complex a:hover {
|
87
87
|
text-decoration: underline;
|
88
|
-
color:
|
88
|
+
color: #f00;
|
89
89
|
font-size: 20px;
|
90
90
|
border-top-width: 2px;
|
91
|
-
border-top-color: #
|
91
|
+
border-top-color: #fc0;
|
92
92
|
border-left-width: 1px;
|
93
|
-
border-left-color:
|
93
|
+
border-left-color: #000;
|
94
94
|
-moz-border-radius: 10px;
|
95
95
|
}
|
@@ -1,7 +1,7 @@
|
|
1
|
-
#main { content: Hello\!; qstr: 'Quo"ted"!'; hstr: Hyph-en\!; width: 30em; background-color:
|
2
|
-
#main #sidebar { background-color: #00ff98; num-normal: 10; num-dec: 10.2; num-dec0: 99; num-neg: -10; esc: 10
|
1
|
+
#main { content: Hello\!; qstr: 'Quo"ted"!'; hstr: Hyph-en\!; width: 30em; background-color: #000; color: #ffa; short-color: #123; named-color: olive; con: "foo" bar 9 hi there "boom"; con2: "noquo" quo; }
|
2
|
+
#main #sidebar { background-color: #00ff98; num-normal: 10; num-dec: 10.2; num-dec0: 99; num-neg: -10; esc: 10\+12; many: 6; order: 7; complex: #4c9db1hi16; }
|
3
3
|
|
4
|
-
#plus { num-num: 7; num-num-un: 25em; num-num-un2: 23em; num-num-neg: 9.87; num-str: 100px; num-col: #b7b7b7; num-perc: 31%; str-str: "hi
|
4
|
+
#plus { num-num: 7; num-num-un: 25em; num-num-un2: 23em; num-num-neg: 9.87; num-str: 100px; num-col: #b7b7b7; num-perc: 31%; str-str: "hi there"; str-str2: "hi there"; str-col: "14em solid #123"; str-num: "times: 13"; col-num: #ff7b9d; col-col: #5173ff; }
|
5
5
|
|
6
6
|
#minus { num-num: 900; col-num: #f9f9f4; col-col: #000035; unary-num: -1; unary-const: 10; unary-paren: -11; unary-two: 12; unary-many: 12; unary-crazy: -15; }
|
7
7
|
|
@@ -26,6 +26,6 @@ body { font: Arial; background: blue; }
|
|
26
26
|
#content.user.show #container.top #column.right { width: 600px; }
|
27
27
|
#content.user.show #container.bottom { background: brown; }
|
28
28
|
|
29
|
-
#foo { background-color: #
|
29
|
+
#foo { background-color: #baf; }
|
30
30
|
|
31
31
|
nonimported { myconst: hello; otherconst: goodbye; post-mixin: here; }
|
@@ -3,7 +3,7 @@
|
|
3
3
|
require File.dirname(__FILE__) + '/../test_helper'
|
4
4
|
require 'sass/engine'
|
5
5
|
|
6
|
-
class SassScriptConversionTest < Test
|
6
|
+
class SassScriptConversionTest < MiniTest::Test
|
7
7
|
def test_bool
|
8
8
|
assert_renders "true"
|
9
9
|
assert_renders "false"
|
@@ -13,9 +13,8 @@ class SassScriptConversionTest < Test::Unit::TestCase
|
|
13
13
|
assert_renders "#abcdef"
|
14
14
|
assert_renders "blue"
|
15
15
|
assert_renders "rgba(0, 1, 2, 0.2)"
|
16
|
-
|
17
|
-
|
18
|
-
assert_equal "blue", render("#0000ff")
|
16
|
+
assert_renders "#abc"
|
17
|
+
assert_renders "#0000ff"
|
19
18
|
end
|
20
19
|
|
21
20
|
def test_number
|
@@ -109,6 +108,10 @@ class SassScriptConversionTest < Test::Unit::TestCase
|
|
109
108
|
assert_renders "(foo: (bar, baz), bip: bop)"
|
110
109
|
end
|
111
110
|
|
111
|
+
def test_selector
|
112
|
+
assert_renders "&"
|
113
|
+
end
|
114
|
+
|
112
115
|
def self.test_precedence(outer, inner)
|
113
116
|
op_outer = Sass::Script::Lexer::OPERATORS_REVERSE[outer]
|
114
117
|
op_inner = Sass::Script::Lexer::OPERATORS_REVERSE[inner]
|
data/test/sass/script_test.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
|
+
# -*- coding: utf-8 -*-
|
2
3
|
require File.dirname(__FILE__) + '/../test_helper'
|
3
4
|
require 'sass/engine'
|
4
5
|
|
@@ -17,7 +18,7 @@ module Sass::Script::Functions
|
|
17
18
|
include Sass::Script::Functions::UserFunctions
|
18
19
|
end
|
19
20
|
|
20
|
-
class SassScriptTest < Test
|
21
|
+
class SassScriptTest < MiniTest::Test
|
21
22
|
include Sass::Script
|
22
23
|
|
23
24
|
def test_color_checks_input
|
@@ -33,18 +34,43 @@ class SassScriptTest < Test::Unit::TestCase
|
|
33
34
|
def test_string_escapes
|
34
35
|
assert_equal "'", resolve("\"'\"")
|
35
36
|
assert_equal '"', resolve("\"\\\"\"")
|
36
|
-
assert_equal "
|
37
|
-
assert_equal "
|
38
|
-
|
39
|
-
assert_equal "
|
40
|
-
assert_equal
|
41
|
-
|
42
|
-
|
37
|
+
assert_equal "\\", resolve("\"\\\\\"")
|
38
|
+
assert_equal "☃", resolve("\"\\2603\"")
|
39
|
+
assert_equal "☃f", resolve("\"\\2603 f\"")
|
40
|
+
assert_equal "☃x", resolve("\"\\2603x\"")
|
41
|
+
assert_equal "\\2603", resolve("\"\\\\2603\"")
|
42
|
+
|
43
|
+
# U+FFFD is the replacement character, "�".
|
44
|
+
assert_equal [0xFFFD].pack("U"), resolve("\"\\0\"")
|
45
|
+
assert_equal [0xFFFD].pack("U"), resolve("\"\\FFFFFF\"")
|
46
|
+
assert_equal [0xFFFD].pack("U"), resolve("\"\\D800\"")
|
47
|
+
assert_equal [0xD7FF].pack("U"), resolve("\"\\D7FF\"")
|
48
|
+
assert_equal [0xFFFD].pack("U"), resolve("\"\\DFFF\"")
|
49
|
+
assert_equal [0xE000].pack("U"), resolve("\"\\E000\"")
|
50
|
+
end
|
51
|
+
|
52
|
+
def test_string_escapes_are_resolved_before_operators
|
53
|
+
assert_equal "true", resolve('"abc" == "\61\62\63"')
|
54
|
+
end
|
55
|
+
|
56
|
+
def test_string_quote
|
57
|
+
assert_equal '"foo"', resolve_quoted('"foo"')
|
58
|
+
assert_equal "'f\"oo'", resolve_quoted('"f\"oo"')
|
59
|
+
assert_equal "\"f'oo\"", resolve_quoted("'f\\'oo'")
|
60
|
+
assert_equal "\"f'o\\\"o\"", resolve_quoted("'f\\'o\"o'")
|
61
|
+
assert_equal '"foo bar"', resolve_quoted('"foo\20 bar"')
|
62
|
+
assert_equal '"foo\a bar"', resolve_quoted('"foo\a bar"')
|
63
|
+
assert_equal '"x\ay"', resolve_quoted('"x\a y"')
|
64
|
+
assert_equal '"\a "', resolve_quoted('"\a\20"')
|
65
|
+
assert_equal '"\a abcdef"', resolve_quoted('"\a abcdef"')
|
66
|
+
assert_equal '"☃abcdef"', resolve_quoted('"\2603 abcdef"')
|
67
|
+
assert_equal '"\\\\"', resolve_quoted('"\\\\"')
|
68
|
+
assert_equal '"foobar"', resolve_quoted("\"foo\\\nbar\"")
|
43
69
|
end
|
44
70
|
|
45
71
|
def test_color_names
|
46
72
|
assert_equal "white", resolve("white")
|
47
|
-
assert_equal "
|
73
|
+
assert_equal "#ffffff", resolve("#ffffff")
|
48
74
|
assert_equal "#fffffe", resolve("white - #000001")
|
49
75
|
assert_equal "transparent", resolve("transparent")
|
50
76
|
assert_equal "transparent", resolve("rgba(0, 0, 0, 0)")
|
@@ -93,7 +119,7 @@ class SassScriptTest < Test::Unit::TestCase
|
|
93
119
|
assert_equal "#123", resolve("#112233", :style => :compressed)
|
94
120
|
assert_equal "#000", resolve("black", :style => :compressed)
|
95
121
|
assert_equal "red", resolve("#f00", :style => :compressed)
|
96
|
-
assert_equal "blue", resolve("
|
122
|
+
assert_equal "blue", resolve("blue", :style => :compressed)
|
97
123
|
assert_equal "navy", resolve("#000080", :style => :compressed)
|
98
124
|
assert_equal "navy #fff", resolve("#000080 white", :style => :compressed)
|
99
125
|
assert_equal "This color is #fff", resolve('"This color is #{ white }"', :style => :compressed)
|
@@ -255,8 +281,8 @@ SASS
|
|
255
281
|
assert_equal eval('1 2 3.0'), eval('1 2 3')
|
256
282
|
assert_equal eval('1, 2, 3.0'), eval('1, 2, 3')
|
257
283
|
assert_equal eval('(1 2), (3, 4), (5 6)'), eval('(1 2), (3, 4), (5 6)')
|
258
|
-
|
259
|
-
|
284
|
+
refute_equal eval('1, 2, 3'), eval('1 2 3')
|
285
|
+
refute_equal eval('1'), eval('"1"')
|
260
286
|
end
|
261
287
|
|
262
288
|
def test_booleans
|
@@ -430,6 +456,36 @@ SASS
|
|
430
456
|
assert_equal "true", resolve("1.1cm == 11mm")
|
431
457
|
end
|
432
458
|
|
459
|
+
def test_length_units
|
460
|
+
assert_equal "2.54", resolve("(1in/1cm)")
|
461
|
+
assert_equal "2.3622", resolve("(1cm/1pc)")
|
462
|
+
assert_equal "4.23333", resolve("(1pc/1mm)")
|
463
|
+
assert_equal "2.83465", resolve("(1mm/1pt)")
|
464
|
+
assert_equal "1.33333", resolve("(1pt/1px)")
|
465
|
+
assert_equal "0.01042", resolve("(1px/1in)")
|
466
|
+
end
|
467
|
+
|
468
|
+
def test_angle_units
|
469
|
+
assert_equal "1.11111", resolve("(1deg/1grad)")
|
470
|
+
assert_equal "0.01571", resolve("(1grad/1rad)")
|
471
|
+
assert_equal "0.15915", resolve("(1rad/1turn)")
|
472
|
+
assert_equal "360", resolve("(1turn/1deg)")
|
473
|
+
end
|
474
|
+
|
475
|
+
def test_time_units
|
476
|
+
assert_equal "1000", resolve("(1s/1ms)")
|
477
|
+
end
|
478
|
+
|
479
|
+
def test_frequency_units
|
480
|
+
assert_equal "0.001", resolve("(1Hz/1kHz)")
|
481
|
+
end
|
482
|
+
|
483
|
+
def test_resolution_units
|
484
|
+
assert_equal "2.54", resolve("(1dpi/1dpcm)")
|
485
|
+
assert_equal "37.79528", resolve("(1dpcm/1dppx)")
|
486
|
+
assert_equal "0.01042", resolve("(1dppx/1dpi)")
|
487
|
+
end
|
488
|
+
|
433
489
|
def test_operations_have_options
|
434
490
|
assert_equal "Options defined!", resolve("assert_options(1 + 1)")
|
435
491
|
assert_equal "Options defined!", resolve("assert_options('bar' + 'baz')")
|
@@ -462,22 +518,22 @@ SASS
|
|
462
518
|
assert_equal "0.5", resolve("$var", {}, env("var" => eval("1px/2px")))
|
463
519
|
end
|
464
520
|
|
465
|
-
def
|
466
|
-
assert_raise_message(Sass::SyntaxError,
|
467
|
-
"Colors must have either three or six digits: '#0'") {eval("#0")}
|
521
|
+
def test_non_ident_colors_with_wrong_number_of_digits
|
468
522
|
assert_raise_message(Sass::SyntaxError,
|
469
|
-
"
|
523
|
+
'Invalid CSS after "": expected expression (e.g. 1px, bold), was "#1"') {eval("#1")}
|
470
524
|
assert_raise_message(Sass::SyntaxError,
|
471
|
-
"
|
525
|
+
'Invalid CSS after "": expected expression (e.g. 1px, bold), was "#12"') {eval("#12")}
|
472
526
|
assert_raise_message(Sass::SyntaxError,
|
473
|
-
"
|
527
|
+
'Invalid CSS after "": expected expression (e.g. 1px, bold), was "#1234"') {eval("#1234")}
|
474
528
|
assert_raise_message(Sass::SyntaxError,
|
475
|
-
"
|
529
|
+
'Invalid CSS after "": expected expression (e.g. 1px, bold), was "#12345"') {eval("#12345")}
|
530
|
+
assert_raise_message(Sass::SyntaxError, 'Invalid CSS after "": expected expression (e.g. ' \
|
531
|
+
'1px, bold), was "#1234567"') {eval("#1234567")}
|
476
532
|
end
|
477
533
|
|
478
534
|
def test_case_insensitive_color_names
|
479
|
-
assert_equal "
|
480
|
-
assert_equal "
|
535
|
+
assert_equal "BLUE", resolve("BLUE")
|
536
|
+
assert_equal "rEd", resolve("rEd")
|
481
537
|
assert_equal "#7f4000", resolve("mix(GrEeN, ReD)")
|
482
538
|
end
|
483
539
|
|
@@ -523,7 +579,7 @@ SASS
|
|
523
579
|
assert_raise_message(Sass::SyntaxError, 'Duplicate key 2px in map (2px: bar, 1px + 1px: baz).') do
|
524
580
|
eval("(2px: bar, 1px + 1px: baz)")
|
525
581
|
end
|
526
|
-
assert_raise_message(Sass::SyntaxError, 'Duplicate key #0000ff in map (blue: bar,
|
582
|
+
assert_raise_message(Sass::SyntaxError, 'Duplicate key #0000ff in map (blue: bar, #00f: baz).') do
|
527
583
|
eval("(blue: bar, #00f: baz)")
|
528
584
|
end
|
529
585
|
end
|
@@ -558,7 +614,7 @@ SASS
|
|
558
614
|
return if RUBY_PLATFORM =~ /java/
|
559
615
|
|
560
616
|
# Don't validate the message; it's different on Rubinius.
|
561
|
-
|
617
|
+
assert_raises(ArgumentError) {resolve("arg-error()")}
|
562
618
|
end
|
563
619
|
|
564
620
|
def test_shallow_argument_error_unwrapped
|
@@ -570,49 +626,25 @@ SASS
|
|
570
626
|
assert_equal "true", resolve("$ie or $undef", {}, env('ie' => Sass::Script::Value::Bool.new(true)))
|
571
627
|
end
|
572
628
|
|
573
|
-
def
|
574
|
-
|
575
|
-
|
576
|
-
Assigning to global variable "$var" by default is deprecated.
|
577
|
-
In future versions of Sass, this will create a new local variable.
|
578
|
-
If you want to assign to the global variable, use "$var: x !global" instead.
|
579
|
-
Note that this will be incompatible with Sass 3.2.
|
580
|
-
WARNING
|
581
|
-
.foo {
|
582
|
-
a: x; }
|
583
|
-
|
584
|
-
.bar {
|
585
|
-
b: x; }
|
586
|
-
CSS
|
587
|
-
$var: 1;
|
588
|
-
|
589
|
-
.foo {
|
590
|
-
$var: x;
|
591
|
-
a: $var;
|
592
|
-
}
|
593
|
-
|
594
|
-
.bar {
|
595
|
-
b: $var;
|
596
|
-
}
|
597
|
-
SCSS
|
598
|
-
end
|
629
|
+
def test_selector
|
630
|
+
env = Sass::Environment.new
|
631
|
+
assert_equal "true", resolve("& == null", {}, env)
|
599
632
|
|
600
|
-
|
601
|
-
|
602
|
-
|
603
|
-
|
604
|
-
|
605
|
-
|
606
|
-
|
607
|
-
|
608
|
-
CSS
|
609
|
-
$var: 1;
|
633
|
+
env.selector = selector('.foo.bar .baz.bang, .bip.bop')
|
634
|
+
assert_equal ".foo.bar .baz.bang, .bip.bop", resolve("&", {}, env)
|
635
|
+
assert_equal ".foo.bar .baz.bang", resolve("nth(&, 1)", {}, env)
|
636
|
+
assert_equal ".bip.bop", resolve("nth(&, 2)", {}, env)
|
637
|
+
assert_equal ".foo.bar", resolve("nth(nth(&, 1), 1)", {}, env)
|
638
|
+
assert_equal ".baz.bang", resolve("nth(nth(&, 1), 2)", {}, env)
|
639
|
+
assert_equal ".bip.bop", resolve("nth(nth(&, 2), 1)", {}, env)
|
640
|
+
assert_equal "string", resolve("type-of(nth(nth(&, 1), 1))", {}, env)
|
610
641
|
|
611
|
-
|
612
|
-
|
613
|
-
|
614
|
-
|
615
|
-
|
642
|
+
env.selector = selector('.foo > .bar')
|
643
|
+
assert_equal ".foo > .bar", resolve("&", {}, env)
|
644
|
+
assert_equal ".foo > .bar", resolve("nth(&, 1)", {}, env)
|
645
|
+
assert_equal ".foo", resolve("nth(nth(&, 1), 1)", {}, env)
|
646
|
+
assert_equal ">", resolve("nth(nth(&, 1), 2)", {}, env)
|
647
|
+
assert_equal ".bar", resolve("nth(nth(&, 1), 3)", {}, env)
|
616
648
|
end
|
617
649
|
|
618
650
|
def test_setting_global_variable_globally
|
@@ -637,7 +669,7 @@ $var: 2;
|
|
637
669
|
SCSS
|
638
670
|
end
|
639
671
|
|
640
|
-
def
|
672
|
+
def test_setting_global_variable_locally
|
641
673
|
assert_no_warning {assert_equal(<<CSS, render(<<SCSS, :syntax => :scss))}
|
642
674
|
.bar {
|
643
675
|
a: x;
|
@@ -663,7 +695,7 @@ $var3: 3;
|
|
663
695
|
SCSS
|
664
696
|
end
|
665
697
|
|
666
|
-
def
|
698
|
+
def test_setting_global_variable_locally_with_default
|
667
699
|
assert_equal(<<CSS, render(<<SCSS, :syntax => :scss))
|
668
700
|
.bar {
|
669
701
|
a: 1;
|
@@ -688,21 +720,104 @@ $var1: 1;
|
|
688
720
|
SCSS
|
689
721
|
end
|
690
722
|
|
691
|
-
def
|
692
|
-
|
693
|
-
|
694
|
-
|
695
|
-
|
696
|
-
|
697
|
-
|
698
|
-
|
699
|
-
|
700
|
-
|
723
|
+
def test_setting_local_variable
|
724
|
+
assert_equal(<<CSS, render(<<SCSS, :syntax => :scss))
|
725
|
+
.a {
|
726
|
+
value: inside; }
|
727
|
+
|
728
|
+
.b {
|
729
|
+
value: outside; }
|
730
|
+
CSS
|
731
|
+
$var: outside;
|
732
|
+
|
733
|
+
.a {
|
734
|
+
$var: inside;
|
735
|
+
value: $var;
|
736
|
+
}
|
737
|
+
|
738
|
+
.b {
|
739
|
+
value: $var;
|
740
|
+
}
|
741
|
+
SCSS
|
742
|
+
end
|
743
|
+
|
744
|
+
def test_setting_local_variable_from_inner_scope
|
745
|
+
assert_equal(<<CSS, render(<<SCSS, :syntax => :scss))
|
746
|
+
.a .b {
|
747
|
+
value: inside; }
|
748
|
+
.a .c {
|
749
|
+
value: inside; }
|
750
|
+
CSS
|
751
|
+
.a {
|
752
|
+
$var: outside;
|
753
|
+
|
754
|
+
.b {
|
755
|
+
$var: inside;
|
756
|
+
value: $var;
|
757
|
+
}
|
758
|
+
|
759
|
+
.c {
|
760
|
+
value: $var;
|
761
|
+
}
|
762
|
+
}
|
763
|
+
SCSS
|
764
|
+
end
|
765
|
+
|
766
|
+
def test_color_format_is_preserved_by_default
|
767
|
+
assert_equal "blue", resolve("blue")
|
768
|
+
assert_equal "bLuE", resolve("bLuE")
|
769
|
+
assert_equal "#00f", resolve("#00f")
|
770
|
+
assert_equal "blue #00F", resolve("blue #00F")
|
771
|
+
assert_equal "blue", resolve("nth(blue #00F, 1)")
|
772
|
+
assert_equal "#00F", resolve("nth(blue #00F, 2)")
|
701
773
|
end
|
702
774
|
|
703
|
-
def
|
704
|
-
assert_equal "
|
705
|
-
assert_equal "
|
775
|
+
def test_color_format_isnt_always_preserved_in_compressed_style
|
776
|
+
assert_equal "red", resolve("red", :style => :compressed)
|
777
|
+
assert_equal "red", resolve("#f00", :style => :compressed)
|
778
|
+
assert_equal "red red", resolve("red #f00", :style => :compressed)
|
779
|
+
assert_equal "red", resolve("nth(red #f00, 2)", :style => :compressed)
|
780
|
+
end
|
781
|
+
|
782
|
+
def test_color_format_is_sometimes_preserved_in_compressed_style
|
783
|
+
assert_equal "ReD", resolve("ReD", :style => :compressed)
|
784
|
+
assert_equal "blue", resolve("blue", :style => :compressed)
|
785
|
+
assert_equal "#00f", resolve("#00f", :style => :compressed)
|
786
|
+
end
|
787
|
+
|
788
|
+
def test_color_format_isnt_preserved_when_modified
|
789
|
+
assert_equal "magenta", resolve("#f00 + #00f")
|
790
|
+
end
|
791
|
+
|
792
|
+
def test_ids
|
793
|
+
assert_equal "#foo", resolve("#foo")
|
794
|
+
assert_equal "#abcd", resolve("#abcd")
|
795
|
+
assert_equal "#abc-def", resolve("#abc-def")
|
796
|
+
assert_equal "#abc_def", resolve("#abc_def")
|
797
|
+
assert_equal "#uvw-xyz", resolve("#uvw-xyz")
|
798
|
+
assert_equal "#uvw_xyz", resolve("#uvw_xyz")
|
799
|
+
assert_equal "#uvwxyz", resolve("#uvw + xyz")
|
800
|
+
end
|
801
|
+
|
802
|
+
def test_scientific_notation
|
803
|
+
assert_equal "2000", resolve("2e3")
|
804
|
+
assert_equal "2000", resolve("2E3")
|
805
|
+
assert_equal "2000", resolve("2e+3")
|
806
|
+
assert_equal "2000em", resolve("2e3em")
|
807
|
+
assert_equal "25000000000", resolve("2.5e10")
|
808
|
+
assert_equal "0.1234", resolve("1234e-4")
|
809
|
+
assert_equal "12.34", resolve("1.234e1")
|
810
|
+
end
|
811
|
+
|
812
|
+
def test_identifier_units
|
813
|
+
assert_equal "5-foo", resolve("2-foo + 3-foo")
|
814
|
+
assert_equal "5-foo-", resolve("2-foo- + 3-foo-")
|
815
|
+
assert_equal "5-\\u2603", resolve("2-\\u2603 + 3-\\u2603")
|
816
|
+
end
|
817
|
+
|
818
|
+
def test_backslash_newline_in_string
|
819
|
+
assert_equal 'foobar', resolve("\"foo\\\nbar\"")
|
820
|
+
assert_equal 'foobar', resolve("'foo\\\nbar'")
|
706
821
|
end
|
707
822
|
|
708
823
|
# Regression Tests
|
@@ -714,6 +829,7 @@ SCSS
|
|
714
829
|
|
715
830
|
def test_minus_without_whitespace
|
716
831
|
assert_equal "5px", resolve("15px-10px")
|
832
|
+
assert_equal "5px-", resolve("15px--10px-")
|
717
833
|
end
|
718
834
|
|
719
835
|
def test_minus_preceded_by_comment
|
@@ -833,6 +949,13 @@ SASS
|
|
833
949
|
val.is_a?(Sass::Script::Value::String) ? val.value : val.to_s
|
834
950
|
end
|
835
951
|
|
952
|
+
def resolve_quoted(str, opts = {}, environment = env)
|
953
|
+
munge_filename opts
|
954
|
+
val = eval(str, opts, environment)
|
955
|
+
assert_kind_of Sass::Script::Value::Base, val
|
956
|
+
val.to_s
|
957
|
+
end
|
958
|
+
|
836
959
|
def assert_unquoted(str, opts = {}, environment = env)
|
837
960
|
munge_filename opts
|
838
961
|
val = eval(str, opts, environment)
|