xass 0.1.0 → 0.1.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (252) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +2 -0
  3. data/Gemfile +9 -0
  4. data/Gemfile.lock +39 -0
  5. data/README.md +131 -193
  6. data/lib/initialize.rb +8 -0
  7. data/lib/xass.rb +67 -0
  8. data/spec/secrets.yml +4 -0
  9. data/spec/spec_helper.rb +8 -0
  10. data/spec/test_spec.rb +5 -0
  11. data/template/secrets.yml +2 -0
  12. data/xass.gemspec +15 -0
  13. metadata +53 -294
  14. data/.yardopts +0 -11
  15. data/CONTRIBUTING +0 -3
  16. data/MIT-LICENSE +0 -20
  17. data/Rakefile +0 -349
  18. data/VERSION +0 -1
  19. data/VERSION_NAME +0 -1
  20. data/bin/push +0 -13
  21. data/bin/sass +0 -13
  22. data/bin/sass-convert +0 -12
  23. data/bin/scss +0 -13
  24. data/extra/update_watch.rb +0 -13
  25. data/init.rb +0 -18
  26. data/lib/sass/cache_stores/base.rb +0 -88
  27. data/lib/sass/cache_stores/chain.rb +0 -33
  28. data/lib/sass/cache_stores/filesystem.rb +0 -64
  29. data/lib/sass/cache_stores/memory.rb +0 -47
  30. data/lib/sass/cache_stores/null.rb +0 -25
  31. data/lib/sass/cache_stores.rb +0 -15
  32. data/lib/sass/callbacks.rb +0 -66
  33. data/lib/sass/css.rb +0 -409
  34. data/lib/sass/engine.rb +0 -930
  35. data/lib/sass/environment.rb +0 -101
  36. data/lib/sass/error.rb +0 -201
  37. data/lib/sass/exec.rb +0 -707
  38. data/lib/sass/importers/base.rb +0 -139
  39. data/lib/sass/importers/filesystem.rb +0 -186
  40. data/lib/sass/importers.rb +0 -22
  41. data/lib/sass/logger/base.rb +0 -32
  42. data/lib/sass/logger/log_level.rb +0 -49
  43. data/lib/sass/logger.rb +0 -15
  44. data/lib/sass/media.rb +0 -213
  45. data/lib/sass/plugin/compiler.rb +0 -406
  46. data/lib/sass/plugin/configuration.rb +0 -123
  47. data/lib/sass/plugin/generic.rb +0 -15
  48. data/lib/sass/plugin/merb.rb +0 -48
  49. data/lib/sass/plugin/rack.rb +0 -60
  50. data/lib/sass/plugin/rails.rb +0 -47
  51. data/lib/sass/plugin/staleness_checker.rb +0 -199
  52. data/lib/sass/plugin.rb +0 -133
  53. data/lib/sass/railtie.rb +0 -10
  54. data/lib/sass/repl.rb +0 -57
  55. data/lib/sass/root.rb +0 -7
  56. data/lib/sass/script/arg_list.rb +0 -52
  57. data/lib/sass/script/bool.rb +0 -18
  58. data/lib/sass/script/color.rb +0 -606
  59. data/lib/sass/script/css_lexer.rb +0 -29
  60. data/lib/sass/script/css_parser.rb +0 -31
  61. data/lib/sass/script/funcall.rb +0 -245
  62. data/lib/sass/script/functions.rb +0 -1543
  63. data/lib/sass/script/interpolation.rb +0 -79
  64. data/lib/sass/script/lexer.rb +0 -345
  65. data/lib/sass/script/list.rb +0 -85
  66. data/lib/sass/script/literal.rb +0 -221
  67. data/lib/sass/script/node.rb +0 -99
  68. data/lib/sass/script/null.rb +0 -37
  69. data/lib/sass/script/number.rb +0 -453
  70. data/lib/sass/script/operation.rb +0 -110
  71. data/lib/sass/script/parser.rb +0 -502
  72. data/lib/sass/script/string.rb +0 -51
  73. data/lib/sass/script/string_interpolation.rb +0 -103
  74. data/lib/sass/script/unary_operation.rb +0 -69
  75. data/lib/sass/script/variable.rb +0 -58
  76. data/lib/sass/script.rb +0 -39
  77. data/lib/sass/scss/css_parser.rb +0 -36
  78. data/lib/sass/scss/parser.rb +0 -1180
  79. data/lib/sass/scss/rx.rb +0 -133
  80. data/lib/sass/scss/script_lexer.rb +0 -15
  81. data/lib/sass/scss/script_parser.rb +0 -25
  82. data/lib/sass/scss/static_parser.rb +0 -54
  83. data/lib/sass/scss.rb +0 -16
  84. data/lib/sass/selector/abstract_sequence.rb +0 -94
  85. data/lib/sass/selector/comma_sequence.rb +0 -92
  86. data/lib/sass/selector/sequence.rb +0 -507
  87. data/lib/sass/selector/simple.rb +0 -119
  88. data/lib/sass/selector/simple_sequence.rb +0 -215
  89. data/lib/sass/selector.rb +0 -452
  90. data/lib/sass/shared.rb +0 -76
  91. data/lib/sass/supports.rb +0 -229
  92. data/lib/sass/tree/charset_node.rb +0 -22
  93. data/lib/sass/tree/comment_node.rb +0 -82
  94. data/lib/sass/tree/content_node.rb +0 -9
  95. data/lib/sass/tree/css_import_node.rb +0 -60
  96. data/lib/sass/tree/debug_node.rb +0 -18
  97. data/lib/sass/tree/directive_node.rb +0 -42
  98. data/lib/sass/tree/each_node.rb +0 -24
  99. data/lib/sass/tree/extend_node.rb +0 -36
  100. data/lib/sass/tree/for_node.rb +0 -36
  101. data/lib/sass/tree/function_node.rb +0 -34
  102. data/lib/sass/tree/if_node.rb +0 -52
  103. data/lib/sass/tree/import_node.rb +0 -75
  104. data/lib/sass/tree/media_node.rb +0 -58
  105. data/lib/sass/tree/mixin_def_node.rb +0 -38
  106. data/lib/sass/tree/mixin_node.rb +0 -39
  107. data/lib/sass/tree/node.rb +0 -196
  108. data/lib/sass/tree/prop_node.rb +0 -152
  109. data/lib/sass/tree/return_node.rb +0 -18
  110. data/lib/sass/tree/root_node.rb +0 -78
  111. data/lib/sass/tree/rule_node.rb +0 -132
  112. data/lib/sass/tree/supports_node.rb +0 -51
  113. data/lib/sass/tree/trace_node.rb +0 -32
  114. data/lib/sass/tree/variable_node.rb +0 -30
  115. data/lib/sass/tree/visitors/base.rb +0 -75
  116. data/lib/sass/tree/visitors/check_nesting.rb +0 -147
  117. data/lib/sass/tree/visitors/convert.rb +0 -316
  118. data/lib/sass/tree/visitors/cssize.rb +0 -241
  119. data/lib/sass/tree/visitors/deep_copy.rb +0 -102
  120. data/lib/sass/tree/visitors/extend.rb +0 -68
  121. data/lib/sass/tree/visitors/perform.rb +0 -446
  122. data/lib/sass/tree/visitors/set_options.rb +0 -125
  123. data/lib/sass/tree/visitors/to_css.rb +0 -228
  124. data/lib/sass/tree/warn_node.rb +0 -18
  125. data/lib/sass/tree/while_node.rb +0 -18
  126. data/lib/sass/util/multibyte_string_scanner.rb +0 -155
  127. data/lib/sass/util/subset_map.rb +0 -109
  128. data/lib/sass/util/test.rb +0 -10
  129. data/lib/sass/util.rb +0 -948
  130. data/lib/sass/version.rb +0 -126
  131. data/lib/sass.rb +0 -95
  132. data/rails/init.rb +0 -1
  133. data/test/Gemfile +0 -3
  134. data/test/Gemfile.lock +0 -10
  135. data/test/sass/cache_test.rb +0 -89
  136. data/test/sass/callbacks_test.rb +0 -61
  137. data/test/sass/conversion_test.rb +0 -1760
  138. data/test/sass/css2sass_test.rb +0 -458
  139. data/test/sass/data/hsl-rgb.txt +0 -319
  140. data/test/sass/engine_test.rb +0 -3244
  141. data/test/sass/exec_test.rb +0 -86
  142. data/test/sass/extend_test.rb +0 -1482
  143. data/test/sass/fixtures/test_staleness_check_across_importers.css +0 -1
  144. data/test/sass/fixtures/test_staleness_check_across_importers.scss +0 -1
  145. data/test/sass/functions_test.rb +0 -1139
  146. data/test/sass/importer_test.rb +0 -192
  147. data/test/sass/logger_test.rb +0 -58
  148. data/test/sass/mock_importer.rb +0 -49
  149. data/test/sass/more_results/more1.css +0 -9
  150. data/test/sass/more_results/more1_with_line_comments.css +0 -26
  151. data/test/sass/more_results/more_import.css +0 -29
  152. data/test/sass/more_templates/_more_partial.sass +0 -2
  153. data/test/sass/more_templates/more1.sass +0 -23
  154. data/test/sass/more_templates/more_import.sass +0 -11
  155. data/test/sass/plugin_test.rb +0 -564
  156. data/test/sass/results/alt.css +0 -4
  157. data/test/sass/results/basic.css +0 -9
  158. data/test/sass/results/cached_import_option.css +0 -3
  159. data/test/sass/results/compact.css +0 -5
  160. data/test/sass/results/complex.css +0 -86
  161. data/test/sass/results/compressed.css +0 -1
  162. data/test/sass/results/expanded.css +0 -19
  163. data/test/sass/results/filename_fn.css +0 -3
  164. data/test/sass/results/if.css +0 -3
  165. data/test/sass/results/import.css +0 -31
  166. data/test/sass/results/import_charset.css +0 -5
  167. data/test/sass/results/import_charset_1_8.css +0 -5
  168. data/test/sass/results/import_charset_ibm866.css +0 -5
  169. data/test/sass/results/import_content.css +0 -1
  170. data/test/sass/results/line_numbers.css +0 -49
  171. data/test/sass/results/mixins.css +0 -95
  172. data/test/sass/results/multiline.css +0 -24
  173. data/test/sass/results/nested.css +0 -22
  174. data/test/sass/results/options.css +0 -1
  175. data/test/sass/results/parent_ref.css +0 -13
  176. data/test/sass/results/script.css +0 -16
  177. data/test/sass/results/scss_import.css +0 -31
  178. data/test/sass/results/scss_importee.css +0 -2
  179. data/test/sass/results/subdir/nested_subdir/nested_subdir.css +0 -1
  180. data/test/sass/results/subdir/subdir.css +0 -3
  181. data/test/sass/results/units.css +0 -11
  182. data/test/sass/results/warn_imported.css +0 -0
  183. data/test/sass/script_conversion_test.rb +0 -299
  184. data/test/sass/script_test.rb +0 -622
  185. data/test/sass/scss/css_test.rb +0 -1100
  186. data/test/sass/scss/rx_test.rb +0 -156
  187. data/test/sass/scss/scss_test.rb +0 -2106
  188. data/test/sass/scss/test_helper.rb +0 -37
  189. data/test/sass/templates/_cached_import_option_partial.scss +0 -1
  190. data/test/sass/templates/_double_import_loop2.sass +0 -1
  191. data/test/sass/templates/_filename_fn_import.scss +0 -11
  192. data/test/sass/templates/_imported_charset_ibm866.sass +0 -4
  193. data/test/sass/templates/_imported_charset_utf8.sass +0 -4
  194. data/test/sass/templates/_imported_content.sass +0 -3
  195. data/test/sass/templates/_partial.sass +0 -2
  196. data/test/sass/templates/_same_name_different_partiality.scss +0 -1
  197. data/test/sass/templates/alt.sass +0 -16
  198. data/test/sass/templates/basic.sass +0 -23
  199. data/test/sass/templates/bork1.sass +0 -2
  200. data/test/sass/templates/bork2.sass +0 -2
  201. data/test/sass/templates/bork3.sass +0 -2
  202. data/test/sass/templates/bork4.sass +0 -2
  203. data/test/sass/templates/bork5.sass +0 -3
  204. data/test/sass/templates/cached_import_option.scss +0 -3
  205. data/test/sass/templates/compact.sass +0 -17
  206. data/test/sass/templates/complex.sass +0 -305
  207. data/test/sass/templates/compressed.sass +0 -15
  208. data/test/sass/templates/double_import_loop1.sass +0 -1
  209. data/test/sass/templates/expanded.sass +0 -17
  210. data/test/sass/templates/filename_fn.scss +0 -18
  211. data/test/sass/templates/if.sass +0 -11
  212. data/test/sass/templates/import.sass +0 -12
  213. data/test/sass/templates/import_charset.sass +0 -9
  214. data/test/sass/templates/import_charset_1_8.sass +0 -6
  215. data/test/sass/templates/import_charset_ibm866.sass +0 -11
  216. data/test/sass/templates/import_content.sass +0 -4
  217. data/test/sass/templates/importee.less +0 -2
  218. data/test/sass/templates/importee.sass +0 -19
  219. data/test/sass/templates/line_numbers.sass +0 -13
  220. data/test/sass/templates/mixin_bork.sass +0 -5
  221. data/test/sass/templates/mixins.sass +0 -76
  222. data/test/sass/templates/multiline.sass +0 -20
  223. data/test/sass/templates/nested.sass +0 -25
  224. data/test/sass/templates/nested_bork1.sass +0 -2
  225. data/test/sass/templates/nested_bork2.sass +0 -2
  226. data/test/sass/templates/nested_bork3.sass +0 -2
  227. data/test/sass/templates/nested_bork4.sass +0 -2
  228. data/test/sass/templates/nested_import.sass +0 -2
  229. data/test/sass/templates/nested_mixin_bork.sass +0 -6
  230. data/test/sass/templates/options.sass +0 -2
  231. data/test/sass/templates/parent_ref.sass +0 -25
  232. data/test/sass/templates/same_name_different_ext.sass +0 -2
  233. data/test/sass/templates/same_name_different_ext.scss +0 -1
  234. data/test/sass/templates/same_name_different_partiality.scss +0 -1
  235. data/test/sass/templates/script.sass +0 -101
  236. data/test/sass/templates/scss_import.scss +0 -11
  237. data/test/sass/templates/scss_importee.scss +0 -1
  238. data/test/sass/templates/single_import_loop.sass +0 -1
  239. data/test/sass/templates/subdir/import_up1.scss +0 -1
  240. data/test/sass/templates/subdir/import_up2.scss +0 -1
  241. data/test/sass/templates/subdir/nested_subdir/_nested_partial.sass +0 -2
  242. data/test/sass/templates/subdir/nested_subdir/nested_subdir.sass +0 -3
  243. data/test/sass/templates/subdir/subdir.sass +0 -6
  244. data/test/sass/templates/units.sass +0 -11
  245. data/test/sass/templates/warn.sass +0 -3
  246. data/test/sass/templates/warn_imported.sass +0 -4
  247. data/test/sass/test_helper.rb +0 -8
  248. data/test/sass/util/multibyte_string_scanner_test.rb +0 -147
  249. data/test/sass/util/subset_map_test.rb +0 -91
  250. data/test/sass/util_test.rb +0 -382
  251. data/test/test_helper.rb +0 -80
  252. /data/{test/sass/results/warn.css → template/files/.gitkeep} +0 -0
@@ -1,3244 +0,0 @@
1
- #!/usr/bin/env ruby
2
- # -*- coding: utf-8 -*-
3
- require File.dirname(__FILE__) + '/../test_helper'
4
- require File.dirname(__FILE__) + '/test_helper'
5
- require 'sass/engine'
6
- require 'stringio'
7
- require 'mock_importer'
8
- require 'pathname'
9
-
10
- module Sass::Script::Functions::UserFunctions
11
- def option(name)
12
- Sass::Script::String.new(@options[name.value.to_sym].to_s)
13
- end
14
- end
15
-
16
- class SassEngineTest < Test::Unit::TestCase
17
- FAKE_FILE_NAME = __FILE__.gsub(/rb$/,"sass")
18
- # A map of erroneous Sass documents to the error messages they should produce.
19
- # The error messages may be arrays;
20
- # if so, the second element should be the line number that should be reported for the error.
21
- # If this isn't provided, the tests will assume the line number should be the last line of the document.
22
- EXCEPTION_MAP = {
23
- "$a: 1 + " => 'Invalid CSS after "1 +": expected expression (e.g. 1px, bold), was ""',
24
- "$a: 1 + 2 +" => 'Invalid CSS after "1 + 2 +": expected expression (e.g. 1px, bold), was ""',
25
- "$a: 1 + 2 + %" => 'Invalid CSS after "1 + 2 + ": expected expression (e.g. 1px, bold), was "%"',
26
- "$a: foo(\"bar\"" => 'Invalid CSS after "foo("bar"": expected ")", was ""',
27
- "$a: 1 }" => 'Invalid CSS after "1 ": expected expression (e.g. 1px, bold), was "}"',
28
- "$a: 1 }foo\"" => 'Invalid CSS after "1 ": expected expression (e.g. 1px, bold), was "}foo""',
29
- ":" => 'Invalid property: ":".',
30
- ": a" => 'Invalid property: ": a".',
31
- "a\n :b" => <<MSG,
32
- Invalid property: ":b" (no value).
33
- If ":b" should be a selector, use "\\:b" instead.
34
- MSG
35
- "a\n b:" => 'Invalid property: "b:" (no value).',
36
- "a\n :b: c" => 'Invalid property: ":b: c".',
37
- "a\n :b:c d" => 'Invalid property: ":b:c d".',
38
- "a\n :b c;" => 'Invalid CSS after "c": expected expression (e.g. 1px, bold), was ";"',
39
- "a\n b: c;" => 'Invalid CSS after "c": expected expression (e.g. 1px, bold), was ";"',
40
- ".foo ^bar\n a: b" => ['Invalid CSS after ".foo ": expected selector, was "^bar"', 1],
41
- "a\n @extend .foo ^bar" => 'Invalid CSS after ".foo ": expected selector, was "^bar"',
42
- "a\n @extend .foo .bar" => "Can't extend .foo .bar: can't extend nested selectors",
43
- "a\n @extend >" => "Can't extend >: invalid selector",
44
- "a\n @extend &.foo" => "Can't extend &.foo: can't extend parent selectors",
45
- "a: b" => 'Properties are only allowed within rules, directives, mixin includes, or other properties.',
46
- ":a b" => 'Properties are only allowed within rules, directives, mixin includes, or other properties.',
47
- "$" => 'Invalid variable: "$".',
48
- "$a" => 'Invalid variable: "$a".',
49
- "$ a" => 'Invalid variable: "$ a".',
50
- "$a b" => 'Invalid variable: "$a b".',
51
- "$a: 1b + 2c" => "Incompatible units: 'c' and 'b'.",
52
- "$a: 1b < 2c" => "Incompatible units: 'c' and 'b'.",
53
- "$a: 1b > 2c" => "Incompatible units: 'c' and 'b'.",
54
- "$a: 1b <= 2c" => "Incompatible units: 'c' and 'b'.",
55
- "$a: 1b >= 2c" => "Incompatible units: 'c' and 'b'.",
56
- "a\n b: 1b * 2c" => "2b*c isn't a valid CSS value.",
57
- "a\n b: 1b % 2c" => "Cannot modulo by a number with units: 2c.",
58
- "$a: 2px + #ccc" => "Cannot add a number with units (2px) to a color (#cccccc).",
59
- "$a: #ccc + 2px" => "Cannot add a number with units (2px) to a color (#cccccc).",
60
- "& a\n :b c" => ["Base-level rules cannot contain the parent-selector-referencing character '&'.", 1],
61
- "a\n :b\n c" => "Illegal nesting: Only properties may be nested beneath properties.",
62
- "$a: b\n :c d\n" => "Illegal nesting: Nothing may be nested beneath variable declarations.",
63
- "$a: b\n :c d\n" => "Illegal nesting: Nothing may be nested beneath variable declarations.",
64
- "@import templates/basic\n foo" => "Illegal nesting: Nothing may be nested beneath import directives.",
65
- "foo\n @import foo.css" => "CSS import directives may only be used at the root of a document.",
66
- "@if true\n @import foo" => "Import directives may not be used within control directives or mixins.",
67
- "@if true\n .foo\n @import foo" => "Import directives may not be used within control directives or mixins.",
68
- "@mixin foo\n @import foo" => "Import directives may not be used within control directives or mixins.",
69
- "@mixin foo\n .foo\n @import foo" => "Import directives may not be used within control directives or mixins.",
70
- "@import foo;" => "Invalid @import: expected end of line, was \";\".",
71
- '$foo: "bar" "baz" !' => %Q{Invalid CSS after ""bar" "baz" ": expected expression (e.g. 1px, bold), was "!"},
72
- '$foo: "bar" "baz" $' => %Q{Invalid CSS after ""bar" "baz" ": expected expression (e.g. 1px, bold), was "$"}, #'
73
- "=foo\n :color red\n.bar\n +bang" => "Undefined mixin 'bang'.",
74
- "=foo\n :color red\n.bar\n +bang_bop" => "Undefined mixin 'bang_bop'.",
75
- "=foo\n :color red\n.bar\n +bang-bop" => "Undefined mixin 'bang-bop'.",
76
- ".foo\n =foo\n :color red\n.bar\n +foo" => "Undefined mixin 'foo'.",
77
- " a\n b: c" => ["Indenting at the beginning of the document is illegal.", 1],
78
- " \n \n\t\n a\n b: c" => ["Indenting at the beginning of the document is illegal.", 4],
79
- "a\n b: c\n b: c" => ["Inconsistent indentation: 1 space was used for indentation, but the rest of the document was indented using 2 spaces.", 3],
80
- "a\n b: c\na\n b: c" => ["Inconsistent indentation: 1 space was used for indentation, but the rest of the document was indented using 2 spaces.", 4],
81
- "a\n\t\tb: c\n\tb: c" => ["Inconsistent indentation: 1 tab was used for indentation, but the rest of the document was indented using 2 tabs.", 3],
82
- "a\n b: c\n b: c" => ["Inconsistent indentation: 3 spaces were used for indentation, but the rest of the document was indented using 2 spaces.", 3],
83
- "a\n b: c\n a\n d: e" => ["Inconsistent indentation: 3 spaces were used for indentation, but the rest of the document was indented using 2 spaces.", 4],
84
- "a\n b: c\na\n d: e" => ["The line was indented 2 levels deeper than the previous line.", 4],
85
- "a\n b: c\n a\n d: e" => ["The line was indented 3 levels deeper than the previous line.", 4],
86
- "a\n \tb: c" => ["Indentation can't use both tabs and spaces.", 2],
87
- "=a(" => 'Invalid CSS after "(": expected variable (e.g. $foo), was ""',
88
- "=a(b)" => 'Invalid CSS after "(": expected variable (e.g. $foo), was "b)"',
89
- "=a(,)" => 'Invalid CSS after "(": expected variable (e.g. $foo), was ",)"',
90
- "=a($)" => 'Invalid CSS after "(": expected variable (e.g. $foo), was "$)"',
91
- "=a($foo bar)" => 'Invalid CSS after "($foo ": expected ")", was "bar)"',
92
- "=foo\n bar: baz\n+foo" => ["Properties are only allowed within rules, directives, mixin includes, or other properties.", 2],
93
- "a-\#{$b\n c: d" => ['Invalid CSS after "a-#{$b": expected "}", was ""', 1],
94
- "=a($b: 1, $c)" => "Required argument $c must come before any optional arguments.",
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.",
97
- "=a($b)\n a: $b\ndiv\n +a" => "Mixin a is missing argument $b.",
98
- "@function foo()\n 1 + 2" => "Functions can only contain variable declarations and control directives.",
99
- "@function foo()\n foo: bar" => "Functions can only contain variable declarations and control directives.",
100
- "@function foo()\n foo: bar\n @return 3" => ["Functions can only contain variable declarations and control directives.", 2],
101
- "@function foo\n @return 1" => ['Invalid CSS after "": expected "(", was ""', 1],
102
- "@function foo(\n @return 1" => ['Invalid CSS after "(": expected variable (e.g. $foo), was ""', 1],
103
- "@function foo(b)\n @return 1" => ['Invalid CSS after "(": expected variable (e.g. $foo), was "b)"', 1],
104
- "@function foo(,)\n @return 1" => ['Invalid CSS after "(": expected variable (e.g. $foo), was ",)"', 1],
105
- "@function foo($)\n @return 1" => ['Invalid CSS after "(": expected variable (e.g. $foo), was "$)"', 1],
106
- "@function foo()\n @return" => 'Invalid @return: expected expression.',
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)" => '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
- "@return 1" => '@return may only be used within a function.',
113
- "@if true\n @return 1" => '@return may only be used within a function.',
114
- "@mixin foo\n @return 1\n@include foo" => ['@return may only be used within a function.', 2],
115
- "@else\n a\n b: c" => ["@else must come after @if.", 1],
116
- "@if false\n@else foo" => "Invalid else directive '@else foo': expected 'if <expr>'.",
117
- "@if false\n@else if " => "Invalid else directive '@else if': expected 'if <expr>'.",
118
- "a\n $b: 12\nc\n d: $b" => 'Undefined variable: "$b".',
119
- "=foo\n $b: 12\nc\n +foo\n d: $b" => 'Undefined variable: "$b".',
120
- "c\n d: $b-foo" => 'Undefined variable: "$b-foo".',
121
- "c\n d: $b_foo" => 'Undefined variable: "$b_foo".',
122
- '@for $a from "foo" to 1' => '"foo" is not an integer.',
123
- '@for $a from 1 to "2"' => '"2" is not an integer.',
124
- '@for $a from 1 to "foo"' => '"foo" is not an integer.',
125
- '@for $a from 1 to 1.232323' => '1.23232 is not an integer.',
126
- '@for $a from 1px to 3em' => "Incompatible units: 'em' and 'px'.",
127
- '@if' => "Invalid if directive '@if': expected expression.",
128
- '@while' => "Invalid while directive '@while': expected expression.",
129
- '@debug' => "Invalid debug directive '@debug': expected expression.",
130
- %Q{@debug "a message"\n "nested message"} => "Illegal nesting: Nothing may be nested beneath debug directives.",
131
- '@warn' => "Invalid warn directive '@warn': expected expression.",
132
- %Q{@warn "a message"\n "nested message"} => "Illegal nesting: Nothing may be nested beneath warn directives.",
133
- "/* foo\n bar\n baz" => "Inconsistent indentation: previous line was indented by 4 spaces, but this line was indented by 2 spaces.",
134
- '+foo(1 + 1: 2)' => 'Invalid CSS after "(1 + 1": expected comma, was ": 2)"',
135
- '+foo($var: )' => 'Invalid CSS after "($var: ": expected mixin argument, was ")"',
136
- '+foo($var: a, $var: b)' => 'Keyword argument "$var" passed more than once',
137
- '+foo($var-var: a, $var_var: b)' => 'Keyword argument "$var_var" passed more than once',
138
- '+foo($var_var: a, $var-var: b)' => 'Keyword argument "$var-var" passed more than once',
139
- "a\n b: foo(1 + 1: 2)" => 'Invalid CSS after "foo(1 + 1": expected comma, was ": 2)"',
140
- "a\n b: foo($var: )" => 'Invalid CSS after "foo($var: ": expected function argument, was ")"',
141
- "a\n b: foo($var: a, $var: b)" => 'Keyword argument "$var" passed more than once',
142
- "a\n b: foo($var-var: a, $var_var: b)" => 'Keyword argument "$var_var" passed more than once',
143
- "a\n b: foo($var_var: a, $var-var: b)" => 'Keyword argument "$var-var" passed more than once',
144
- "@if foo\n @extend .bar" => ["Extend directives may only be used within rules.", 2],
145
- "$var: true\n@while $var\n @extend .bar\n $var: false" => ["Extend directives may only be used within rules.", 3],
146
- "@for $i from 0 to 1\n @extend .bar" => ["Extend directives may only be used within rules.", 2],
147
- "@mixin foo\n @extend .bar\n@include foo" => ["Extend directives may only be used within rules.", 2],
148
- "foo\n &a\n b: c" => ["Invalid CSS after \"&\": expected \"{\", was \"a\"\n\n\"a\" may only be used at the beginning of a compound selector.", 2],
149
- "foo\n &1\n b: c" => ["Invalid CSS after \"&\": expected \"{\", was \"1\"\n\n\"1\" may only be used at the beginning of a compound selector.", 2],
150
- "foo %\n a: b" => ['Invalid CSS after "foo %": expected placeholder name, was ""', 1],
151
- "=foo\n @content error" => "Invalid content directive. Trailing characters found: \"error\".",
152
- "=foo\n @content\n b: c" => "Illegal nesting: Nothing may be nested beneath @content directives.",
153
- "@content" => '@content may only be used within a mixin.',
154
- "=simple\n .simple\n color: red\n+simple\n color: blue" => ['Mixin "simple" does not accept a content block.', 4],
155
- "@import \"foo\" // bar" => "Invalid CSS after \"\"foo\" \": expected media query list, was \"// bar\"",
156
-
157
- # Regression tests
158
- "a\n b:\n c\n d" => ["Illegal nesting: Only properties may be nested beneath properties.", 3],
159
- "& foo\n bar: baz\n blat: bang" => ["Base-level rules cannot contain the parent-selector-referencing character '&'.", 1],
160
- "a\n b: c\n& foo\n bar: baz\n blat: bang" => ["Base-level rules cannot contain the parent-selector-referencing character '&'.", 3],
161
- "@" => "Invalid directive: '@'.",
162
- }
163
-
164
- def teardown
165
- clean_up_sassc
166
- end
167
-
168
- def test_basic_render
169
- renders_correctly "basic", { :style => :compact }
170
- end
171
-
172
- def test_empty_render
173
- assert_equal "", render("")
174
- end
175
-
176
- def test_multiple_calls_to_render
177
- sass = Sass::Engine.new("a\n b: c")
178
- assert_equal sass.render, sass.render
179
- end
180
-
181
- def test_alternate_styles
182
- renders_correctly "expanded", { :style => :expanded }
183
- renders_correctly "compact", { :style => :compact }
184
- renders_correctly "nested", { :style => :nested }
185
- renders_correctly "compressed", { :style => :compressed }
186
- end
187
-
188
- def test_compile
189
- assert_equal "div { hello: world; }\n", Sass.compile("$who: world\ndiv\n hello: $who", :syntax => :sass, :style => :compact)
190
- assert_equal "div { hello: world; }\n", Sass.compile("$who: world; div { hello: $who }", :style => :compact)
191
- end
192
-
193
- def test_compile_file
194
- FileUtils.mkdir_p(absolutize("tmp"))
195
- open(absolutize("tmp/test_compile_file.sass"), "w") {|f| f.write("$who: world\ndiv\n hello: $who")}
196
- open(absolutize("tmp/test_compile_file.scss"), "w") {|f| f.write("$who: world; div { hello: $who }")}
197
- assert_equal "div { hello: world; }\n", Sass.compile_file(absolutize("tmp/test_compile_file.sass"), :style => :compact)
198
- assert_equal "div { hello: world; }\n", Sass.compile_file(absolutize("tmp/test_compile_file.scss"), :style => :compact)
199
- ensure
200
- FileUtils.rm_rf(absolutize("tmp"))
201
- end
202
-
203
- def test_compile_file_to_css_file
204
- FileUtils.mkdir_p(absolutize("tmp"))
205
- open(absolutize("tmp/test_compile_file.sass"), "w") {|f| f.write("$who: world\ndiv\n hello: $who")}
206
- open(absolutize("tmp/test_compile_file.scss"), "w") {|f| f.write("$who: world; div { hello: $who }")}
207
- Sass.compile_file(absolutize("tmp/test_compile_file.sass"), absolutize("tmp/test_compile_file_sass.css"), :style => :compact)
208
- Sass.compile_file(absolutize("tmp/test_compile_file.scss"), absolutize("tmp/test_compile_file_scss.css"), :style => :compact)
209
- assert_equal "div { hello: world; }\n", File.read(absolutize("tmp/test_compile_file_sass.css"))
210
- assert_equal "div { hello: world; }\n", File.read(absolutize("tmp/test_compile_file_scss.css"))
211
- ensure
212
- FileUtils.rm_rf(absolutize("tmp"))
213
- end
214
-
215
- def test_flexible_tabulation
216
- assert_equal("p {\n a: b; }\n p q {\n c: d; }\n",
217
- render("p\n a: b\n q\n c: d\n"))
218
- assert_equal("p {\n a: b; }\n p q {\n c: d; }\n",
219
- render("p\n\ta: b\n\tq\n\t\tc: d\n"))
220
- end
221
-
222
- def test_import_same_name_different_ext
223
- assert_warning <<WARNING do
224
- WARNING: On line 1 of test_import_same_name_different_ext_inline.sass:
225
- It's not clear which file to import for '@import "same_name_different_ext"'.
226
- Candidates:
227
- same_name_different_ext.sass
228
- same_name_different_ext.scss
229
- For now I'll choose same_name_different_ext.sass.
230
- This will be an error in future versions of Sass.
231
- WARNING
232
- options = {:load_paths => [File.dirname(__FILE__) + '/templates/']}
233
- munge_filename options
234
- result = Sass::Engine.new("@import 'same_name_different_ext'", options).render
235
- assert_equal(<<CSS, result)
236
- .foo {
237
- ext: sass; }
238
- CSS
239
- end
240
- end
241
-
242
- def test_import_same_name_different_partiality
243
- assert_warning <<WARNING do
244
- WARNING: On line 1 of test_import_same_name_different_partiality_inline.sass:
245
- It's not clear which file to import for '@import "same_name_different_partiality"'.
246
- Candidates:
247
- _same_name_different_partiality.scss
248
- same_name_different_partiality.scss
249
- For now I'll choose _same_name_different_partiality.scss.
250
- This will be an error in future versions of Sass.
251
- WARNING
252
- options = {:load_paths => [File.dirname(__FILE__) + '/templates/']}
253
- munge_filename options
254
- result = Sass::Engine.new("@import 'same_name_different_partiality'", options).render
255
- assert_equal(<<CSS, result)
256
- .foo {
257
- partial: yes; }
258
- CSS
259
- end
260
- end
261
-
262
- EXCEPTION_MAP.each do |key, value|
263
- define_method("test_exception (#{key.inspect})") do
264
- line = 10
265
- begin
266
- silence_warnings {Sass::Engine.new(key, :filename => FAKE_FILE_NAME, :line => line).render}
267
- rescue Sass::SyntaxError => err
268
- value = [value] unless value.is_a?(Array)
269
-
270
- assert_equal(value.first.rstrip, err.message, "Line: #{key}")
271
- assert_equal(FAKE_FILE_NAME, err.sass_filename)
272
- assert_equal((value[1] || key.split("\n").length) + line - 1, err.sass_line, "Line: #{key}")
273
- assert_match(/#{Regexp.escape(FAKE_FILE_NAME)}:[0-9]+/, err.backtrace[0], "Line: #{key}")
274
- else
275
- assert(false, "Exception not raised for\n#{key}")
276
- end
277
- end
278
- end
279
-
280
- def test_exception_line
281
- to_render = <<SASS
282
- rule
283
- :prop val
284
- // comment!
285
-
286
- :broken
287
- SASS
288
- begin
289
- Sass::Engine.new(to_render).render
290
- rescue Sass::SyntaxError => err
291
- assert_equal(5, err.sass_line)
292
- else
293
- assert(false, "Exception not raised for '#{to_render}'!")
294
- end
295
- end
296
-
297
- def test_exception_location
298
- to_render = <<SASS
299
- rule
300
- :prop val
301
- // comment!
302
-
303
- :broken
304
- SASS
305
- begin
306
- Sass::Engine.new(to_render, :filename => FAKE_FILE_NAME, :line => (__LINE__-7)).render
307
- rescue Sass::SyntaxError => err
308
- assert_equal(FAKE_FILE_NAME, err.sass_filename)
309
- assert_equal((__LINE__-6), err.sass_line)
310
- else
311
- assert(false, "Exception not raised for '#{to_render}'!")
312
- end
313
- end
314
-
315
- def test_imported_exception
316
- [1, 2, 3, 4].each do |i|
317
- begin
318
- Sass::Engine.new("@import bork#{i}", :load_paths => [File.dirname(__FILE__) + '/templates/']).render
319
- rescue Sass::SyntaxError => err
320
- assert_equal(2, err.sass_line)
321
- assert_match(/(\/|^)bork#{i}\.sass$/, err.sass_filename)
322
-
323
- assert_hash_has(err.sass_backtrace.first,
324
- :filename => err.sass_filename, :line => err.sass_line)
325
-
326
- assert_nil(err.sass_backtrace[1][:filename])
327
- assert_equal(1, err.sass_backtrace[1][:line])
328
-
329
- assert_match(/(\/|^)bork#{i}\.sass:2$/, err.backtrace.first)
330
- assert_equal("(sass):1", err.backtrace[1])
331
- else
332
- assert(false, "Exception not raised for imported template: bork#{i}")
333
- end
334
- end
335
- end
336
-
337
- def test_double_imported_exception
338
- [1, 2, 3, 4].each do |i|
339
- begin
340
- Sass::Engine.new("@import nested_bork#{i}", :load_paths => [File.dirname(__FILE__) + '/templates/']).render
341
- rescue Sass::SyntaxError => err
342
- assert_equal(2, err.sass_line)
343
- assert_match(/(\/|^)bork#{i}\.sass$/, err.sass_filename)
344
-
345
- assert_hash_has(err.sass_backtrace.first,
346
- :filename => err.sass_filename, :line => err.sass_line)
347
-
348
- assert_match(/(\/|^)nested_bork#{i}\.sass$/, err.sass_backtrace[1][:filename])
349
- assert_equal(2, err.sass_backtrace[1][:line])
350
-
351
- assert_nil(err.sass_backtrace[2][:filename])
352
- assert_equal(1, err.sass_backtrace[2][:line])
353
-
354
- assert_match(/(\/|^)bork#{i}\.sass:2$/, err.backtrace.first)
355
- assert_match(/(\/|^)nested_bork#{i}\.sass:2$/, err.backtrace[1])
356
- assert_equal("(sass):1", err.backtrace[2])
357
- else
358
- assert(false, "Exception not raised for imported template: bork#{i}")
359
- end
360
- end
361
- end
362
-
363
- def test_selector_tracing
364
- actual_css = render(<<-SCSS, :syntax => :scss, :trace_selectors => true)
365
- @mixin mixed {
366
- .mixed { color: red; }
367
- }
368
- .context {
369
- @include mixed;
370
- }
371
- SCSS
372
- assert_equal(<<CSS,actual_css)
373
- /* on line 2 of test_selector_tracing_inline.scss, in `mixed'
374
- from line 5 of test_selector_tracing_inline.scss */
375
- .context .mixed {
376
- color: red; }
377
- CSS
378
- end
379
-
380
- def test_mixin_exception
381
- render(<<SASS)
382
- =error-mixin($a)
383
- color: $a * 1em * 1px
384
-
385
- =outer-mixin($a)
386
- +error-mixin($a)
387
-
388
- .error
389
- +outer-mixin(12)
390
- SASS
391
- assert(false, "Exception not raised")
392
- rescue Sass::SyntaxError => err
393
- assert_equal(2, err.sass_line)
394
- assert_equal(filename_for_test, err.sass_filename)
395
- assert_equal("error-mixin", err.sass_mixin)
396
-
397
- assert_hash_has(err.sass_backtrace.first, :line => err.sass_line,
398
- :filename => err.sass_filename, :mixin => err.sass_mixin)
399
- assert_hash_has(err.sass_backtrace[1], :line => 5,
400
- :filename => filename_for_test, :mixin => "outer-mixin")
401
- assert_hash_has(err.sass_backtrace[2], :line => 8,
402
- :filename => filename_for_test, :mixin => nil)
403
-
404
- assert_equal("#{filename_for_test}:2:in `error-mixin'", err.backtrace.first)
405
- assert_equal("#{filename_for_test}:5:in `outer-mixin'", err.backtrace[1])
406
- assert_equal("#{filename_for_test}:8", err.backtrace[2])
407
- end
408
-
409
- def test_mixin_callsite_exception
410
- render(<<SASS)
411
- =one-arg-mixin($a)
412
- color: $a
413
-
414
- =outer-mixin($a)
415
- +one-arg-mixin($a, 12)
416
-
417
- .error
418
- +outer-mixin(12)
419
- SASS
420
- assert(false, "Exception not raised")
421
- rescue Sass::SyntaxError => err
422
- assert_hash_has(err.sass_backtrace.first, :line => 5,
423
- :filename => filename_for_test, :mixin => "one-arg-mixin")
424
- assert_hash_has(err.sass_backtrace[1], :line => 5,
425
- :filename => filename_for_test, :mixin => "outer-mixin")
426
- assert_hash_has(err.sass_backtrace[2], :line => 8,
427
- :filename => filename_for_test, :mixin => nil)
428
- end
429
-
430
- def test_mixin_exception_cssize
431
- render(<<SASS)
432
- =parent-ref-mixin
433
- & foo
434
- a: b
435
-
436
- =outer-mixin
437
- +parent-ref-mixin
438
-
439
- +outer-mixin
440
- SASS
441
- assert(false, "Exception not raised")
442
- rescue Sass::SyntaxError => err
443
- assert_hash_has(err.sass_backtrace.first, :line => 2,
444
- :filename => filename_for_test, :mixin => "parent-ref-mixin")
445
- assert_hash_has(err.sass_backtrace[1], :line => 6,
446
- :filename => filename_for_test, :mixin => "outer-mixin")
447
- assert_hash_has(err.sass_backtrace[2], :line => 8,
448
- :filename => filename_for_test, :mixin => nil)
449
- end
450
-
451
- def test_mixin_and_import_exception
452
- Sass::Engine.new("@import nested_mixin_bork", :load_paths => [File.dirname(__FILE__) + '/templates/']).render
453
- assert(false, "Exception not raised")
454
- rescue Sass::SyntaxError => err
455
- assert_match(/(\/|^)nested_mixin_bork\.sass$/, err.sass_backtrace.first[:filename])
456
- assert_hash_has(err.sass_backtrace.first, :mixin => "error-mixin", :line => 4)
457
-
458
- assert_match(/(\/|^)mixin_bork\.sass$/, err.sass_backtrace[1][:filename])
459
- assert_hash_has(err.sass_backtrace[1], :mixin => "outer-mixin", :line => 2)
460
-
461
- assert_match(/(\/|^)mixin_bork\.sass$/, err.sass_backtrace[2][:filename])
462
- assert_hash_has(err.sass_backtrace[2], :mixin => nil, :line => 5)
463
-
464
- assert_match(/(\/|^)nested_mixin_bork\.sass$/, err.sass_backtrace[3][:filename])
465
- assert_hash_has(err.sass_backtrace[3], :mixin => nil, :line => 6)
466
-
467
- assert_hash_has(err.sass_backtrace[4], :filename => nil, :mixin => nil, :line => 1)
468
- end
469
-
470
- def test_basic_mixin_loop_exception
471
- render <<SASS
472
- @mixin foo
473
- @include foo
474
- @include foo
475
- SASS
476
- assert(false, "Exception not raised")
477
- rescue Sass::SyntaxError => err
478
- assert_equal("An @include loop has been found: foo includes itself", err.message)
479
- assert_hash_has(err.sass_backtrace[0], :mixin => "foo", :line => 2)
480
- end
481
-
482
- def test_double_mixin_loop_exception
483
- render <<SASS
484
- @mixin foo
485
- @include bar
486
- @mixin bar
487
- @include foo
488
- @include foo
489
- SASS
490
- assert(false, "Exception not raised")
491
- rescue Sass::SyntaxError => err
492
- assert_equal(<<MESSAGE.rstrip, err.message)
493
- An @include loop has been found:
494
- foo includes bar
495
- bar includes foo
496
- MESSAGE
497
- assert_hash_has(err.sass_backtrace[0], :mixin => "bar", :line => 4)
498
- assert_hash_has(err.sass_backtrace[1], :mixin => "foo", :line => 2)
499
- end
500
-
501
- def test_deep_mixin_loop_exception
502
- render <<SASS
503
- @mixin foo
504
- @include bar
505
-
506
- @mixin bar
507
- @include baz
508
-
509
- @mixin baz
510
- @include foo
511
-
512
- @include foo
513
- SASS
514
- assert(false, "Exception not raised")
515
- rescue Sass::SyntaxError => err
516
- assert_equal(<<MESSAGE.rstrip, err.message)
517
- An @include loop has been found:
518
- foo includes bar
519
- bar includes baz
520
- baz includes foo
521
- MESSAGE
522
- assert_hash_has(err.sass_backtrace[0], :mixin => "baz", :line => 8)
523
- assert_hash_has(err.sass_backtrace[1], :mixin => "bar", :line => 5)
524
- assert_hash_has(err.sass_backtrace[2], :mixin => "foo", :line => 2)
525
- end
526
-
527
- def test_mixin_loop_with_content
528
- render <<SASS
529
- =foo
530
- @content
531
- =bar
532
- +foo
533
- +bar
534
- +bar
535
- SASS
536
- assert(false, "Exception not raised")
537
- rescue Sass::SyntaxError => err
538
- assert_equal("An @include loop has been found: bar includes itself", err.message)
539
- assert_hash_has(err.sass_backtrace[0], :mixin => "@content", :line => 5)
540
- end
541
-
542
- def test_basic_import_loop_exception
543
- import = filename_for_test
544
- importer = MockImporter.new
545
- importer.add_import(import, "@import '#{import}'")
546
-
547
- engine = Sass::Engine.new("@import '#{import}'", :filename => import,
548
- :load_paths => [importer])
549
-
550
- assert_raise_message(Sass::SyntaxError, <<ERR.rstrip) {engine.render}
551
- An @import loop has been found: #{import} imports itself
552
- ERR
553
- end
554
-
555
- def test_double_import_loop_exception
556
- importer = MockImporter.new
557
- importer.add_import("foo", "@import 'bar'")
558
- importer.add_import("bar", "@import 'foo'")
559
-
560
- engine = Sass::Engine.new('@import "foo"', :filename => filename_for_test,
561
- :load_paths => [importer], :importer => importer)
562
-
563
- assert_raise_message(Sass::SyntaxError, <<ERR.rstrip) {engine.render}
564
- An @import loop has been found:
565
- #{filename_for_test} imports foo
566
- foo imports bar
567
- bar imports foo
568
- ERR
569
- end
570
-
571
- def test_deep_import_loop_exception
572
- importer = MockImporter.new
573
- importer.add_import("foo", "@import 'bar'")
574
- importer.add_import("bar", "@import 'baz'")
575
- importer.add_import("baz", "@import 'foo'")
576
-
577
- engine = Sass::Engine.new('@import "foo"', :filename => filename_for_test,
578
- :load_paths => [importer], :importer => importer)
579
-
580
- assert_raise_message(Sass::SyntaxError, <<ERR.rstrip) {engine.render}
581
- An @import loop has been found:
582
- #{filename_for_test} imports foo
583
- foo imports bar
584
- bar imports baz
585
- baz imports foo
586
- ERR
587
- end
588
-
589
- def test_exception_css_with_offset
590
- opts = {:full_exception => true, :line => 362}
591
- render(("a\n b: c\n" * 10) + "d\n e:\n" + ("f\n g: h\n" * 10), opts)
592
- rescue Sass::SyntaxError => e
593
- assert_equal(<<CSS, Sass::SyntaxError.exception_to_css(e, opts).split("\n")[0..15].join("\n"))
594
- /*
595
- Syntax error: Invalid property: "e:" (no value).
596
- on line 383 of test_exception_css_with_offset_inline.sass
597
-
598
- 378: a
599
- 379: b: c
600
- 380: a
601
- 381: b: c
602
- 382: d
603
- 383: e:
604
- 384: f
605
- 385: g: h
606
- 386: f
607
- 387: g: h
608
- 388: f
609
- CSS
610
- else
611
- assert(false, "Exception not raised for test_exception_css_with_offset")
612
- end
613
-
614
- def test_exception_css_with_mixins
615
- opts = {:full_exception => true}
616
- render(<<SASS, opts)
617
- =error-mixin($a)
618
- color: $a * 1em * 1px
619
-
620
- =outer-mixin($a)
621
- +error-mixin($a)
622
-
623
- .error
624
- +outer-mixin(12)
625
- SASS
626
- rescue Sass::SyntaxError => e
627
- assert_equal(<<CSS, Sass::SyntaxError.exception_to_css(e, opts).split("\n")[0..13].join("\n"))
628
- /*
629
- Syntax error: 12em*px isn't a valid CSS value.
630
- on line 2 of test_exception_css_with_mixins_inline.sass, in `error-mixin'
631
- from line 5 of test_exception_css_with_mixins_inline.sass, in `outer-mixin'
632
- from line 8 of test_exception_css_with_mixins_inline.sass
633
-
634
- 1: =error-mixin($a)
635
- 2: color: $a * 1em * 1px
636
- 3:
637
- 4: =outer-mixin($a)
638
- 5: +error-mixin($a)
639
- 6:
640
- 7: .error
641
- CSS
642
- else
643
- assert(false, "Exception not raised")
644
- end
645
-
646
- def test_cssize_exception_css
647
- opts = {:full_exception => true}
648
- render(<<SASS, opts)
649
- .filler
650
- stuff: "stuff!"
651
-
652
- a: b
653
-
654
- .more.filler
655
- a: b
656
- SASS
657
- rescue Sass::SyntaxError => e
658
- assert_equal(<<CSS, Sass::SyntaxError.exception_to_css(e, opts).split("\n")[0..11].join("\n"))
659
- /*
660
- Syntax error: Properties are only allowed within rules, directives, mixin includes, or other properties.
661
- on line 4 of test_cssize_exception_css_inline.sass
662
-
663
- 1: .filler
664
- 2: stuff: "stuff!"
665
- 3:
666
- 4: a: b
667
- 5:
668
- 6: .more.filler
669
- 7: a: b
670
- CSS
671
- else
672
- assert(false, "Exception not raised")
673
- end
674
-
675
- def test_css_import
676
- assert_equal("@import url(./fonts.css);\n", render("@import \"./fonts.css\""))
677
- end
678
-
679
- def test_http_import
680
- assert_equal("@import url(http://fonts.googleapis.com/css?family=Droid+Sans);\n",
681
- render("@import \"http://fonts.googleapis.com/css?family=Droid+Sans\""))
682
- end
683
-
684
- def test_protocol_relative_import
685
- assert_equal("@import url(//fonts.googleapis.com/css?family=Droid+Sans);\n",
686
- render("@import \"//fonts.googleapis.com/css?family=Droid+Sans\""))
687
- end
688
-
689
- def test_import_with_interpolation
690
- assert_equal(<<CSS, render(<<SASS))
691
- @import url("http://fonts.googleapis.com/css?family=Droid+Sans");
692
- CSS
693
- $family: unquote("Droid+Sans")
694
- @import url("http://fonts.googleapis.com/css?family=\#{$family}")
695
- SASS
696
- end
697
-
698
- def test_import_with_dynamic_media_query
699
- assert_equal(<<CSS, render(<<SASS))
700
- @import "foo" print and (-webkit-min-device-pixel-ratio-foo: 25);
701
- CSS
702
- $media: print
703
- $key: -webkit-min-device-pixel-ratio
704
- $value: 20
705
- @import "foo" \#{$media} and ($key + "-foo": $value + 5)
706
- SASS
707
- end
708
-
709
- def test_url_import
710
- assert_equal("@import url(fonts.sass);\n", render("@import url(fonts.sass)"))
711
- end
712
-
713
- def test_sass_import
714
- sassc_file = sassc_path("importee")
715
- assert !File.exists?(sassc_file)
716
- renders_correctly "import", { :style => :compact, :load_paths => [File.dirname(__FILE__) + "/templates"] }
717
- assert File.exists?(sassc_file)
718
- end
719
-
720
- def test_sass_pathname_import
721
- sassc_file = sassc_path("importee")
722
- assert !File.exists?(sassc_file)
723
- renders_correctly("import",
724
- :style => :compact,
725
- :load_paths => [Pathname.new(File.dirname(__FILE__) + "/templates")])
726
- assert File.exists?(sassc_file)
727
- end
728
-
729
- def test_import_from_global_load_paths
730
- importer = MockImporter.new
731
- importer.add_import("imported", "div{color:red}")
732
- Sass.load_paths << importer
733
-
734
- assert_equal "div {\n color: red; }\n", Sass::Engine.new('@import "imported"', :importer => importer).render
735
- ensure
736
- Sass.load_paths.clear
737
- end
738
-
739
- def test_nonexistent_import
740
- assert_raise_message(Sass::SyntaxError, <<ERR.rstrip) do
741
- File to import not found or unreadable: nonexistent.sass.
742
- Load path: #{Dir.pwd}
743
- ERR
744
- render("@import nonexistent.sass")
745
- end
746
- end
747
-
748
- def test_nonexistent_extensionless_import
749
- assert_raise_message(Sass::SyntaxError, <<ERR.rstrip) do
750
- File to import not found or unreadable: nonexistent.
751
- Load path: #{Dir.pwd}
752
- ERR
753
- render("@import nonexistent")
754
- end
755
- end
756
-
757
- def test_no_cache
758
- assert !File.exists?(sassc_path("importee"))
759
- renders_correctly("import", {
760
- :style => :compact, :cache => false,
761
- :load_paths => [File.dirname(__FILE__) + "/templates"],
762
- })
763
- assert !File.exists?(sassc_path("importee"))
764
- end
765
-
766
- def test_import_in_rule
767
- assert_equal(<<CSS, render(<<SASS, :load_paths => [File.dirname(__FILE__) + '/templates/']))
768
- .foo #foo {
769
- background-color: #bbaaff; }
770
-
771
- .bar {
772
- a: b; }
773
- .bar #foo {
774
- background-color: #bbaaff; }
775
- CSS
776
- .foo
777
- @import partial
778
-
779
- .bar
780
- a: b
781
- @import partial
782
- SASS
783
- end
784
-
785
- def test_units
786
- renders_correctly "units"
787
- end
788
-
789
- def test_default_function
790
- assert_equal(<<CSS, render(<<SASS))
791
- foo {
792
- bar: url("foo.png"); }
793
- CSS
794
- foo
795
- bar: url("foo.png")
796
- SASS
797
- assert_equal("foo {\n bar: url(); }\n", render("foo\n bar: url()\n"));
798
- end
799
-
800
- def test_string_minus
801
- assert_equal("foo {\n bar: baz-boom-bat; }\n", render(%Q{foo\n bar: baz-boom-bat}))
802
- assert_equal("foo {\n bar: -baz-boom; }\n", render(%Q{foo\n bar: -baz-boom}))
803
- end
804
-
805
- def test_string_div
806
- assert_equal("foo {\n bar: baz/boom/bat; }\n", render(%Q{foo\n bar: baz/boom/bat}))
807
- assert_equal("foo {\n bar: /baz/boom; }\n", render(%Q{foo\n bar: /baz/boom}))
808
- end
809
-
810
- def test_basic_multiline_selector
811
- assert_equal("#foo #bar,\n#baz #boom {\n foo: bar; }\n",
812
- render("#foo #bar,\n#baz #boom\n :foo bar"))
813
- assert_equal("#foo #bar,\n#foo #baz {\n foo: bar; }\n",
814
- render("#foo\n #bar,\n #baz\n :foo bar"))
815
- assert_equal("#foo,\n#bar {\n foo: bar; }\n #foo #baz,\n #bar #baz {\n foo: bar; }\n",
816
- render("#foo,\n#bar\n :foo bar\n #baz\n :foo bar"))
817
- assert_equal("#foo #bar, #baz #boom { foo: bar; }\n",
818
- render("#foo #bar,\n#baz #boom\n :foo bar", :style => :compact))
819
-
820
- assert_equal("#foo #bar,#baz #boom{foo:bar}\n",
821
- render("#foo #bar,\n#baz #boom\n :foo bar", :style => :compressed))
822
-
823
- assert_equal("#foo #bar,\n#baz #boom {\n foo: bar; }\n",
824
- render("#foo #bar,,\n,#baz #boom,\n :foo bar"))
825
-
826
- assert_equal("#bip #bop {\n foo: bar; }\n",
827
- render("#bip #bop,, ,\n :foo bar"))
828
- end
829
-
830
- def test_complex_multiline_selector
831
- renders_correctly "multiline"
832
- end
833
-
834
- def test_colon_only
835
- begin
836
- render("a\n b: c", :property_syntax => :old)
837
- rescue Sass::SyntaxError => e
838
- assert_equal("Illegal property syntax: can't use new syntax when :property_syntax => :old is set.",
839
- e.message)
840
- assert_equal(2, e.sass_line)
841
- else
842
- assert(false, "SyntaxError not raised for :property_syntax => :old")
843
- end
844
-
845
- begin
846
- render("a\n :b c", :property_syntax => :new)
847
- assert_equal(2, e.sass_line)
848
- rescue Sass::SyntaxError => e
849
- assert_equal("Illegal property syntax: can't use old syntax when :property_syntax => :new is set.",
850
- e.message)
851
- else
852
- assert(false, "SyntaxError not raised for :property_syntax => :new")
853
- end
854
- end
855
-
856
- def test_pseudo_elements
857
- assert_equal(<<CSS, render(<<SASS))
858
- ::first-line {
859
- size: 10em; }
860
- CSS
861
- ::first-line
862
- size: 10em
863
- SASS
864
- end
865
-
866
- def test_directive
867
- assert_equal("@a b;\n", render("@a b"))
868
-
869
- assert_equal("@a {\n b: c; }\n", render("@a\n :b c"))
870
- assert_equal("@a { b: c; }\n", render("@a\n :b c", :style => :compact))
871
- assert_equal("@a {\n b: c;\n}\n", render("@a\n :b c", :style => :expanded))
872
- assert_equal("@a{b:c}\n", render("@a\n :b c", :style => :compressed))
873
-
874
- assert_equal("@a {\n b: c;\n d: e; }\n",
875
- render("@a\n :b c\n :d e"))
876
- assert_equal("@a { b: c; d: e; }\n",
877
- render("@a\n :b c\n :d e", :style => :compact))
878
- assert_equal("@a {\n b: c;\n d: e;\n}\n",
879
- render("@a\n :b c\n :d e", :style => :expanded))
880
- assert_equal("@a{b:c;d:e}\n",
881
- render("@a\n :b c\n :d e", :style => :compressed))
882
-
883
- assert_equal("@a {\n #b {\n c: d; } }\n",
884
- render("@a\n #b\n :c d"))
885
- assert_equal("@a { #b { c: d; } }\n",
886
- render("@a\n #b\n :c d", :style => :compact))
887
- assert_equal("@a {\n #b {\n c: d;\n }\n}\n",
888
- render("@a\n #b\n :c d", :style => :expanded))
889
- assert_equal("@a{#b{c:d}}\n",
890
- render("@a\n #b\n :c d", :style => :compressed))
891
-
892
- assert_equal("@a {\n #b {\n a: b; }\n #b #c {\n d: e; } }\n",
893
- render("@a\n #b\n :a b\n #c\n :d e"))
894
- assert_equal("@a { #b { a: b; }\n #b #c { d: e; } }\n",
895
- render("@a\n #b\n :a b\n #c\n :d e", :style => :compact))
896
- assert_equal("@a {\n #b {\n a: b;\n }\n #b #c {\n d: e;\n }\n}\n",
897
- render("@a\n #b\n :a b\n #c\n :d e", :style => :expanded))
898
- assert_equal("@a{#b{a:b}#b #c{d:e}}\n",
899
- render("@a\n #b\n :a b\n #c\n :d e", :style => :compressed))
900
-
901
- assert_equal("@a {\n #foo,\n #bar {\n b: c; } }\n",
902
- render("@a\n #foo, \n #bar\n :b c"))
903
- assert_equal("@a { #foo, #bar { b: c; } }\n",
904
- render("@a\n #foo, \n #bar\n :b c", :style => :compact))
905
- assert_equal("@a {\n #foo,\n #bar {\n b: c;\n }\n}\n",
906
- render("@a\n #foo, \n #bar\n :b c", :style => :expanded))
907
- assert_equal("@a{#foo,#bar{b:c}}\n",
908
- render("@a\n #foo, \n #bar\n :b c", :style => :compressed))
909
-
910
- to_render = <<END
911
- @a
912
- :b c
913
- #d
914
- :e f
915
- :g h
916
- END
917
- rendered = <<END
918
- @a { b: c;
919
- #d { e: f; }
920
- g: h; }
921
- END
922
- assert_equal(rendered, render(to_render, :style => :compact))
923
-
924
- assert_equal("@a{b:c;#d{e:f}g:h}\n", render(to_render, :style => :compressed))
925
- end
926
-
927
- def test_property_hacks
928
- assert_equal(<<CSS, render(<<SASS))
929
- foo {
930
- _name: val;
931
- *name: val;
932
- #name: val;
933
- .name: val;
934
- name/**/: val;
935
- name/*\\**/: val;
936
- name: val; }
937
- CSS
938
- foo
939
- _name: val
940
- *name: val
941
- #name: val
942
- .name: val
943
- name/**/: val
944
- name/*\\**/: val
945
- name: val
946
- SASS
947
- end
948
-
949
- def test_properties_with_space_after_colon
950
- assert_equal <<CSS, render(<<SASS)
951
- foo {
952
- bar: baz;
953
- bizz: bap; }
954
- CSS
955
- foo
956
- bar : baz
957
- bizz : bap
958
- SASS
959
- end
960
-
961
- def test_line_annotations
962
- assert_equal(<<CSS, render(<<SASS, :line_comments => true, :style => :compact))
963
- /* line 2, test_line_annotations_inline.sass */
964
- foo bar { foo: bar; }
965
- /* line 5, test_line_annotations_inline.sass */
966
- foo baz { blip: blop; }
967
-
968
- /* line 9, test_line_annotations_inline.sass */
969
- floodle { flop: blop; }
970
-
971
- /* line 18, test_line_annotations_inline.sass */
972
- bup { mix: on; }
973
- /* line 15, test_line_annotations_inline.sass */
974
- bup mixin { moop: mup; }
975
-
976
- /* line 22, test_line_annotations_inline.sass */
977
- bip hop, skip hop { a: b; }
978
- CSS
979
- foo
980
- bar
981
- foo: bar
982
-
983
- baz
984
- blip: blop
985
-
986
-
987
- floodle
988
-
989
- flop: blop
990
-
991
- =mxn
992
- mix: on
993
- mixin
994
- moop: mup
995
-
996
- bup
997
- +mxn
998
-
999
- bip, skip
1000
- hop
1001
- a: b
1002
- SASS
1003
- end
1004
-
1005
- def test_line_annotations_with_filename
1006
- renders_correctly "line_numbers", :line_comments => true, :load_paths => [File.dirname(__FILE__) + "/templates"]
1007
- end
1008
-
1009
- def test_debug_info
1010
- esc_file_name = Sass::SCSS::RX.escape_ident(Sass::Util.scope("test_debug_info_inline.sass"))
1011
-
1012
- assert_equal(<<CSS, render(<<SASS, :debug_info => true, :style => :compact))
1013
- @media -sass-debug-info{filename{font-family:file\\:\\/\\/#{esc_file_name}}line{font-family:\\000032}}
1014
- foo bar { foo: bar; }
1015
- @media -sass-debug-info{filename{font-family:file\\:\\/\\/#{esc_file_name}}line{font-family:\\000035}}
1016
- foo baz { blip: blop; }
1017
-
1018
- @media -sass-debug-info{filename{font-family:file\\:\\/\\/#{esc_file_name}}line{font-family:\\000039}}
1019
- floodle { flop: blop; }
1020
-
1021
- @media -sass-debug-info{filename{font-family:file\\:\\/\\/#{esc_file_name}}line{font-family:\\0000318}}
1022
- bup { mix: on; }
1023
- @media -sass-debug-info{filename{font-family:file\\:\\/\\/#{esc_file_name}}line{font-family:\\0000315}}
1024
- bup mixin { moop: mup; }
1025
-
1026
- @media -sass-debug-info{filename{font-family:file\\:\\/\\/#{esc_file_name}}line{font-family:\\0000322}}
1027
- bip hop, skip hop { a: b; }
1028
- CSS
1029
- foo
1030
- bar
1031
- foo: bar
1032
-
1033
- baz
1034
- blip: blop
1035
-
1036
-
1037
- floodle
1038
-
1039
- flop: blop
1040
-
1041
- =mxn
1042
- mix: on
1043
- mixin
1044
- moop: mup
1045
-
1046
- bup
1047
- +mxn
1048
-
1049
- bip, skip
1050
- hop
1051
- a: b
1052
- SASS
1053
- end
1054
-
1055
- def test_debug_info_without_filename
1056
- assert_equal(<<CSS, Sass::Engine.new(<<SASS, :debug_info => true).render)
1057
- @media -sass-debug-info{filename{}line{font-family:\\000031}}
1058
- foo {
1059
- a: b; }
1060
- CSS
1061
- foo
1062
- a: b
1063
- SASS
1064
- end
1065
-
1066
- def test_debug_info_with_compressed
1067
- assert_equal(<<CSS, render(<<SASS, :debug_info => true, :style => :compressed))
1068
- foo{a:b}
1069
- CSS
1070
- foo
1071
- a: b
1072
- SASS
1073
- end
1074
-
1075
- def test_debug_info_with_line_annotations
1076
- esc_file_name = Sass::SCSS::RX.escape_ident(Sass::Util.scope("test_debug_info_with_line_annotations_inline.sass"))
1077
-
1078
- assert_equal(<<CSS, render(<<SASS, :debug_info => true, :line_comments => true))
1079
- @media -sass-debug-info{filename{font-family:file\\:\\/\\/#{esc_file_name}}line{font-family:\\000031}}
1080
- foo {
1081
- a: b; }
1082
- CSS
1083
- foo
1084
- a: b
1085
- SASS
1086
- end
1087
-
1088
- def test_debug_info_in_keyframes
1089
- assert_equal(<<CSS, render(<<SASS, :debug_info => true))
1090
- @-webkit-keyframes warm {
1091
- from {
1092
- color: black; }
1093
-
1094
- to {
1095
- color: red; } }
1096
- CSS
1097
- @-webkit-keyframes warm
1098
- from
1099
- color: black
1100
- to
1101
- color: red
1102
- SASS
1103
- end
1104
-
1105
- def test_empty_first_line
1106
- assert_equal("#a {\n b: c; }\n", render("#a\n\n b: c"))
1107
- end
1108
-
1109
- def test_escaped_rule
1110
- assert_equal(":focus {\n a: b; }\n", render("\\:focus\n a: b"))
1111
- assert_equal("a {\n b: c; }\n a :focus {\n d: e; }\n", render("\\a\n b: c\n \\:focus\n d: e"))
1112
- end
1113
-
1114
- def test_cr_newline
1115
- assert_equal("foo {\n a: b;\n c: d;\n e: f; }\n", render("foo\r a: b\r\n c: d\n\r e: f"))
1116
- end
1117
-
1118
- def test_property_with_content_and_nested_props
1119
- assert_equal(<<CSS, render(<<SASS))
1120
- foo {
1121
- a: b;
1122
- a-c: d;
1123
- a-c-e: f; }
1124
- CSS
1125
- foo
1126
- a: b
1127
- c: d
1128
- e: f
1129
- SASS
1130
-
1131
- assert_equal(<<CSS, render(<<SASS))
1132
- foo {
1133
- a: b;
1134
- a-c-e: f; }
1135
- CSS
1136
- foo
1137
- a: b
1138
- c:
1139
- e: f
1140
- SASS
1141
- end
1142
-
1143
- def test_guarded_assign
1144
- assert_equal("foo {\n a: b; }\n", render(%Q{$foo: b\n$foo: c !default\nfoo\n a: $foo}))
1145
- assert_equal("foo {\n a: b; }\n", render(%Q{$foo: b !default\nfoo\n a: $foo}))
1146
- assert_equal("foo {\n a: b; }\n", render(%Q{$foo: null\n$foo: b !default\nfoo\n a: $foo}))
1147
- end
1148
-
1149
- def test_mixins
1150
- renders_correctly "mixins", { :style => :expanded }
1151
- end
1152
-
1153
- def test_directive_style_mixins
1154
- assert_equal <<CSS, render(<<SASS)
1155
- bar {
1156
- prop: baz; }
1157
- CSS
1158
- @mixin foo($arg)
1159
- prop: $arg
1160
-
1161
- bar
1162
- @include foo(baz)
1163
- SASS
1164
- end
1165
-
1166
- def test_mixins_dont_interfere_with_sibling_combinator
1167
- assert_equal("foo + bar {\n a: b; }\nfoo + baz {\n c: d; }\n",
1168
- render("foo\n +\n bar\n a: b\n baz\n c: d"))
1169
- end
1170
-
1171
- def test_mixin_args
1172
- assert_equal("blat {\n baz: hi; }\n", render(<<SASS))
1173
- =foo($bar)
1174
- baz: $bar
1175
- blat
1176
- +foo(hi)
1177
- SASS
1178
- assert_equal("blat {\n baz: 3; }\n", render(<<SASS))
1179
- =foo($a, $b)
1180
- baz: $a + $b
1181
- blat
1182
- +foo(1, 2)
1183
- SASS
1184
- assert_equal("blat {\n baz: 4;\n baz: 3;\n baz: 5;\n bang: 3; }\n", render(<<SASS))
1185
- =foo($c: (6 + 4) / 2)
1186
- baz: $c
1187
- $c: 3
1188
- blat
1189
- +foo($c + 1)
1190
- +foo(($c + 3)/2)
1191
- +foo
1192
- bang: $c
1193
- SASS
1194
- end
1195
-
1196
- def test_default_values_for_mixin_arguments
1197
- assert_equal("white {\n color: white; }\n\nblack {\n color: black; }\n", render(<<SASS))
1198
- =foo($a: #FFF)
1199
- :color $a
1200
- white
1201
- +foo
1202
- black
1203
- +foo(#000)
1204
- SASS
1205
- assert_equal(<<CSS, render(<<SASS))
1206
- one {
1207
- color: white;
1208
- padding: 1px;
1209
- margin: 4px; }
1210
-
1211
- two {
1212
- color: white;
1213
- padding: 2px;
1214
- margin: 5px; }
1215
-
1216
- three {
1217
- color: white;
1218
- padding: 2px;
1219
- margin: 3px; }
1220
- CSS
1221
- $a: 5px
1222
- =foo($a, $b: 1px, $c: 3px + $b)
1223
- :color $a
1224
- :padding $b
1225
- :margin $c
1226
- one
1227
- +foo(#fff)
1228
- two
1229
- +foo(#fff, 2px)
1230
- three
1231
- +foo(#fff, 2px, 3px)
1232
- SASS
1233
- assert_equal(<<CSS, render(<<SASS))
1234
- one {
1235
- color: white;
1236
- padding: 1px;
1237
- margin: 4px; }
1238
-
1239
- two {
1240
- color: white;
1241
- padding: 2px;
1242
- margin: 5px; }
1243
-
1244
- three {
1245
- color: white;
1246
- padding: 2px;
1247
- margin: 3px; }
1248
- CSS
1249
- $a: 5px
1250
- =foo($a, $b: 1px, $c: null)
1251
- $c: 3px + $b !default
1252
- color: $a
1253
- padding: $b
1254
- margin: $c
1255
- one
1256
- +foo(#fff)
1257
- two
1258
- +foo(#fff, 2px)
1259
- three
1260
- +foo(#fff, 2px, 3px)
1261
- SASS
1262
- end
1263
-
1264
- def test_hyphen_underscore_insensitive_mixins
1265
- assert_equal(<<CSS, render(<<SASS))
1266
- a {
1267
- b: 12;
1268
- c: foo; }
1269
- CSS
1270
- =mixin-hyphen
1271
- b: 12
1272
-
1273
- =mixin_under
1274
- c: foo
1275
-
1276
- a
1277
- +mixin_hyphen
1278
- +mixin-under
1279
- SASS
1280
- end
1281
-
1282
- def test_css_identifier_mixin
1283
- assert_equal(<<CSS, render(<<SASS))
1284
- a {
1285
- foo: 12; }
1286
- CSS
1287
- =\\{foo\\(12\\)($a)
1288
- foo: $a
1289
-
1290
- a
1291
- +\\{foo\\(12\\)(12)
1292
- SASS
1293
- end
1294
-
1295
- def test_basic_function
1296
- assert_equal(<<CSS, render(<<SASS))
1297
- bar {
1298
- a: 3; }
1299
- CSS
1300
- @function foo()
1301
- @return 1 + 2
1302
-
1303
- bar
1304
- a: foo()
1305
- SASS
1306
- end
1307
-
1308
- def test_function_args
1309
- assert_equal(<<CSS, render(<<SASS))
1310
- bar {
1311
- a: 3; }
1312
- CSS
1313
- @function plus($var1, $var2)
1314
- @return $var1 + $var2
1315
-
1316
- bar
1317
- a: plus(1, 2)
1318
- SASS
1319
- end
1320
-
1321
- def test_function_arg_default
1322
- assert_equal(<<CSS, render(<<SASS))
1323
- bar {
1324
- a: 3; }
1325
- CSS
1326
- @function plus($var1, $var2: 2)
1327
- @return $var1 + $var2
1328
-
1329
- bar
1330
- a: plus(1)
1331
- SASS
1332
- end
1333
-
1334
- def test_function_arg_keyword
1335
- assert_equal(<<CSS, render(<<SASS))
1336
- bar {
1337
- a: 1bar; }
1338
- CSS
1339
- @function plus($var1: 1, $var2: 2)
1340
- @return $var1 + $var2
1341
-
1342
- bar
1343
- a: plus($var2: bar)
1344
- SASS
1345
- end
1346
-
1347
- def test_function_with_missing_argument
1348
- render(<<SASS)
1349
- @function plus($var1, $var2)
1350
- @return $var1 + $var2
1351
-
1352
- bar
1353
- a: plus($var2: bar)
1354
- SASS
1355
- flunk("Expected exception")
1356
- rescue Sass::SyntaxError => e
1357
- assert_equal("Function plus is missing argument $var1.", e.message)
1358
- end
1359
-
1360
- def test_function_with_extra_argument
1361
- render(<<SASS)
1362
- @function plus($var1, $var2)
1363
- @return $var1 + $var2
1364
-
1365
- bar
1366
- a: plus($var1: foo, $var2: bar, $var3: baz)
1367
- SASS
1368
- flunk("Expected exception")
1369
- rescue Sass::SyntaxError => e
1370
- assert_equal("Function plus doesn't have an argument named $var3.", e.message)
1371
- end
1372
-
1373
- def test_function_with_positional_and_keyword_argument
1374
- render(<<SASS)
1375
- @function plus($var1, $var2)
1376
- @return $var1 + $var2
1377
-
1378
- bar
1379
- a: plus(foo, bar, $var2: baz)
1380
- SASS
1381
- flunk("Expected exception")
1382
- rescue Sass::SyntaxError => e
1383
- assert_equal("Function plus was passed argument $var2 both by position and by name.", e.message)
1384
- end
1385
-
1386
- def test_function_with_keyword_before_positional_argument
1387
- render(<<SASS)
1388
- @function plus($var1, $var2)
1389
- @return $var1 + $var2
1390
-
1391
- bar
1392
- a: plus($var2: foo, bar)
1393
- SASS
1394
- flunk("Expected exception")
1395
- rescue Sass::SyntaxError => e
1396
- assert_equal("Positional arguments must come before keyword arguments.", e.message)
1397
- end
1398
-
1399
- def test_function_with_if
1400
- assert_equal(<<CSS, render(<<SASS))
1401
- bar {
1402
- a: foo;
1403
- b: bar; }
1404
- CSS
1405
- @function my-if($cond, $val1, $val2)
1406
- @if $cond
1407
- @return $val1
1408
- @else
1409
- @return $val2
1410
-
1411
- bar
1412
- a: my-if(true, foo, bar)
1413
- b: my-if(false, foo, bar)
1414
- SASS
1415
- end
1416
-
1417
- def test_function_with_var
1418
- assert_equal(<<CSS, render(<<SASS))
1419
- bar {
1420
- a: 1; }
1421
- CSS
1422
- @function foo($val1, $val2)
1423
- $intermediate: $val1 + $val2
1424
- @return $intermediate/3
1425
-
1426
- bar
1427
- a: foo(1, 2)
1428
- SASS
1429
- end
1430
-
1431
- def test_control_directive_in_nested_property
1432
- assert_equal(<<CSS, render(<<SASS))
1433
- foo {
1434
- a-b: c; }
1435
- CSS
1436
- foo
1437
- a:
1438
- @if true
1439
- b: c
1440
- SASS
1441
- end
1442
-
1443
- def test_interpolation
1444
- assert_equal("a-1 {\n b-2-3: c-3; }\n", render(<<SASS))
1445
- $a: 1
1446
- $b: 2
1447
- $c: 3
1448
- a-\#{$a}
1449
- b-\#{$b}-\#{$c}: c-\#{$a + $b}
1450
- SASS
1451
- end
1452
-
1453
- def test_complex_property_interpolation
1454
- assert_equal(<<CSS, render(<<SASS))
1455
- a-1 {
1456
- b-2 3-fizzap18: c-3; }
1457
- CSS
1458
- $a: 1
1459
- $b: 2
1460
- $c: 3
1461
- a-\#{$a}
1462
- b-\#{$b $c}-\#{fizzap + ($c + 15)}: c-\#{$a + $b}
1463
- SASS
1464
- end
1465
-
1466
- def test_if_directive
1467
- assert_equal("a {\n b: 1; }\n", render(<<SASS))
1468
- $var: true
1469
- a
1470
- @if $var
1471
- b: 1
1472
- @if not $var
1473
- b: 2
1474
- SASS
1475
-
1476
- assert_equal("a {\n b: 2; }\n", render(<<SASS))
1477
- $var: null
1478
- a
1479
- @if $var
1480
- b: 1
1481
- @if not $var
1482
- b: 2
1483
- SASS
1484
- end
1485
-
1486
- def test_for
1487
- assert_equal(<<CSS, render(<<SASS))
1488
- a-0 {
1489
- two-i: 0; }
1490
-
1491
- a-1 {
1492
- two-i: 2; }
1493
-
1494
- a-2 {
1495
- two-i: 4; }
1496
-
1497
- a-3 {
1498
- two-i: 6; }
1499
-
1500
- b-1 {
1501
- j-1: 0; }
1502
-
1503
- b-2 {
1504
- j-1: 1; }
1505
-
1506
- b-3 {
1507
- j-1: 2; }
1508
-
1509
- b-4 {
1510
- j-1: 3; }
1511
- CSS
1512
- $a: 3
1513
- @for $i from 0 to $a + 1
1514
- a-\#{$i}
1515
- two-i: 2 * $i
1516
-
1517
- @for $j from 1 through 4
1518
- b-\#{$j}
1519
- j-1: $j - 1
1520
- SASS
1521
- end
1522
-
1523
- def test_while
1524
- assert_equal(<<CSS, render(<<SASS))
1525
- a-5 {
1526
- blooble: gloop; }
1527
-
1528
- a-4 {
1529
- blooble: gloop; }
1530
-
1531
- a-3 {
1532
- blooble: gloop; }
1533
-
1534
- a-2 {
1535
- blooble: gloop; }
1536
-
1537
- a-1 {
1538
- blooble: gloop; }
1539
- CSS
1540
- $a: 5
1541
- @while $a != 0
1542
- a-\#{$a}
1543
- blooble: gloop
1544
- $a: $a - 1
1545
- SASS
1546
- end
1547
-
1548
- def test_else
1549
- assert_equal(<<CSS, render(<<SASS))
1550
- a {
1551
- t1: t;
1552
- t2: t;
1553
- t3: t;
1554
- t4: t; }
1555
- CSS
1556
- a
1557
- @if true
1558
- t1: t
1559
- @else
1560
- f1: f
1561
-
1562
- @if false
1563
- f2: f
1564
- @else
1565
- t2: t
1566
-
1567
- @if false
1568
- f3: f1
1569
- @else if 1 + 1 == 3
1570
- f3: f2
1571
- @else
1572
- t3: t
1573
-
1574
- @if false
1575
- f4: f1
1576
- @else if 1 + 1 == 2
1577
- t4: t
1578
- @else
1579
- f4: f2
1580
-
1581
- @if false
1582
- f5: f1
1583
- @else if false
1584
- f5: f2
1585
- SASS
1586
- end
1587
-
1588
- def test_each
1589
- assert_equal(<<CSS, render(<<SASS))
1590
- a {
1591
- b: 1px;
1592
- b: 2px;
1593
- b: 3px;
1594
- b: 4px;
1595
- c: foo;
1596
- c: bar;
1597
- c: baz;
1598
- c: bang;
1599
- d: blue; }
1600
- CSS
1601
- a
1602
- @each $number in 1px 2px 3px 4px
1603
- b: $number
1604
- @each $str in foo, bar, baz, bang
1605
- c: $str
1606
- @each $single in blue
1607
- d: $single
1608
- SASS
1609
- end
1610
-
1611
- def test_variable_reassignment
1612
- assert_equal(<<CSS, render(<<SASS))
1613
- a {
1614
- b: 1;
1615
- c: 2; }
1616
- CSS
1617
- $a: 1
1618
- a
1619
- b: $a
1620
- $a: 2
1621
- c: $a
1622
- SASS
1623
- end
1624
-
1625
- def test_variable_scope
1626
- assert_equal(<<CSS, render(<<SASS))
1627
- a {
1628
- b-1: c;
1629
- b-2: c;
1630
- d: 12; }
1631
-
1632
- b {
1633
- d: 17; }
1634
- CSS
1635
- $i: 12
1636
- a
1637
- @for $i from 1 through 2
1638
- b-\#{$i}: c
1639
- d: $i
1640
-
1641
- =foo
1642
- $i: 17
1643
-
1644
- b
1645
- +foo
1646
- d: $i
1647
- SASS
1648
- end
1649
-
1650
- def test_hyphen_underscore_insensitive_variables
1651
- assert_equal(<<CSS, render(<<SASS))
1652
- a {
1653
- b: c; }
1654
-
1655
- d {
1656
- e: 13;
1657
- f: foobar; }
1658
- CSS
1659
- $var-hyphen: 12
1660
- $var_under: foo
1661
-
1662
- a
1663
- $var_hyphen: 1 + $var_hyphen
1664
- $var-under: $var-under + bar
1665
- b: c
1666
-
1667
- d
1668
- e: $var-hyphen
1669
- f: $var_under
1670
- SASS
1671
- end
1672
-
1673
- def test_css_identifier_variable
1674
- assert_equal(<<CSS, render(<<SASS))
1675
- a {
1676
- b: 12; }
1677
- CSS
1678
- $\\{foo\\(12\\): 12
1679
-
1680
- a
1681
- b: $\\{foo\\(12\\)
1682
- SASS
1683
- end
1684
-
1685
- def test_important
1686
- assert_equal(<<CSS, render(<<SASS))
1687
- a {
1688
- b: 12px !important; }
1689
- CSS
1690
- $foo: 12px
1691
- a
1692
- b: $foo !important
1693
- SASS
1694
- end
1695
-
1696
- def test_argument_error
1697
- assert_raise(Sass::SyntaxError) { render("a\n b: hsl(1)") }
1698
- end
1699
-
1700
- def test_comments_at_the_top_of_a_document
1701
- render(<<SASS)
1702
- //
1703
- This is a comment that
1704
- continues to the second line.
1705
- foo
1706
- bar: baz
1707
- SASS
1708
- end
1709
-
1710
- def test_loud_comments_containing_a_comment_close
1711
- actual_css = render(<<SASS)
1712
- /*
1713
- This is a comment that
1714
- continues to the second line. */
1715
- foo
1716
- bar: baz
1717
- SASS
1718
- assert_equal(<<CSS, actual_css)
1719
- /* This is a comment that
1720
- * continues to the second line. */
1721
- foo {
1722
- bar: baz; }
1723
- CSS
1724
- end
1725
-
1726
- def test_loud_comments_with_starred_lines
1727
- assert_equal(<<CSS, render(<<SASS))
1728
- /* This is a comment that
1729
- * continues to the second line.
1730
- * And even to the third! */
1731
- CSS
1732
- /* This is a comment that
1733
- * continues to the second line.
1734
- * And even to the third!
1735
- SASS
1736
- end
1737
-
1738
- def test_loud_comments_with_no_space_after_starred_lines
1739
- assert_equal(<<CSS, render(<<SASS))
1740
- /*bip bop
1741
- *beep boop
1742
- *bap blimp */
1743
- CSS
1744
- /*bip bop
1745
- *beep boop
1746
- *bap blimp
1747
- SASS
1748
- end
1749
-
1750
- def test_comment_indentation_at_beginning_of_doc
1751
- assert_equal <<CSS, render(<<SASS)
1752
- /* foo
1753
- * bar
1754
- * baz */
1755
- foo {
1756
- a: b; }
1757
- CSS
1758
- /* foo
1759
- bar
1760
- baz
1761
- foo
1762
- a: b
1763
- SASS
1764
- end
1765
-
1766
- def test_unusual_comment_indentation
1767
- assert_equal <<CSS, render(<<SASS)
1768
- foo {
1769
- /* foo
1770
- * bar
1771
- * baz */ }
1772
- CSS
1773
- foo
1774
- /* foo
1775
- bar
1776
- baz
1777
- SASS
1778
- end
1779
-
1780
- def test_loud_comment_with_close
1781
- assert_equal <<CSS, render(<<SASS)
1782
- foo {
1783
- /* foo
1784
- * bar */ }
1785
- CSS
1786
- foo
1787
- /* foo
1788
- bar */
1789
- SASS
1790
- end
1791
-
1792
- def test_loud_comment_with_separate_line_close
1793
- assert_equal <<CSS, render(<<SASS)
1794
- foo {
1795
- /* foo
1796
- * bar
1797
- */ }
1798
- CSS
1799
- foo
1800
- /* foo
1801
- * bar
1802
- */
1803
- SASS
1804
- end
1805
-
1806
- def test_loud_comment_in_compressed_mode
1807
- assert_equal <<CSS, render(<<SASS, :style => :compressed)
1808
- foo{color:blue;/*! foo
1809
- * bar
1810
- */}
1811
- CSS
1812
- foo
1813
- color: blue
1814
- /*! foo
1815
- * bar
1816
- */
1817
- SASS
1818
- end
1819
-
1820
- def test_loud_comment_is_evaluated
1821
- assert_equal <<CSS, render(<<SASS)
1822
- /*!
1823
- * Hue: 327.21649deg */
1824
- CSS
1825
- /*!
1826
- Hue: \#{hue(#f836a0)}
1827
- SASS
1828
- end
1829
-
1830
- def test_attribute_selector_with_spaces
1831
- assert_equal(<<CSS, render(<<SASS))
1832
- a b[foo=bar] {
1833
- c: d; }
1834
- CSS
1835
- a
1836
- b[foo = bar]
1837
- c: d
1838
- SASS
1839
- end
1840
-
1841
- def test_quoted_colon
1842
- assert_equal(<<CSS, render(<<SASS))
1843
- a b[foo="bar: baz"] {
1844
- c: d; }
1845
- CSS
1846
- a
1847
- b[foo="bar: baz"]
1848
- c: d
1849
- SASS
1850
- end
1851
-
1852
- def test_quoted_comma
1853
- assert_equal(<<CSS, render(<<SASS))
1854
- a b[foo="bar, baz"] {
1855
- c: d; }
1856
- CSS
1857
- a
1858
- b[foo="bar, baz"]
1859
- c: d
1860
- SASS
1861
- end
1862
-
1863
- def test_quoted_ampersand
1864
- assert_equal(<<CSS, render(<<SASS))
1865
- a b[foo="bar & baz"] {
1866
- c: d; }
1867
- CSS
1868
- a
1869
- b[foo="bar & baz"]
1870
- c: d
1871
- SASS
1872
- end
1873
-
1874
- def test_empty_selector_warning
1875
- assert_warning(<<END) {render("foo bar")}
1876
- WARNING on line 1 of test_empty_selector_warning_inline.sass:
1877
- This selector doesn't have any properties and will not be rendered.
1878
- END
1879
- end
1880
-
1881
- def test_nonprinting_empty_property
1882
- assert_equal(<<CSS, render(<<SASS))
1883
- a {
1884
- c: "";
1885
- e: f; }
1886
- CSS
1887
- $null-value: null
1888
- $empty-string: ''
1889
- $empty-list: (null)
1890
- a
1891
- b: $null-value
1892
- c: $empty-string
1893
- d: $empty-list
1894
- e: f
1895
-
1896
- g
1897
- h: null
1898
- SASS
1899
- end
1900
-
1901
- def test_root_level_pseudo_class_with_new_properties
1902
- assert_equal(<<CSS, render(<<SASS, :property_syntax => :new))
1903
- :focus {
1904
- outline: 0; }
1905
- CSS
1906
- :focus
1907
- outline: 0
1908
- SASS
1909
- end
1910
-
1911
- def test_pseudo_class_with_new_properties
1912
- assert_equal(<<CSS, render(<<SASS, :property_syntax => :new))
1913
- p :focus {
1914
- outline: 0; }
1915
- CSS
1916
- p
1917
- :focus
1918
- outline: 0
1919
- SASS
1920
- end
1921
-
1922
- def test_nil_option
1923
- assert_equal(<<CSS, render(<<SASS, :format => nil))
1924
- foo {
1925
- a: b; }
1926
- CSS
1927
- foo
1928
- a: b
1929
- SASS
1930
- end
1931
-
1932
- def test_interpolation_in_raw_functions
1933
- assert_equal(<<CSS, render(<<SASS))
1934
- foo {
1935
- filter: progid:Microsoft.foo.bar.Baz(flip=foobar, bang=#00ff00cc); }
1936
- CSS
1937
- foo
1938
- filter: progid:Microsoft.foo.bar.Baz(flip=\#{foo + bar}, bang=#00ff00cc)
1939
- SASS
1940
- end
1941
-
1942
- # SassScript string behavior
1943
-
1944
- def test_plus_preserves_quotedness
1945
- assert_equal(<<CSS, render(<<SASS))
1946
- foo {
1947
- a: "foo1";
1948
- b: "1foo";
1949
- c: foo1;
1950
- d: 1foo;
1951
- e: "foobar";
1952
- f: foobar; }
1953
- CSS
1954
- foo
1955
- a: "foo" + 1
1956
- b: 1 + "foo"
1957
- c: foo + 1
1958
- d: 1 + foo
1959
- e: "foo" + bar
1960
- f: foo + "bar"
1961
- SASS
1962
- end
1963
-
1964
- def test_colon_properties_preserve_quotedness
1965
- assert_equal(<<CSS, render(<<SASS))
1966
- foo {
1967
- a: "foo";
1968
- b: bar;
1969
- c: "foo" bar;
1970
- d: foo, "bar"; }
1971
- CSS
1972
- foo
1973
- a: "foo"
1974
- b: bar
1975
- c: "foo" bar
1976
- d: foo, "bar"
1977
- SASS
1978
- end
1979
-
1980
- def test_colon_variables_preserve_quotedness
1981
- assert_equal(<<CSS, render(<<SASS))
1982
- foo {
1983
- a: "foo";
1984
- b: bar; }
1985
- CSS
1986
- $a: "foo"
1987
- $b: bar
1988
-
1989
- foo
1990
- a: $a
1991
- b: $b
1992
- SASS
1993
- end
1994
-
1995
- def test_colon_args_preserve_quotedness
1996
- assert_equal(<<CSS, render(<<SASS))
1997
- foo {
1998
- a: "foo";
1999
- b: bar;
2000
- c: "foo" bar;
2001
- d: foo, "bar"; }
2002
- CSS
2003
- =foo($a: "foo", $b: bar, $c: "foo" bar, $d: (foo, "bar"))
2004
- foo
2005
- a: $a
2006
- b: $b
2007
- c: $c
2008
- d: $d
2009
-
2010
- +foo
2011
- SASS
2012
- end
2013
-
2014
- def test_interpolation_unquotes_strings
2015
- assert_equal(<<CSS, render(<<SASS))
2016
- .foo-bar {
2017
- a: b; }
2018
- CSS
2019
- .foo-\#{"bar"}
2020
- a: b
2021
- SASS
2022
-
2023
- assert_equal(<<CSS, render(<<SASS))
2024
- .foo {
2025
- a: b c; }
2026
- CSS
2027
- .foo
2028
- a: b \#{"c"}
2029
- SASS
2030
- end
2031
-
2032
- def test_interpolation_unquotes_strings_in_vars
2033
- assert_equal(<<CSS, render(<<SASS))
2034
- .foo-bar {
2035
- a: b; }
2036
- CSS
2037
- $var: "bar"
2038
-
2039
- .foo-\#{$var}
2040
- a: b
2041
- SASS
2042
- end
2043
-
2044
- def test_interpolation_doesnt_deep_unquote_strings
2045
- assert_equal(<<CSS, render(<<SASS))
2046
- .foo {
2047
- a: "bar" "baz"; }
2048
- CSS
2049
- .foo
2050
- a: \#{"bar" "baz"}
2051
- SASS
2052
- end
2053
-
2054
- def test_warn_directive
2055
- expected_warning = <<EXPECTATION
2056
- WARNING: this is a warning
2057
- on line 4 of test_warn_directive_inline.sass
2058
-
2059
- WARNING: this is a mixin warning
2060
- on line 2 of test_warn_directive_inline.sass, in `foo'
2061
- from line 7 of test_warn_directive_inline.sass
2062
- EXPECTATION
2063
- assert_warning expected_warning do
2064
- assert_equal <<CSS, render(<<SASS)
2065
- bar {
2066
- c: d; }
2067
- CSS
2068
- =foo
2069
- @warn "this is a mixin warning"
2070
-
2071
- @warn "this is a warning"
2072
- bar
2073
- c: d
2074
- +foo
2075
- SASS
2076
- end
2077
- end
2078
-
2079
- def test_warn_directive_when_quiet
2080
- assert_warning "" do
2081
- assert_equal <<CSS, render(<<SASS, :quiet => true)
2082
- CSS
2083
- @warn "this is a warning"
2084
- SASS
2085
- end
2086
- end
2087
-
2088
- def test_warn_with_imports
2089
- expected_warning = <<WARN
2090
- WARNING: In the main file
2091
- on line 1 of #{File.dirname(__FILE__)}/templates/warn.sass
2092
-
2093
- WARNING: Imported
2094
- on line 1 of #{File.dirname(__FILE__)}/templates/warn_imported.sass
2095
- from line 2 of #{File.dirname(__FILE__)}/templates/warn.sass
2096
-
2097
- WARNING: In an imported mixin
2098
- on line 4 of #{File.dirname(__FILE__)}/templates/warn_imported.sass, in `emits-a-warning'
2099
- from line 3 of #{File.dirname(__FILE__)}/templates/warn.sass
2100
- WARN
2101
- assert_warning expected_warning do
2102
- renders_correctly "warn", :style => :compact, :load_paths => [File.dirname(__FILE__) + "/templates"]
2103
- end
2104
- end
2105
-
2106
- def test_media_bubbling
2107
- assert_equal <<CSS, render(<<SASS)
2108
- .foo {
2109
- a: b; }
2110
- @media bar {
2111
- .foo {
2112
- c: d; } }
2113
- .foo .baz {
2114
- e: f; }
2115
- @media bip {
2116
- .foo .baz {
2117
- g: h; } }
2118
-
2119
- .other {
2120
- i: j; }
2121
- CSS
2122
- .foo
2123
- a: b
2124
- @media bar
2125
- c: d
2126
- .baz
2127
- e: f
2128
- @media bip
2129
- g: h
2130
-
2131
- .other
2132
- i: j
2133
- SASS
2134
-
2135
- assert_equal <<CSS, render(<<SASS, :style => :compact)
2136
- .foo { a: b; }
2137
- @media bar { .foo { c: d; } }
2138
- .foo .baz { e: f; }
2139
- @media bip { .foo .baz { g: h; } }
2140
-
2141
- .other { i: j; }
2142
- CSS
2143
- .foo
2144
- a: b
2145
- @media bar
2146
- c: d
2147
- .baz
2148
- e: f
2149
- @media bip
2150
- g: h
2151
-
2152
- .other
2153
- i: j
2154
- SASS
2155
-
2156
- assert_equal <<CSS, render(<<SASS, :style => :expanded)
2157
- .foo {
2158
- a: b;
2159
- }
2160
- @media bar {
2161
- .foo {
2162
- c: d;
2163
- }
2164
- }
2165
- .foo .baz {
2166
- e: f;
2167
- }
2168
- @media bip {
2169
- .foo .baz {
2170
- g: h;
2171
- }
2172
- }
2173
-
2174
- .other {
2175
- i: j;
2176
- }
2177
- CSS
2178
- .foo
2179
- a: b
2180
- @media bar
2181
- c: d
2182
- .baz
2183
- e: f
2184
- @media bip
2185
- g: h
2186
-
2187
- .other
2188
- i: j
2189
- SASS
2190
- end
2191
-
2192
- def test_double_media_bubbling
2193
- assert_equal <<CSS, render(<<SASS)
2194
- @media bar and (a: b) {
2195
- .foo {
2196
- c: d; } }
2197
- CSS
2198
- @media bar
2199
- @media (a: b)
2200
- .foo
2201
- c: d
2202
- SASS
2203
-
2204
- assert_equal <<CSS, render(<<SASS)
2205
- @media bar {
2206
- .foo {
2207
- a: b; } }
2208
- @media bar and (a: b) {
2209
- .foo {
2210
- c: d; } }
2211
- CSS
2212
- .foo
2213
- @media bar
2214
- a: b
2215
- @media (a: b)
2216
- c: d
2217
- SASS
2218
- end
2219
-
2220
- def test_double_media_bubbling_with_commas
2221
- assert_equal <<CSS, render(<<SASS)
2222
- @media (a: b) and (e: f), (c: d) and (e: f), (a: b) and (g: h), (c: d) and (g: h) {
2223
- .foo {
2224
- c: d; } }
2225
- CSS
2226
- @media (a: b), (c: d)
2227
- @media (e: f), (g: h)
2228
- .foo
2229
- c: d
2230
- SASS
2231
- end
2232
-
2233
- def test_rule_media_rule_bubbling
2234
- assert_equal <<CSS, render(<<SASS)
2235
- @media bar {
2236
- .foo {
2237
- a: b;
2238
- e: f; }
2239
- .foo .baz {
2240
- c: d; } }
2241
- CSS
2242
- .foo
2243
- @media bar
2244
- a: b
2245
- .baz
2246
- c: d
2247
- e: f
2248
- SASS
2249
- end
2250
-
2251
- def test_nested_media_around_properties
2252
- assert_equal <<CSS, render(<<SASS)
2253
- .outside {
2254
- color: red;
2255
- background: blue; }
2256
- @media print {
2257
- .outside {
2258
- color: black; } }
2259
- @media print and (a: b) {
2260
- .outside .inside {
2261
- border: 1px solid black; } }
2262
- .outside .middle {
2263
- display: block; }
2264
- CSS
2265
- .outside
2266
- color: red
2267
- @media print
2268
- color: black
2269
- .inside
2270
- @media (a: b)
2271
- border: 1px solid black
2272
- background: blue
2273
- .middle
2274
- display: block
2275
- SASS
2276
- end
2277
-
2278
- def test_media_with_parent_references
2279
- sass_str = <<SASS
2280
- .outside
2281
- @media print
2282
- &.inside
2283
- border: 1px solid black
2284
- SASS
2285
- css_str = <<CSS
2286
- @media print {
2287
- .outside.inside {
2288
- border: 1px solid black; } }
2289
- CSS
2290
- assert_equal css_str, render(sass_str)
2291
- end
2292
-
2293
- def test_eliminated_media_bubbling
2294
- assert_equal <<CSS, render(<<SASS)
2295
- @media screen {
2296
- a: b; }
2297
- CSS
2298
- @media screen
2299
- a: b
2300
- @media print
2301
- c: d
2302
- SASS
2303
-
2304
- assert_equal <<CSS, render(<<SASS)
2305
- @media not print {
2306
- a: b; }
2307
- CSS
2308
- @media not print
2309
- a: b
2310
- @media print
2311
- c: d
2312
- SASS
2313
-
2314
- assert_equal <<CSS, render(<<SASS)
2315
- @media not print {
2316
- a: b; }
2317
- CSS
2318
- @media not print
2319
- a: b
2320
- @media not screen
2321
- c: d
2322
- SASS
2323
- end
2324
-
2325
- def test_non_eliminated_media_bubbling
2326
- assert_equal <<CSS, render(<<SASS)
2327
- @media screen {
2328
- a: b; }
2329
- @media screen and (a: b) {
2330
- c: d; }
2331
- CSS
2332
- @media screen
2333
- a: b
2334
- @media screen and (a: b)
2335
- c: d
2336
- SASS
2337
-
2338
- assert_equal <<CSS, render(<<SASS)
2339
- @media not print {
2340
- a: b; }
2341
- @media screen {
2342
- c: d; }
2343
- CSS
2344
- @media not print
2345
- a: b
2346
- @media screen
2347
- c: d
2348
- SASS
2349
-
2350
- assert_equal <<CSS, render(<<SASS)
2351
- @media only screen {
2352
- a: b; }
2353
- @media only screen and (a: b) {
2354
- c: d; }
2355
- CSS
2356
- @media only screen
2357
- a: b
2358
- @media screen and (a: b)
2359
- c: d
2360
- SASS
2361
- end
2362
-
2363
- def test_directive_interpolation
2364
- assert_equal <<CSS, render(<<SASS)
2365
- @foo bar12 qux {
2366
- a: b; }
2367
- CSS
2368
- $baz: 12
2369
- @foo bar\#{$baz} qux
2370
- a: b
2371
- SASS
2372
- end
2373
-
2374
- def test_media_interpolation
2375
- assert_equal <<CSS, render(<<SASS)
2376
- @media bar12 {
2377
- a: b; }
2378
- CSS
2379
- $baz: 12
2380
- @media bar\#{$baz}
2381
- a: b
2382
- SASS
2383
- end
2384
-
2385
- def test_variables_in_media
2386
- assert_equal <<CSS, render(<<SASS)
2387
- @media screen and (-webkit-min-device-pixel-ratio-foo: 25), only print {
2388
- a: b; }
2389
- CSS
2390
- $media1: screen
2391
- $media2: print
2392
- $var: -webkit-min-device-pixel-ratio
2393
- $val: 20
2394
- @media \#{$media1} and ($var + "-foo": $val + 5), only \#{$media2}
2395
- a: b
2396
- SASS
2397
- end
2398
-
2399
- # Regression tests
2400
-
2401
- def test_parent_mixin_in_content_nested
2402
- assert_equal(<<CSS, render(<<SASS))
2403
- a {
2404
- b: c; }
2405
- CSS
2406
- =foo
2407
- @content
2408
-
2409
- =bar
2410
- +foo
2411
- +foo
2412
- a
2413
- b: c
2414
-
2415
- +bar
2416
- SASS
2417
- end
2418
-
2419
- def test_supports_bubbles
2420
- assert_equal <<CSS, render(<<SASS)
2421
- parent {
2422
- background: orange; }
2423
- @supports (perspective: 10px) or (-moz-perspective: 10px) {
2424
- parent child {
2425
- background: blue; } }
2426
- CSS
2427
- parent
2428
- background: orange
2429
- @supports (perspective: 10px) or (-moz-perspective: 10px)
2430
- child
2431
- background: blue
2432
- SASS
2433
- end
2434
-
2435
- def test_line_numbers_with_dos_line_endings
2436
- assert_equal <<CSS, render(<<SASS, :line_comments => true)
2437
- /* line 5, test_line_numbers_with_dos_line_endings_inline.sass */
2438
- .foo {
2439
- a: b; }
2440
- CSS
2441
- \r
2442
- \r
2443
- \r
2444
- \r
2445
- .foo
2446
- a: b
2447
- SASS
2448
- end
2449
-
2450
- def test_variable_in_media_in_mixin
2451
- assert_equal <<CSS, render(<<SASS)
2452
- @media screen and (min-width: 10px) {
2453
- body {
2454
- background: red; } }
2455
- @media screen and (min-width: 20px) {
2456
- body {
2457
- background: blue; } }
2458
- CSS
2459
- @mixin respond-to($width)
2460
- @media screen and (min-width: $width)
2461
- @content
2462
-
2463
- body
2464
- @include respond-to(10px)
2465
- background: red
2466
- @include respond-to(20px)
2467
- background: blue
2468
- SASS
2469
- end
2470
-
2471
- def test_tricky_mixin_loop_exception
2472
- render <<SASS
2473
- @mixin foo($a)
2474
- @if $a
2475
- @include foo(false)
2476
- @include foo(true)
2477
- @else
2478
- a: b
2479
-
2480
- a
2481
- @include foo(true)
2482
- SASS
2483
- assert(false, "Exception not raised")
2484
- rescue Sass::SyntaxError => err
2485
- assert_equal("An @include loop has been found: foo includes itself", err.message)
2486
- assert_hash_has(err.sass_backtrace[0], :mixin => "foo", :line => 3)
2487
- end
2488
-
2489
- def test_interpolated_comment_in_mixin
2490
- assert_equal <<CSS, render(<<SASS)
2491
- /*! color: red */
2492
- .foo {
2493
- color: red; }
2494
-
2495
- /*! color: blue */
2496
- .foo {
2497
- color: blue; }
2498
-
2499
- /*! color: green */
2500
- .foo {
2501
- color: green; }
2502
- CSS
2503
- =foo($var)
2504
- /*! color: \#{$var}
2505
- .foo
2506
- color: $var
2507
-
2508
- +foo(red)
2509
- +foo(blue)
2510
- +foo(green)
2511
- SASS
2512
- end
2513
-
2514
- def test_parens_in_mixins
2515
- assert_equal(<<CSS, render(<<SASS))
2516
- .foo {
2517
- color: #01ff7f;
2518
- background-color: #000102; }
2519
- CSS
2520
- =foo($c1, $c2: rgb(0, 1, 2))
2521
- color: $c1
2522
- background-color: $c2
2523
-
2524
- .foo
2525
- +foo(rgb(1,255,127))
2526
- SASS
2527
- end
2528
-
2529
- def test_comment_beneath_prop
2530
- assert_equal(<<RESULT, render(<<SOURCE))
2531
- .box {
2532
- border-style: solid; }
2533
- RESULT
2534
- .box
2535
- :border
2536
- //:color black
2537
- :style solid
2538
- SOURCE
2539
-
2540
- assert_equal(<<RESULT, render(<<SOURCE))
2541
- .box {
2542
- /* :color black */
2543
- border-style: solid; }
2544
- RESULT
2545
- .box
2546
- :border
2547
- /* :color black
2548
- :style solid
2549
- SOURCE
2550
-
2551
- assert_equal(<<RESULT, render(<<SOURCE, :style => :compressed))
2552
- .box{border-style:solid}
2553
- RESULT
2554
- .box
2555
- :border
2556
- /*:color black
2557
- :style solid
2558
- SOURCE
2559
- end
2560
-
2561
- def test_compressed_comment_beneath_directive
2562
- assert_equal(<<RESULT, render(<<SOURCE, :style => :compressed))
2563
- @foo{a:b}
2564
- RESULT
2565
- @foo
2566
- a: b
2567
- /*b: c
2568
- SOURCE
2569
- end
2570
-
2571
- def test_comment_with_crazy_indentation
2572
- assert_equal(<<CSS, render(<<SASS))
2573
- /* This is a loud comment:
2574
- * Where the indentation is wonky. */
2575
- .comment {
2576
- width: 1px; }
2577
- CSS
2578
- /*
2579
- This is a loud comment:
2580
- Where the indentation is wonky.
2581
- //
2582
- This is a silent comment:
2583
- Where the indentation is wonky.
2584
- .comment
2585
- width: 1px
2586
- SASS
2587
- end
2588
-
2589
- def test_plus_with_space
2590
- assert_equal(<<CSS, render(<<SASS))
2591
- a + b {
2592
- color: green; }
2593
- CSS
2594
- a
2595
- + b
2596
- color: green
2597
- SASS
2598
- end
2599
-
2600
- def test_empty_line_comment
2601
- assert_equal(<<CSS, render(<<SASS))
2602
- /* Foo
2603
- *
2604
- * Bar */
2605
- CSS
2606
- /*
2607
- Foo
2608
-
2609
- Bar
2610
- SASS
2611
- end
2612
-
2613
- def test_empty_comment
2614
- assert_equal(<<CSS, render(<<SASS))
2615
- /* */
2616
- a {
2617
- /* */
2618
- b: c; }
2619
- CSS
2620
- /*
2621
- a
2622
- /*
2623
- b: c
2624
- SASS
2625
- end
2626
-
2627
- def test_options_available_in_environment
2628
- assert_equal(<<CSS, render(<<SASS))
2629
- a {
2630
- b: nested; }
2631
- CSS
2632
- a
2633
- b: option("style")
2634
- SASS
2635
- end
2636
-
2637
- def test_mixin_no_arg_error
2638
- assert_raise_message(Sass::SyntaxError, 'Invalid CSS after "($bar,": expected variable (e.g. $foo), was ")"') do
2639
- render(<<SASS)
2640
- =foo($bar,)
2641
- bip: bap
2642
- SASS
2643
- end
2644
- end
2645
-
2646
- def test_import_with_commas_in_url
2647
- assert_equal <<CSS, render(<<SASS)
2648
- @import url(foo.css?bar,baz);
2649
- CSS
2650
- @import url(foo.css?bar,baz)
2651
- SASS
2652
- end
2653
-
2654
- def test_silent_comment_in_prop_val_after_important
2655
- assert_equal(<<CSS, render(<<SASS))
2656
- .advanced {
2657
- display: none !important; }
2658
- CSS
2659
- .advanced
2660
- display: none !important // yeah, yeah. it's not really a style anyway.
2661
- SASS
2662
- end
2663
-
2664
- def test_mixin_with_keyword_args
2665
- assert_equal <<CSS, render(<<SASS)
2666
- .mixed {
2667
- required: foo;
2668
- arg1: default-val1;
2669
- arg2: non-default-val2; }
2670
- CSS
2671
- =a-mixin($required, $arg1: default-val1, $arg2: default-val2)
2672
- required: $required
2673
- arg1: $arg1
2674
- arg2: $arg2
2675
- .mixed
2676
- +a-mixin(foo, $arg2: non-default-val2)
2677
- SASS
2678
- end
2679
-
2680
- def test_mixin_with_keyword_arg_variable_value
2681
- assert_equal <<CSS, render(<<SASS)
2682
- .mixed {
2683
- required: foo;
2684
- arg1: default-val1;
2685
- arg2: a-value; }
2686
- CSS
2687
- =a-mixin($required, $arg1: default-val1, $arg2: default-val2)
2688
- required: $required
2689
- arg1: $arg1
2690
- arg2: $arg2
2691
- .mixed
2692
- $a-value: a-value
2693
- +a-mixin(foo, $arg2: $a-value)
2694
- SASS
2695
- end
2696
-
2697
- def test_mixin_keyword_args_handle_variable_underscore_dash_equivalence
2698
- assert_equal <<CSS, render(<<SASS)
2699
- .mixed {
2700
- required: foo;
2701
- arg1: non-default-val1;
2702
- arg2: non-default-val2; }
2703
- CSS
2704
- =a-mixin($required, $arg-1: default-val1, $arg_2: default-val2)
2705
- required: $required
2706
- arg1: $arg_1
2707
- arg2: $arg-2
2708
- .mixed
2709
- +a-mixin(foo, $arg-2: non-default-val2, $arg_1: non-default-val1)
2710
- SASS
2711
- end
2712
-
2713
- def test_passing_required_args_as_a_keyword_arg
2714
- assert_equal <<CSS, render(<<SASS)
2715
- .mixed {
2716
- required: foo;
2717
- arg1: default-val1;
2718
- arg2: default-val2; }
2719
- CSS
2720
- =a-mixin($required, $arg1: default-val1, $arg2: default-val2)
2721
- required: $required
2722
- arg1: $arg1
2723
- arg2: $arg2
2724
- .mixed
2725
- +a-mixin($required: foo)
2726
- SASS
2727
- end
2728
-
2729
- def test_passing_all_as_keyword_args_in_opposite_order
2730
- assert_equal <<CSS, render(<<SASS)
2731
- .mixed {
2732
- required: foo;
2733
- arg1: non-default-val1;
2734
- arg2: non-default-val2; }
2735
- CSS
2736
- =a-mixin($required, $arg1: default-val1, $arg2: default-val2)
2737
- required: $required
2738
- arg1: $arg1
2739
- arg2: $arg2
2740
- .mixed
2741
- +a-mixin($arg2: non-default-val2, $arg1: non-default-val1, $required: foo)
2742
- SASS
2743
- end
2744
-
2745
- def test_function_output_with_comma
2746
- assert_equal <<CSS, render(<<SASS)
2747
- foo {
2748
- a: b(c), d(e); }
2749
- CSS
2750
- foo
2751
- a: b(c), d(e)
2752
- SASS
2753
- end
2754
-
2755
- def test_interpolation_with_comma
2756
- assert_equal <<CSS, render(<<SASS)
2757
- foo {
2758
- a: foo, bar; }
2759
- CSS
2760
- $foo: foo
2761
- foo
2762
- a: \#{$foo}, bar
2763
- SASS
2764
- end
2765
-
2766
- def test_string_interpolation_with_comma
2767
- assert_equal <<CSS, render(<<SASS)
2768
- foo {
2769
- a: "bip foo bap", bar; }
2770
- CSS
2771
- $foo: foo
2772
- foo
2773
- a: "bip \#{$foo} bap", bar
2774
- SASS
2775
- end
2776
-
2777
- def test_unknown_directive
2778
- assert_equal <<CSS, render(<<SASS)
2779
- @baz {
2780
- c: d; }
2781
- CSS
2782
- @baz
2783
- c: d
2784
- SASS
2785
- end
2786
-
2787
- def test_loud_comment_interpolations_can_be_escaped
2788
- assert_equal <<CSS, render(<<SASS)
2789
- /* \#{foo} */
2790
- CSS
2791
- /* \\\#{foo}
2792
- SASS
2793
- assert_equal <<CSS, render(<<SASS)
2794
- /*! \#{foo} */
2795
- CSS
2796
- /*! \\\#{foo}
2797
- SASS
2798
- end
2799
-
2800
- def test_selector_compression
2801
- assert_equal <<CSS, render(<<SASS, :style => :compressed)
2802
- a>b,c+d,:-moz-any(e,f,g){h:i}
2803
- CSS
2804
- a > b, c + d, :-moz-any(e, f, g)
2805
- h: i
2806
- SASS
2807
- end
2808
-
2809
- def test_comment_like_selector
2810
- assert_raise_message(Sass::SyntaxError, 'Invalid CSS after "/": expected identifier, was " foo"') {render(<<SASS)}
2811
- / foo
2812
- a: b
2813
- SASS
2814
- end
2815
-
2816
- def test_nested_empty_directive
2817
- assert_equal <<CSS, render(<<SASS)
2818
- @media screen {
2819
- .foo {
2820
- a: b; }
2821
-
2822
- @unknown-directive; }
2823
- CSS
2824
- @media screen
2825
- .foo
2826
- a: b
2827
-
2828
- @unknown-directive
2829
- SASS
2830
- end
2831
-
2832
- # Encodings
2833
-
2834
- unless Sass::Util.ruby1_8?
2835
- def test_encoding_error
2836
- render("foo\nbar\nb\xFEaz".force_encoding("utf-8"))
2837
- assert(false, "Expected exception")
2838
- rescue Sass::SyntaxError => e
2839
- assert_equal(3, e.sass_line)
2840
- assert_equal('Invalid UTF-8 character "\xFE"', e.message)
2841
- end
2842
-
2843
- def test_ascii_incompatible_encoding_error
2844
- template = "foo\nbar\nb_z".encode("utf-16le")
2845
- template[9] = "\xFE".force_encoding("utf-16le")
2846
- render(template)
2847
- assert(false, "Expected exception")
2848
- rescue Sass::SyntaxError => e
2849
- assert_equal(3, e.sass_line)
2850
- assert_equal('Invalid UTF-16LE character "\xFE"', e.message)
2851
- end
2852
-
2853
- def test_same_charset_as_encoding
2854
- assert_renders_encoded(<<CSS, <<SASS)
2855
- @charset "UTF-8";
2856
- fóó {
2857
- a: b; }
2858
- CSS
2859
- @charset "utf-8"
2860
- fóó
2861
- a: b
2862
- SASS
2863
- end
2864
-
2865
- def test_different_charset_than_encoding
2866
- assert_renders_encoded(<<CSS.force_encoding("IBM866"), <<SASS)
2867
- @charset "IBM866";
2868
- fóó {
2869
- a: b; }
2870
- CSS
2871
- @charset "ibm866"
2872
- fóó
2873
- a: b
2874
- SASS
2875
- end
2876
-
2877
- def test_different_encoding_than_system
2878
- assert_renders_encoded(<<CSS.encode("IBM866"), <<SASS.encode("IBM866"))
2879
- @charset "IBM866";
2880
- тАЬ {
2881
- a: b; }
2882
- CSS
2883
- тАЬ
2884
- a: b
2885
- SASS
2886
- end
2887
-
2888
- def test_multibyte_charset
2889
- assert_renders_encoded(<<CSS.encode("UTF-16LE"), <<SASS.encode("UTF-16LE").force_encoding("UTF-8"))
2890
- @charset "UTF-16LE";
2891
- fóó {
2892
- a: b; }
2893
- CSS
2894
- @charset "utf-16le"
2895
- fóó
2896
- a: b
2897
- SASS
2898
- end
2899
-
2900
- def test_multibyte_charset_without_endian_specifier
2901
- assert_renders_encoded(<<CSS.encode("UTF-32BE"), <<SASS.encode("UTF-32BE").force_encoding("UTF-8"))
2902
- @charset "UTF-32BE";
2903
- fóó {
2904
- a: b; }
2905
- CSS
2906
- @charset "utf-32"
2907
- fóó
2908
- a: b
2909
- SASS
2910
- end
2911
-
2912
- def test_utf8_bom
2913
- assert_renders_encoded(<<CSS, <<SASS.force_encoding("BINARY"))
2914
- @charset "UTF-8";
2915
- fóó {
2916
- a: b; }
2917
- CSS
2918
- \uFEFFfóó
2919
- a: b
2920
- SASS
2921
- end
2922
-
2923
- def test_utf16le_bom
2924
- assert_renders_encoded(<<CSS.encode("UTF-16LE"), <<SASS.encode("UTF-16LE").force_encoding("BINARY"))
2925
- @charset "UTF-16LE";
2926
- fóó {
2927
- a: b; }
2928
- CSS
2929
- \uFEFFfóó
2930
- a: b
2931
- SASS
2932
- end
2933
-
2934
- def test_utf32be_bom
2935
- assert_renders_encoded(<<CSS.encode("UTF-32BE"), <<SASS.encode("UTF-32BE").force_encoding("BINARY"))
2936
- @charset "UTF-32BE";
2937
- fóó {
2938
- a: b; }
2939
- CSS
2940
- \uFEFFfóó
2941
- a: b
2942
- SASS
2943
- end
2944
-
2945
- # Encoding Regression Test
2946
-
2947
- def test_multibyte_prop_name
2948
- assert_equal(<<CSS, render(<<SASS))
2949
- @charset "UTF-8";
2950
- #bar {
2951
- cölor: blue; }
2952
- CSS
2953
- #bar
2954
- cölor: blue
2955
- SASS
2956
- end
2957
-
2958
- def test_multibyte_and_interpolation
2959
- assert_equal(<<CSS, render(<<SCSS, :syntax => :scss))
2960
- #bar {
2961
- background: a 0%; }
2962
- CSS
2963
- #bar {
2964
- // 
2965
- background: \#{a} 0%;
2966
- }
2967
- SCSS
2968
- end
2969
- end
2970
-
2971
- def test_original_filename_set
2972
- importer = MockImporter.new
2973
- importer.add_import("imported", "div{color:red}")
2974
-
2975
- original_filename = filename_for_test
2976
- engine = Sass::Engine.new('@import "imported"; div{color:blue}',
2977
- :filename => original_filename, :load_paths => [importer], :syntax => :scss, :importer => importer)
2978
- engine.render
2979
-
2980
- assert_equal original_filename, engine.options[:original_filename]
2981
- assert_equal original_filename, importer.engine("imported").options[:original_filename]
2982
- end
2983
-
2984
- def test_deprecated_PRECISION
2985
- assert_warning(<<END) {assert_equal 100_000.0, Sass::Script::Number::PRECISION}
2986
- Sass::Script::Number::PRECISION is deprecated and will be removed in a future release. Use Sass::Script::Number.precision_factor instead.
2987
- END
2988
- end
2989
-
2990
- def test_changing_precision
2991
- old_precision = Sass::Script::Number.precision
2992
- begin
2993
- Sass::Script::Number.precision = 8
2994
- assert_equal <<CSS, render(<<SASS)
2995
- div {
2996
- maximum: 1.00000001;
2997
- too-much: 1.0; }
2998
- CSS
2999
- div
3000
- maximum : 1.00000001
3001
- too-much: 1.000000001
3002
- SASS
3003
- ensure
3004
- Sass::Script::Number.precision = old_precision
3005
- end
3006
- end
3007
-
3008
- def test_content
3009
- assert_equal <<CSS, render(<<SASS)
3010
- .children {
3011
- background-color: red;
3012
- color: blue;
3013
- border-color: red; }
3014
- CSS
3015
- $color: blue
3016
- =context($class, $color: red)
3017
- .\#{$class}
3018
- background-color: $color
3019
- @content
3020
- border-color: $color
3021
- +context(children)
3022
- color: $color
3023
- SASS
3024
- end
3025
-
3026
- def test_selector_in_content
3027
- assert_equal <<CSS, render(<<SASS)
3028
- .parent {
3029
- background-color: red;
3030
- border-color: red; }
3031
- .parent .children {
3032
- color: blue; }
3033
- CSS
3034
- $color: blue
3035
- =context($class, $color: red)
3036
- .\#{$class}
3037
- background-color: $color
3038
- @content
3039
- border-color: $color
3040
- +context(parent)
3041
- .children
3042
- color: $color
3043
- SASS
3044
- end
3045
-
3046
- def test_using_parent_mixin_in_content
3047
- assert_equal <<CSS, render(<<SASS)
3048
- .parent {
3049
- before-color: red;
3050
- after-color: red; }
3051
- .parent .sibling {
3052
- before-color: yellow;
3053
- after-color: yellow; }
3054
- .parent .sibling .child {
3055
- before-color: green;
3056
- color: blue;
3057
- after-color: green; }
3058
- CSS
3059
- $color: blue
3060
- =context($class, $color: red)
3061
- .\#{$class}
3062
- before-color: $color
3063
- @content
3064
- after-color: $color
3065
- +context(parent)
3066
- +context(sibling, $color: yellow)
3067
- +context(child, $color: green)
3068
- color: $color
3069
- SASS
3070
- end
3071
-
3072
- def test_content_more_than_once
3073
- assert_equal <<CSS, render(<<SASS)
3074
- .once {
3075
- color: blue; }
3076
-
3077
- .twice {
3078
- color: blue; }
3079
- CSS
3080
- $color: blue
3081
- =context($class, $color: red)
3082
- .once
3083
- @content
3084
- .twice
3085
- @content
3086
- +context(parent)
3087
- color: $color
3088
- SASS
3089
- end
3090
-
3091
- def test_content_with_variable
3092
- assert_equal <<CSS, render(<<SASS)
3093
- .foo {
3094
- a: 1px; }
3095
- CSS
3096
- =foo
3097
- .foo
3098
- @content
3099
- +foo
3100
- $a: 1px
3101
- a: $a
3102
- SASS
3103
- end
3104
-
3105
- def test_nested_content_blocks
3106
- assert_equal <<CSS, render(<<SASS)
3107
- .foo {
3108
- a: foo; }
3109
- .foo .bar {
3110
- a: bar; }
3111
- .foo .bar .baz {
3112
- a: baz; }
3113
- .foo .bar .baz .outside {
3114
- a: outside;
3115
- color: red; }
3116
- CSS
3117
- $a: outside
3118
- =baz($a: baz)
3119
- .baz
3120
- a: $a
3121
- @content
3122
- =bar($a: bar)
3123
- .bar
3124
- a: $a
3125
- +baz
3126
- @content
3127
- =foo($a: foo)
3128
- .foo
3129
- a: $a
3130
- +bar
3131
- @content
3132
- +foo
3133
- .outside
3134
- a: $a
3135
- color: red
3136
- SASS
3137
- end
3138
-
3139
- def test_content_not_seen_through_mixin
3140
- assert_equal <<CSS, render(<<SASS)
3141
- a foo {
3142
- mixin: foo;
3143
- a: b; }
3144
- a foo bar {
3145
- mixin: bar; }
3146
- CSS
3147
- =foo
3148
- foo
3149
- mixin: foo
3150
- @content
3151
- +bar
3152
- =bar
3153
- bar
3154
- mixin: bar
3155
- @content
3156
- a
3157
- +foo
3158
- a: b
3159
- SASS
3160
- end
3161
-
3162
- def test_content_backtrace_for_perform
3163
- render(<<SASS)
3164
- =foo
3165
- @content
3166
-
3167
- a
3168
- +foo
3169
- b: 1em + 2px
3170
- SASS
3171
- assert(false, "Expected exception")
3172
- rescue Sass::SyntaxError => e
3173
- assert_equal([
3174
- {:mixin => '@content', :line => 6, :filename => 'test_content_backtrace_for_perform_inline.sass'},
3175
- {:mixin => 'foo', :line => 2, :filename => 'test_content_backtrace_for_perform_inline.sass'},
3176
- {:line => 5, :filename => 'test_content_backtrace_for_perform_inline.sass'},
3177
- ], e.sass_backtrace)
3178
- end
3179
-
3180
- def test_content_backtrace_for_cssize
3181
- render(<<SASS)
3182
- =foo
3183
- @content
3184
-
3185
- a
3186
- +foo
3187
- @extend foo bar baz
3188
- SASS
3189
- assert(false, "Expected exception")
3190
- rescue Sass::SyntaxError => e
3191
- assert_equal([
3192
- {:mixin => '@content', :line => 6, :filename => 'test_content_backtrace_for_cssize_inline.sass'},
3193
- {:mixin => 'foo', :line => 2, :filename => 'test_content_backtrace_for_cssize_inline.sass'},
3194
- {:line => 5, :filename => 'test_content_backtrace_for_cssize_inline.sass'},
3195
- ], e.sass_backtrace)
3196
- end
3197
-
3198
- private
3199
-
3200
- def assert_hash_has(hash, expected)
3201
- expected.each {|k, v| assert_equal(v, hash[k])}
3202
- end
3203
-
3204
- def assert_renders_encoded(css, sass)
3205
- result = render(sass)
3206
- assert_equal css.encoding, result.encoding
3207
- assert_equal css, result
3208
- end
3209
-
3210
- def render(sass, options = {})
3211
- munge_filename options
3212
- options[:importer] ||= MockImporter.new
3213
- Sass::Engine.new(sass, options).render
3214
- end
3215
-
3216
- def renders_correctly(name, options={})
3217
- sass_file = load_file(name, "sass")
3218
- css_file = load_file(name, "css")
3219
- options[:filename] ||= filename(name, "sass")
3220
- options[:syntax] ||= :sass
3221
- options[:css_filename] ||= filename(name, "css")
3222
- css_result = Sass::Engine.new(sass_file, options).render
3223
- assert_equal css_file, css_result
3224
- end
3225
-
3226
- def load_file(name, type = "sass")
3227
- @result = ''
3228
- File.new(filename(name, type)).each_line { |l| @result += l }
3229
- @result
3230
- end
3231
-
3232
- def filename(name, type)
3233
- File.dirname(__FILE__) + "/#{type == 'sass' ? 'templates' : 'results'}/#{name}.#{type}"
3234
- end
3235
-
3236
- def sassc_path(template)
3237
- sassc_path = File.join(File.dirname(__FILE__) + "/templates/#{template}.sass")
3238
- engine = Sass::Engine.new("", :filename => sassc_path,
3239
- :importer => Sass::Importers::Filesystem.new("."))
3240
- key = engine.send(:sassc_key)
3241
- File.join(engine.options[:cache_location], key)
3242
- end
3243
- end
3244
-