css_parser_master 1.2.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.gitignore +4 -0
- data/CHANGELOG +34 -0
- data/LICENSE +21 -0
- data/README +0 -0
- data/README.rdoc +77 -0
- data/Rakefile.rb +18 -0
- data/VERSION +1 -0
- data/lib/css_parser_master.rb +156 -0
- data/lib/css_parser_master/declaration.rb +31 -0
- data/lib/css_parser_master/declaration_api.rb +91 -0
- data/lib/css_parser_master/declarations.rb +23 -0
- data/lib/css_parser_master/parser.rb +388 -0
- data/lib/css_parser_master/regexps.rb +46 -0
- data/lib/css_parser_master/rule_set.rb +337 -0
- data/lib/css_parser_master/selector.rb +33 -0
- data/lib/css_parser_master/selectors.rb +27 -0
- data/test/fixtures/import-circular-reference.css +4 -0
- data/test/fixtures/import-with-media-types.css +3 -0
- data/test/fixtures/import1.css +3 -0
- data/test/fixtures/simple.css +6 -0
- data/test/fixtures/subdir/import2.css +3 -0
- data/test/test_css_parser_basic.rb +84 -0
- data/test/test_css_parser_loading.rb +110 -0
- data/test/test_css_parser_media_types.rb +71 -0
- data/test/test_css_parser_misc.rb +151 -0
- data/test/test_css_parser_regexps.rb +69 -0
- data/test/test_helper.rb +6 -0
- data/test/test_merging.rb +88 -0
- data/test/test_rule_set.rb +90 -0
- data/test/test_rule_set_creating_shorthand.rb +90 -0
- data/test/test_rule_set_expanding_shorthand.rb +179 -0
- data/test/test_ruleset_expand.rb +40 -0
- data/test/test_selector.rb +26 -0
- data/test/test_selector_parsing.rb +27 -0
- metadata +112 -0
@@ -0,0 +1,33 @@
|
|
1
|
+
require 'css_parser_master/declaration_api'
|
2
|
+
|
3
|
+
module CssParserMaster
|
4
|
+
class Selector
|
5
|
+
include CssParserMaster::DeclarationAPI
|
6
|
+
|
7
|
+
attr_accessor :selector, :declarations, :specificity
|
8
|
+
|
9
|
+
def initialize(selector, declarations, specificity)
|
10
|
+
@selector = selector
|
11
|
+
@order = 0
|
12
|
+
@declarations = {}
|
13
|
+
parse_declarations!(declarations)
|
14
|
+
# puts "init @declarations: #{@declarations}"
|
15
|
+
@specificity = specificity
|
16
|
+
end
|
17
|
+
|
18
|
+
def declarations_to_s(options = {})
|
19
|
+
# puts "declarations_to_s: #{declarations.inspect}"
|
20
|
+
s = declarations.map do |decl|
|
21
|
+
decl[1].to_text
|
22
|
+
end.join('')
|
23
|
+
# puts "res: #{s}"
|
24
|
+
s
|
25
|
+
end
|
26
|
+
|
27
|
+
|
28
|
+
def to_text
|
29
|
+
"#{selector}\n{\n#{declarations_to_s}\n} \n"
|
30
|
+
end
|
31
|
+
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
module CssParserMaster
|
2
|
+
class Selectors
|
3
|
+
include Enumerable
|
4
|
+
|
5
|
+
attr_reader :selectors
|
6
|
+
|
7
|
+
def << selector
|
8
|
+
selectors << selector
|
9
|
+
end
|
10
|
+
|
11
|
+
def all
|
12
|
+
map{|sel| sel.split(',') }
|
13
|
+
end
|
14
|
+
|
15
|
+
def each
|
16
|
+
selectors.each { |sel| yield sel }
|
17
|
+
end
|
18
|
+
|
19
|
+
def empty?
|
20
|
+
selectors.empty?
|
21
|
+
end
|
22
|
+
|
23
|
+
def initialize(selectors = [])
|
24
|
+
@selectors = selectors
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
@@ -0,0 +1,84 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper'
|
2
|
+
|
3
|
+
# Test cases for reading and generating CSS shorthand properties
|
4
|
+
class CssParserBasicTests < Test::Unit::TestCase
|
5
|
+
include CssParser
|
6
|
+
|
7
|
+
def setup
|
8
|
+
@cp = CssParser::Parser.new
|
9
|
+
@css = <<-EOT
|
10
|
+
html, body, p { margin: 0px; }
|
11
|
+
p { padding: 0px; }
|
12
|
+
#content { font: 12px/normal sans-serif; }
|
13
|
+
EOT
|
14
|
+
end
|
15
|
+
|
16
|
+
def test_finding_by_selector
|
17
|
+
@cp.add_block!(@css)
|
18
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('body').join(' ')
|
19
|
+
assert_equal 'margin: 0px; padding: 0px;', @cp.find_by_selector('p').join(' ')
|
20
|
+
end
|
21
|
+
|
22
|
+
def test_adding_block
|
23
|
+
@cp.add_block!(@css)
|
24
|
+
# @cp.selector_declarations do |sel, decl|
|
25
|
+
# puts "sel: #{sel.inspect}"
|
26
|
+
# puts "decl: #{decl.inspect}"
|
27
|
+
# end
|
28
|
+
|
29
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('body').join
|
30
|
+
end
|
31
|
+
|
32
|
+
def test_adding_a_rule
|
33
|
+
@cp.add_rule!('div', 'color: blue;')
|
34
|
+
|
35
|
+
# @cp.selector_declarations do |sel, decl|
|
36
|
+
# puts "sel: #{sel.inspect}"
|
37
|
+
# puts "decl: #{decl.inspect}"
|
38
|
+
# end
|
39
|
+
|
40
|
+
assert_equal 'color: blue;', @cp.find_by_selector('div').join(' ')
|
41
|
+
end
|
42
|
+
|
43
|
+
def test_adding_a_rule_set
|
44
|
+
rs = CssParser::RuleSet.new('div', 'color: blue;')
|
45
|
+
@cp.add_rule_set!(rs)
|
46
|
+
assert_equal 'color: blue;', @cp.find_by_selector('div').join(' ')
|
47
|
+
end
|
48
|
+
|
49
|
+
def test_selector_declarations
|
50
|
+
expected = [
|
51
|
+
{:selector => "#content p", :declarations => "color: #fff;", :specificity => 101},
|
52
|
+
{:selector => "a", :declarations => "color: #fff;", :specificity => 1}
|
53
|
+
]
|
54
|
+
|
55
|
+
actual = []
|
56
|
+
rs = RuleSet.new('#content p, a', 'color: #fff;')
|
57
|
+
@cp.add_rule_set!(rs)
|
58
|
+
@cp.selector_declarations do |sel, decl|
|
59
|
+
# puts "sel: #{sel.to_text}"
|
60
|
+
# puts "decl: #{decl[1].to_text}"
|
61
|
+
end
|
62
|
+
# assert_equal(expected, actual)
|
63
|
+
end
|
64
|
+
|
65
|
+
|
66
|
+
def test_toggling_uri_conversion
|
67
|
+
# with conversion
|
68
|
+
cp_with_conversion = Parser.new(:absolute_paths => true)
|
69
|
+
cp_with_conversion.add_block!("body { background: url('../style/yellow.png?abc=123') };",
|
70
|
+
:base_uri => 'http://example.org/style/basic.css')
|
71
|
+
|
72
|
+
assert_equal "background: url('http://example.org/style/yellow.png?abc=123');",
|
73
|
+
cp_with_conversion['body'].join(' ')
|
74
|
+
|
75
|
+
# without conversion
|
76
|
+
cp_without_conversion = Parser.new(:absolute_paths => false)
|
77
|
+
cp_without_conversion.add_block!("body { background: url('../style/yellow.png?abc=123') };",
|
78
|
+
:base_uri => 'http://example.org/style/basic.css')
|
79
|
+
|
80
|
+
assert_equal "background: url('../style/yellow.png?abc=123');",
|
81
|
+
cp_without_conversion['body'].join(' ')
|
82
|
+
end
|
83
|
+
|
84
|
+
end
|
@@ -0,0 +1,110 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper'
|
2
|
+
|
3
|
+
# Test cases for the CssParser's loading functions.
|
4
|
+
class CssParserLoadingTests < Test::Unit::TestCase
|
5
|
+
include CssParser
|
6
|
+
include WEBrick
|
7
|
+
|
8
|
+
def setup
|
9
|
+
# from http://nullref.se/blog/2006/5/17/testing-with-webrick
|
10
|
+
@cp = Parser.new
|
11
|
+
|
12
|
+
@uri_base = 'http://localhost:12000'
|
13
|
+
|
14
|
+
www_root = File.dirname(__FILE__) + '/fixtures/'
|
15
|
+
|
16
|
+
@server_thread = Thread.new do
|
17
|
+
s = WEBrick::HTTPServer.new(:Port => 12000, :DocumentRoot => www_root, :Logger => Log.new(nil, BasicLog::FATAL), :AccessLog => [])
|
18
|
+
@port = s.config[:Port]
|
19
|
+
begin
|
20
|
+
s.start
|
21
|
+
ensure
|
22
|
+
s.shutdown
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
sleep 1 # ensure the server has time to load
|
27
|
+
end
|
28
|
+
|
29
|
+
def teardown
|
30
|
+
@server_thread.kill
|
31
|
+
@server_thread.join(5)
|
32
|
+
@server_thread = nil
|
33
|
+
end
|
34
|
+
|
35
|
+
def test_loading_a_local_file
|
36
|
+
file_name = File.dirname(__FILE__) + '/fixtures/simple.css'
|
37
|
+
@cp.load_file!(file_name)
|
38
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('p').join(' ')
|
39
|
+
end
|
40
|
+
|
41
|
+
def test_loading_a_remote_file
|
42
|
+
@cp.load_uri!("#{@uri_base}/simple.css")
|
43
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('p').join(' ')
|
44
|
+
end
|
45
|
+
|
46
|
+
def test_following_at_import_rules_local
|
47
|
+
base_dir = File.dirname(__FILE__) + '/fixtures'
|
48
|
+
@cp.load_file!('import1.css', base_dir)
|
49
|
+
|
50
|
+
# from '/import1.css'
|
51
|
+
assert_equal 'color: lime;', @cp.find_by_selector('div').join(' ')
|
52
|
+
|
53
|
+
# from '/subdir/import2.css'
|
54
|
+
assert_equal 'text-decoration: none;', @cp.find_by_selector('a').join(' ')
|
55
|
+
|
56
|
+
# from '/subdir/../simple.css'
|
57
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('p').join(' ')
|
58
|
+
end
|
59
|
+
|
60
|
+
def test_following_at_import_rules_remote
|
61
|
+
@cp.load_uri!("#{@uri_base}/import1.css")
|
62
|
+
|
63
|
+
# from '/import1.css'
|
64
|
+
assert_equal 'color: lime;', @cp.find_by_selector('div').join(' ')
|
65
|
+
|
66
|
+
# from '/subdir/import2.css'
|
67
|
+
assert_equal 'text-decoration: none;', @cp.find_by_selector('a').join(' ')
|
68
|
+
|
69
|
+
# from '/subdir/../simple.css'
|
70
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('p').join(' ')
|
71
|
+
end
|
72
|
+
|
73
|
+
def test_following_at_import_rules_from_add_block
|
74
|
+
css_block = '@import "../simple.css";'
|
75
|
+
|
76
|
+
@cp.add_block!(css_block, :base_uri => "#{@uri_base}/subdir/")
|
77
|
+
|
78
|
+
# from 'simple.css'
|
79
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('p').join(' ')
|
80
|
+
end
|
81
|
+
|
82
|
+
def test_importing_with_media_types
|
83
|
+
@cp.load_uri!("#{@uri_base}/import-with-media-types.css")
|
84
|
+
|
85
|
+
# from simple.css with :screen media type
|
86
|
+
assert_equal 'margin: 0px;', @cp.find_by_selector('p', :screen).join(' ')
|
87
|
+
assert_equal '', @cp.find_by_selector('p', :tty).join(' ')
|
88
|
+
end
|
89
|
+
|
90
|
+
def test_throwing_circular_reference_exception
|
91
|
+
assert_raise CircularReferenceError do
|
92
|
+
@cp.load_uri!("#{@uri_base}/import-circular-reference.css")
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
96
|
+
def test_toggling_not_found_exceptions
|
97
|
+
cp_with_exceptions = Parser.new(:io_exceptions => true)
|
98
|
+
|
99
|
+
assert_raise RemoteFileError do
|
100
|
+
cp_with_exceptions.load_uri!("#{@uri_base}/no-exist.xyz")
|
101
|
+
end
|
102
|
+
|
103
|
+
cp_without_exceptions = Parser.new(:io_exceptions => false)
|
104
|
+
|
105
|
+
assert_nothing_raised RemoteFileError do
|
106
|
+
cp_without_exceptions.load_uri!("#{@uri_base}/no-exist.xyz")
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
end
|
@@ -0,0 +1,71 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper'
|
2
|
+
|
3
|
+
# Test cases for the handling of media types
|
4
|
+
class CssParserMediaTypesTests < Test::Unit::TestCase
|
5
|
+
include CssParser
|
6
|
+
|
7
|
+
def setup
|
8
|
+
@cp = Parser.new
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_finding_by_media_type
|
12
|
+
# from http://www.w3.org/TR/CSS21/media.html#at-media-rule
|
13
|
+
css = <<-EOT
|
14
|
+
@media print {
|
15
|
+
body { font-size: 10pt }
|
16
|
+
}
|
17
|
+
@media screen {
|
18
|
+
body { font-size: 13px }
|
19
|
+
}
|
20
|
+
@media screen, print {
|
21
|
+
body { line-height: 1.2 }
|
22
|
+
}
|
23
|
+
EOT
|
24
|
+
|
25
|
+
@cp.add_block!(css)
|
26
|
+
|
27
|
+
assert_equal 'font-size: 10pt; line-height: 1.2;', @cp.find_by_selector('body', :print).join(' ')
|
28
|
+
assert_equal 'font-size: 13px; line-height: 1.2;', @cp.find_by_selector('body', :screen).join(' ')
|
29
|
+
end
|
30
|
+
|
31
|
+
def atest_finding_by_multiple_media_types
|
32
|
+
css = <<-EOT
|
33
|
+
@media print {
|
34
|
+
body { font-size: 10pt }
|
35
|
+
}
|
36
|
+
@media handheld {
|
37
|
+
body { font-size: 13px }
|
38
|
+
}
|
39
|
+
@media screen, print {
|
40
|
+
body { line-height: 1.2 }
|
41
|
+
}
|
42
|
+
EOT
|
43
|
+
@cp.add_block!(css)
|
44
|
+
|
45
|
+
assert_equal 'font-size: 13px; line-height: 1.2;', @cp.find_by_selector('body', [:screen,:handheld]).join(' ')
|
46
|
+
end
|
47
|
+
|
48
|
+
def test_adding_block_with_media_types
|
49
|
+
css = <<-EOT
|
50
|
+
body { font-size: 10pt }
|
51
|
+
EOT
|
52
|
+
|
53
|
+
@cp.add_block!(css, :media_types => [:screen])
|
54
|
+
|
55
|
+
assert_equal 'font-size: 10pt;', @cp.find_by_selector('body', :screen).join(' ')
|
56
|
+
assert @cp.find_by_selector('body', :handheld).empty?
|
57
|
+
end
|
58
|
+
|
59
|
+
def atest_adding_rule_set_with_media_type
|
60
|
+
@cp.add_rule!('body', 'color: black;', [:handheld,:tty])
|
61
|
+
@cp.add_rule!('body', 'color: blue;', :screen)
|
62
|
+
assert_equal 'color: black;', @cp.find_by_selector('body', :handheld).join(' ')
|
63
|
+
end
|
64
|
+
|
65
|
+
def atest_selecting_with_all_meda_type
|
66
|
+
@cp.add_rule!('body', 'color: black;', [:handheld,:tty])
|
67
|
+
assert_equal 'color: black;', @cp.find_by_selector('body', :all).join(' ')
|
68
|
+
end
|
69
|
+
|
70
|
+
|
71
|
+
end
|
@@ -0,0 +1,151 @@
|
|
1
|
+
require File.dirname(__FILE__) + '/test_helper'
|
2
|
+
|
3
|
+
# Test cases for the CssParser.
|
4
|
+
class CssParserTests < Test::Unit::TestCase
|
5
|
+
include CssParser
|
6
|
+
|
7
|
+
def setup
|
8
|
+
@cp = Parser.new
|
9
|
+
end
|
10
|
+
|
11
|
+
def test_at_page_rule
|
12
|
+
# from http://www.w3.org/TR/CSS21/page.html#page-selectors
|
13
|
+
css = <<-EOT
|
14
|
+
@page { margin: 2cm }
|
15
|
+
|
16
|
+
@page :first {
|
17
|
+
margin-top: 10cm
|
18
|
+
}
|
19
|
+
EOT
|
20
|
+
|
21
|
+
@cp.add_block!(css)
|
22
|
+
|
23
|
+
assert_equal 'margin: 2cm;', @cp.find_by_selector('@page').join(' ')
|
24
|
+
assert_equal 'margin-top: 10cm;', @cp.find_by_selector('@page :first').join(' ')
|
25
|
+
end
|
26
|
+
|
27
|
+
def test_should_ignore_comments
|
28
|
+
# see http://www.w3.org/Style/CSS/Test/CSS2.1/current/html4/t040109-c17-comments-00-b.htm
|
29
|
+
css =<<-EOT
|
30
|
+
/* This is a CSS comment. */
|
31
|
+
.one {color: green;} /* Another comment */
|
32
|
+
/* The following should not be used:
|
33
|
+
.one {color: red;} */
|
34
|
+
.two {color: green; /* color: yellow; */}
|
35
|
+
/**
|
36
|
+
.three {color: red;} */
|
37
|
+
.three {color: green;}
|
38
|
+
/**/
|
39
|
+
.four a b{color: green;}
|
40
|
+
/*********/
|
41
|
+
.five a {color: green;}
|
42
|
+
/* a comment **/
|
43
|
+
.six {color: green;}
|
44
|
+
EOT
|
45
|
+
|
46
|
+
@cp.add_block!(css)
|
47
|
+
@cp.each_selector_sorted(:all, :order => :asc) do |sel|
|
48
|
+
# puts sel.inspect
|
49
|
+
assert_equal 'color: green;', sel.declarations_to_s
|
50
|
+
end
|
51
|
+
|
52
|
+
puts "DESCENDING specificity ORDER"
|
53
|
+
@cp.each_selector_sorted(:all, :order => :desc) do |sel|
|
54
|
+
# puts sel.inspect
|
55
|
+
assert_equal 'color: green;', sel.declarations_to_s
|
56
|
+
end
|
57
|
+
|
58
|
+
end
|
59
|
+
|
60
|
+
def test_parsing_blocks
|
61
|
+
# dervived from http://www.w3.org/TR/CSS21/syndata.html#rule-sets
|
62
|
+
css = <<-EOT
|
63
|
+
div[name='test'] {
|
64
|
+
|
65
|
+
color:
|
66
|
+
|
67
|
+
red;
|
68
|
+
|
69
|
+
}div:hover{coloR:red;
|
70
|
+
}div:first-letter{color:red;/*color:blue;}"commented out"*/}
|
71
|
+
|
72
|
+
p[example="public class foo\
|
73
|
+
{\
|
74
|
+
private string x;\
|
75
|
+
\
|
76
|
+
foo(int x) {\
|
77
|
+
this.x = 'test';\
|
78
|
+
this.x = \"test\";\
|
79
|
+
}\
|
80
|
+
\
|
81
|
+
}"] { color: red }
|
82
|
+
|
83
|
+
p { color:red}
|
84
|
+
EOT
|
85
|
+
|
86
|
+
@cp.add_block!(css)
|
87
|
+
|
88
|
+
@cp.each_selector do |sel|
|
89
|
+
assert_equal 'color: red;', sel.declarations_to_s
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
# def test_ignoring_malformed_declarations
|
94
|
+
# flunk
|
95
|
+
# # dervived from http://www.w3.org/TR/CSS21/syndata.html#parsing-errors
|
96
|
+
# css = <<-EOT
|
97
|
+
# p { color:green }
|
98
|
+
# p { color:green; color } /* malformed declaration missing ':', value */
|
99
|
+
# p { color:red; color; color:green } /* same with expected recovery */
|
100
|
+
# p { color:green; color: } /* malformed declaration missing value */
|
101
|
+
# p { color:red; color:; color:green } /* same with expected recovery */
|
102
|
+
# p { color:green; color{;color:maroon} } /* unexpected tokens { } */
|
103
|
+
# p { color:red; color{;color:maroon}; color:green } /* same with recovery */
|
104
|
+
# EOT
|
105
|
+
#
|
106
|
+
# @cp.add_block!(css)
|
107
|
+
#
|
108
|
+
# @cp.each_selector do |sel|
|
109
|
+
# assert_equal 'color: green;', sel.declarations
|
110
|
+
# end
|
111
|
+
# end
|
112
|
+
|
113
|
+
def test_calculating_specificity
|
114
|
+
# from http://www.w3.org/TR/CSS21/cascade.html#specificity
|
115
|
+
assert_equal 0, CssParser.calculate_specificity('*')
|
116
|
+
assert_equal 1, CssParser.calculate_specificity('li')
|
117
|
+
assert_equal 2, CssParser.calculate_specificity('li:first-line')
|
118
|
+
assert_equal 2, CssParser.calculate_specificity('ul li')
|
119
|
+
assert_equal 3, CssParser.calculate_specificity('ul ol+li')
|
120
|
+
assert_equal 11, CssParser.calculate_specificity('h1 + *[rel=up]')
|
121
|
+
assert_equal 13, CssParser.calculate_specificity('ul ol li.red')
|
122
|
+
assert_equal 21, CssParser.calculate_specificity('li.red.level')
|
123
|
+
assert_equal 100, CssParser.calculate_specificity('#x34y')
|
124
|
+
|
125
|
+
# from http://www.hixie.ch/tests/adhoc/css/cascade/specificity/003.html
|
126
|
+
assert_equal CssParser.calculate_specificity('div *'), CssParser.calculate_specificity('p')
|
127
|
+
assert CssParser.calculate_specificity('body div *') > CssParser.calculate_specificity('div *')
|
128
|
+
|
129
|
+
# other tests
|
130
|
+
assert_equal 11, CssParser.calculate_specificity('h1[id|=123]')
|
131
|
+
end
|
132
|
+
|
133
|
+
def test_converting_uris
|
134
|
+
base_uri = 'http://www.example.org/style/basic.css'
|
135
|
+
["body { background: url(yellow) };", "body { background: url('yellow') };",
|
136
|
+
"body { background: url('/style/yellow') };",
|
137
|
+
"body { background: url(\"../style/yellow\") };",
|
138
|
+
"body { background: url(\"lib/../../style/yellow\") };"].each do |css|
|
139
|
+
converted_css = CssParser.convert_uris(css, base_uri)
|
140
|
+
assert_equal "body { background: url('http://www.example.org/style/yellow') };", converted_css
|
141
|
+
end
|
142
|
+
|
143
|
+
converted_css = CssParser.convert_uris("body { background: url(../style/yellow-dot_symbol$.png?abc=123&def=456&ghi=789#1011) };", base_uri)
|
144
|
+
assert_equal "body { background: url('http://www.example.org/style/yellow-dot_symbol$.png?abc=123&def=456&ghi=789#1011') };", converted_css
|
145
|
+
|
146
|
+
# taken from error log: 2007-10-23 04:37:41#2399
|
147
|
+
converted_css = CssParser.convert_uris('.specs {font-family:Helvetica;font-weight:bold;font-style:italic;color:#008CA8;font-size:1.4em;list-style-image:url("images/bullet.gif");}', 'http://www.example.org/directory/file.html')
|
148
|
+
assert_equal ".specs {font-family:Helvetica;font-weight:bold;font-style:italic;color:#008CA8;font-size:1.4em;list-style-image:url('http://www.example.org/directory/images/bullet.gif');}", converted_css
|
149
|
+
end
|
150
|
+
|
151
|
+
end
|