juicer 0.2.6 → 1.0.0

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.
Files changed (122) hide show
  1. data/History.txt +28 -0
  2. data/Rakefile +84 -36
  3. data/Readme.rdoc +192 -23
  4. data/VERSION +1 -0
  5. data/bin/juicer +2 -4
  6. data/lib/juicer.rb +9 -10
  7. data/lib/juicer/asset/path.rb +275 -0
  8. data/lib/juicer/asset/path_resolver.rb +79 -0
  9. data/lib/juicer/binary.rb +3 -5
  10. data/lib/juicer/cache_buster.rb +112 -27
  11. data/lib/juicer/command/install.rb +4 -2
  12. data/lib/juicer/command/list.rb +16 -9
  13. data/lib/juicer/command/merge.rb +30 -14
  14. data/lib/juicer/command/verify.rb +1 -1
  15. data/lib/juicer/css_cache_buster.rb +31 -47
  16. data/lib/juicer/datafy/datafy.rb +20 -0
  17. data/lib/juicer/dependency_resolver/css_dependency_resolver.rb +29 -0
  18. data/lib/juicer/dependency_resolver/dependency_resolver.rb +101 -0
  19. data/lib/juicer/dependency_resolver/javascript_dependency_resolver.rb +23 -0
  20. data/lib/juicer/ext/logger.rb +5 -0
  21. data/lib/juicer/ext/string.rb +47 -0
  22. data/lib/juicer/ext/symbol.rb +15 -0
  23. data/lib/juicer/image_embed.rb +129 -0
  24. data/lib/juicer/install/base.rb +2 -2
  25. data/lib/juicer/install/closure_compiler_installer.rb +69 -0
  26. data/lib/juicer/install/jslint_installer.rb +3 -3
  27. data/lib/juicer/install/rhino_installer.rb +3 -2
  28. data/lib/juicer/install/yui_compressor_installer.rb +3 -2
  29. data/lib/juicer/jslint.rb +1 -1
  30. data/lib/juicer/merger/base.rb +1 -1
  31. data/lib/juicer/merger/javascript_merger.rb +3 -4
  32. data/lib/juicer/merger/stylesheet_merger.rb +13 -15
  33. data/lib/juicer/minifyer/closure_compiler.rb +90 -0
  34. data/lib/juicer/minifyer/java_base.rb +77 -0
  35. data/lib/juicer/minifyer/yui_compressor.rb +15 -48
  36. data/test/bin/jslint-1.0.js +523 -0
  37. data/test/bin/jslint.js +523 -0
  38. data/test/bin/rhino1_7R1.zip +0 -0
  39. data/test/bin/rhino1_7R2-RC1.jar +0 -0
  40. data/test/bin/rhino1_7R2-RC1.zip +0 -0
  41. data/test/bin/yuicompressor +0 -0
  42. data/test/bin/yuicompressor-2.3.5.zip +0 -0
  43. data/test/bin/yuicompressor-2.4.2.jar +0 -0
  44. data/test/bin/yuicompressor-2.4.2.zip +0 -0
  45. data/test/data/Changelog.txt +10 -0
  46. data/test/data/a.css +3 -0
  47. data/test/data/a.js +5 -0
  48. data/test/data/a1.css +5 -0
  49. data/test/data/b.css +1 -0
  50. data/test/data/b.js +5 -0
  51. data/test/data/b1.css +5 -0
  52. data/test/data/c1.css +3 -0
  53. data/test/data/css/2.gif +1 -0
  54. data/test/data/css/test.css +11 -0
  55. data/test/data/css/test2.css +1 -0
  56. data/test/data/d1.css +3 -0
  57. data/test/data/images/1.png +1 -0
  58. data/test/data/my_app.js +2 -0
  59. data/test/data/not-ok.js +2 -0
  60. data/test/data/ok.js +3 -0
  61. data/test/data/path_test.css +5 -0
  62. data/test/data/path_test2.css +14 -0
  63. data/test/data/pkg/module/moda.js +2 -0
  64. data/test/data/pkg/module/modb.js +3 -0
  65. data/test/data/pkg/pkg.js +1 -0
  66. data/test/fixtures/yui-download.html +425 -0
  67. data/test/test_helper.rb +36 -7
  68. data/test/unit/juicer/asset/path_resolver_test.rb +76 -0
  69. data/test/unit/juicer/asset/path_test.rb +370 -0
  70. data/test/unit/juicer/cache_buster_test.rb +104 -0
  71. data/test/{juicer/test_chainable.rb → unit/juicer/chainable_test.rb} +1 -1
  72. data/test/unit/juicer/command/install_test.rb +58 -0
  73. data/test/{juicer/command/test_list.rb → unit/juicer/command/list_test.rb} +26 -14
  74. data/test/unit/juicer/command/merge_test.rb +162 -0
  75. data/test/{juicer/command/test_util.rb → unit/juicer/command/util_test.rb} +10 -6
  76. data/test/unit/juicer/command/verify_test.rb +48 -0
  77. data/test/{juicer/test_css_cache_buster.rb → unit/juicer/css_cache_buster_test.rb} +10 -30
  78. data/test/unit/juicer/datafy_test.rb +37 -0
  79. data/test/{juicer/merger/test_css_dependency_resolver.rb → unit/juicer/dependency_resolver/css_dependency_resolver_test.rb} +2 -2
  80. data/test/{juicer/merger/test_javascript_dependency_resolver.rb → unit/juicer/dependency_resolver/javascript_dependency_resolver_test.rb} +13 -2
  81. data/test/unit/juicer/ext/{#string_test.rb# → string_test.rb} +0 -7
  82. data/test/unit/juicer/ext/symbol_test.rb +27 -0
  83. data/test/unit/juicer/image_embed_test.rb +271 -0
  84. data/test/unit/juicer/install/installer_base_test.rb +214 -0
  85. data/test/{juicer/install/test_jslint_installer.rb → unit/juicer/install/jslint_installer_test.rb} +1 -1
  86. data/test/{juicer/install/test_rhino_installer.rb → unit/juicer/install/rhino_installer_test.rb} +1 -1
  87. data/test/{juicer/install/test_yui_compressor_installer.rb → unit/juicer/install/yui_compressor_test.rb} +16 -16
  88. data/test/unit/juicer/jslint_test.rb +60 -0
  89. data/test/{juicer/merger/test_base.rb → unit/juicer/merger/base_test.rb} +1 -1
  90. data/test/{juicer/merger/test_javascript_merger.rb → unit/juicer/merger/javascript_merger_test.rb} +2 -2
  91. data/test/{juicer/merger/test_stylesheet_merger.rb → unit/juicer/merger/stylesheet_merger_test.rb} +15 -13
  92. data/test/unit/juicer/minifyer/closure_compressor_test.rb +107 -0
  93. data/test/{integration → unit}/juicer/minifyer/yui_compressor_test.rb +30 -47
  94. data/test/unit/juicer_test.rb +1 -0
  95. metadata +207 -113
  96. data/lib/juicer/core.rb +0 -61
  97. data/lib/juicer/merger/css_dependency_resolver.rb +0 -25
  98. data/lib/juicer/merger/dependency_resolver.rb +0 -82
  99. data/lib/juicer/merger/javascript_dependency_resolver.rb +0 -21
  100. data/tasks/ann.rake +0 -80
  101. data/tasks/bones.rake +0 -20
  102. data/tasks/gem.rake +0 -201
  103. data/tasks/git.rake +0 -40
  104. data/tasks/notes.rake +0 -27
  105. data/tasks/post_load.rake +0 -34
  106. data/tasks/rdoc.rake +0 -51
  107. data/tasks/rubyforge.rake +0 -55
  108. data/tasks/setup.rb +0 -292
  109. data/tasks/spec.rake +0 -54
  110. data/tasks/svn.rake +0 -47
  111. data/tasks/test.rake +0 -40
  112. data/tasks/test/setup.rake +0 -35
  113. data/tasks/zentest.rake +0 -36
  114. data/test/juicer/command/test_install.rb +0 -53
  115. data/test/juicer/command/test_merge.rb +0 -160
  116. data/test/juicer/command/test_verify.rb +0 -33
  117. data/test/juicer/install/test_installer_base.rb +0 -195
  118. data/test/juicer/minifyer/test_yui_compressor.rb +0 -159
  119. data/test/juicer/test_cache_buster.rb +0 -58
  120. data/test/juicer/test_core.rb +0 -47
  121. data/test/juicer/test_jslint.rb +0 -33
  122. data/test/test_juicer.rb +0 -4
data/test/test_helper.rb CHANGED
@@ -1,9 +1,23 @@
1
1
  require 'fileutils'
2
2
  require 'test/unit'
3
- require File.expand_path(File.join(File.dirname(__FILE__), %w[.. lib juicer])) unless defined?(Juicer)
3
+ require 'shoulda'
4
+ require 'mocha'
5
+ require 'open-uri'
6
+ require 'juicer'
7
+
8
+ begin
9
+ require 'turn'
10
+ rescue LoadError => err
11
+ puts "Protip: Install turn gem for better test reports. #{err.message}"
12
+ end
13
+
14
+ if RUBY_VERSION < "1.9"
15
+ require 'redgreen' if ENV['TM_DIRECTORY'].nil?
16
+ end
4
17
 
5
18
  $data_dir = File.join(File.expand_path(File.dirname(__FILE__)), "data")
6
- Juicer::LOGGER = Logger.new StringIO.new
19
+ Juicer.send(:remove_const, :LOGGER)
20
+ Juicer::LOGGER = Logger.new(StringIO.new)
7
21
 
8
22
  # Prefixes paths with the data dir
9
23
  def path(path)
@@ -34,6 +48,8 @@ module Kernel
34
48
  def open(name, *rest, &block)
35
49
  if name =~ /http.+yuicompressor-(\d\.\d\.\d)\.zip$/
36
50
  name = File.join($data_dir, "..", "bin", "yuicompressor-#{$1}.zip")
51
+ elsif name =~ /http:\/\/yuilibrary\.com\/download/
52
+ name = File.join($data_dir, "../fixtures/yui-download.html")
37
53
  elsif name =~ /http.+yuicompressor/
38
54
  name = File.join($data_dir, "..", "bin", "yuicompressor")
39
55
  elsif name =~ /http.+jslint/
@@ -76,13 +92,13 @@ module Juicer
76
92
  mkfile(@dir, 'a.js', "/**\n * @depend b.js\n */\n\n/* Dette er a.js */")
77
93
  mkfile(@dir, 'b.css', "/* Dette er b.css */")
78
94
  mkfile(@dir, 'b.js', "/**\n * @depends a.js\n */\n\n/* Dette er b.css */")
79
- mkfile(@dir, 'a1.css', "@import 'b1.css';\n@import 'c1.css';\nbody {\n width: 800px;\n}\n")
80
- mkfile(@dir, 'b1.css', "@import 'd1.css';\n\nhtml {\n background: red;\n}\n")
95
+ mkfile(@dir, 'a1.css', "@import\t'b1.css';\n@import 'c1.css';\nbody {\n width: 800px;\n}\n")
96
+ mkfile(@dir, 'b1.css', "@import url('d1.css');\n\nhtml {\n background: red;\n}\n")
81
97
  mkfile(@dir, 'c1.css', "h1 {\n font-size: 12px;\n}\n")
82
98
  mkfile(@dir, 'd1.css', "h2 {\n font-size: 10px;\n}\n")
83
- mkfile(@dir, 'ok.js', "function hey() {\n alert(\"Hey\");\n}\n")
99
+ mkfile(@dir, 'ok.js', "function hey() {\n return \"Hey\";\n}\n")
84
100
  mkfile(@dir, 'not-ok.js', "var a = 34\nb = 78;\n")
85
-
101
+
86
102
  images = mkdir File.join(@dir, "images")
87
103
  mkfile(images, '1.png', "")
88
104
 
@@ -127,9 +143,22 @@ p { background: url(/a2.css); }
127
143
  mkfile(@dir, 'path_test2.css', css)
128
144
 
129
145
  mkfile(@dir, 'Changelog.txt', "2008.02.09 | stb-base 1.29\n\nFEATURE: Core | Bla bla bla bla bla\nFEATURE: UI: | Bla bla bla bla bla\n\n\n2008.02.09 | stb-base 1.29\n\nFEATURE: Core | Bla bla bla bla bla\nFEATURE: UI: | Bla bla bla bla bla\n")
146
+
147
+ # my_app.js depends on the pkg directory
148
+ mkfile(@dir, "my_app.js", "// @depend pkg\n var myApp = pkg.a;")
149
+
150
+ # package directory contains pkg.js, module/moda.js, and module/modb.js
151
+ # moda.js depends on ../pkg.js
152
+ # modb.js depends on moda.js and ../pkg.js
153
+ pkg_dir = mkdir File.join(@dir, "pkg")
154
+ module_dir = mkdir File.join(pkg_dir, "module")
155
+ mkfile(pkg_dir, "pkg.js", "var pkg = {};")
156
+ mkfile(module_dir, "moda.js", "// @depend ../pkg.js\npkg.a = '';")
157
+ mkfile(module_dir, "modb.js", "// @depend ../pkg.js\n// @depend moda.js\npkg.b = '';")
158
+
130
159
  end
131
160
 
132
- private
161
+ private
133
162
  # Create a file
134
163
  def mkfile(parent, name, content)
135
164
  file = File.open(File.join(parent, name), 'w+') { |f| f.puts content }
@@ -0,0 +1,76 @@
1
+ # -*- coding: utf-8 -*-
2
+
3
+ require "test_helper"
4
+ require "juicer/asset/path_resolver"
5
+
6
+ class AssetPathResolverTest < Test::Unit::TestCase
7
+ context "initializing path resolver" do
8
+ should "use current directory as base" do
9
+ resolver = Juicer::Asset::PathResolver.new
10
+
11
+ assert_equal Dir.pwd, resolver.base
12
+ end
13
+
14
+ should "ensure all hosts are complete with scheme" do
15
+ resolver = Juicer::Asset::PathResolver.new :hosts => %w[localhost my.project]
16
+
17
+ assert_equal %w[http://localhost http://my.project], resolver.hosts
18
+ end
19
+
20
+ should "set document root" do
21
+ resolver = Juicer::Asset::PathResolver.new :document_root => Dir.pwd
22
+
23
+ assert_equal Dir.pwd, resolver.document_root
24
+ end
25
+ end
26
+
27
+ context "resolving path" do
28
+ should "return asset object with the same options as the resolver" do
29
+ resolver = Juicer::Asset::PathResolver.new :document_root => "/var/www", :hosts => ["localhost", "mysite.com"]
30
+ asset = resolver.resolve("../images/logo.png")
31
+
32
+ assert_equal resolver.base, asset.base
33
+ assert_equal resolver.document_root, asset.document_root
34
+ assert_equal resolver.hosts, asset.hosts
35
+ end
36
+ end
37
+
38
+ context "cycling hosts" do
39
+ should "return one host at a time" do
40
+ resolver = Juicer::Asset::PathResolver.new :hosts => %w[localhost my.project]
41
+
42
+ assert_equal "http://localhost", resolver.cycle_hosts
43
+ assert_equal "http://my.project", resolver.cycle_hosts
44
+ assert_equal "http://localhost", resolver.cycle_hosts
45
+ end
46
+
47
+ should "be aliased through host" do
48
+ resolver = Juicer::Asset::PathResolver.new :hosts => %w[localhost my.project]
49
+
50
+ assert_equal "http://localhost", resolver.host
51
+ assert_equal "http://my.project", resolver.host
52
+ assert_equal "http://localhost", resolver.host
53
+ end
54
+ end
55
+
56
+ context "setting base" do
57
+ should "update property" do
58
+ resolver = Juicer::Asset::PathResolver.new
59
+ new_base = "/var/www/test"
60
+ resolver.base = new_base
61
+
62
+ assert_equal new_base, resolver.base
63
+ end
64
+
65
+ should "update base option for new assets" do
66
+ resolver = Juicer::Asset::PathResolver.new
67
+ asset1 = resolver.resolve "css/1.css"
68
+ resolver.base = "/var/www/test"
69
+ asset2 = resolver.resolve "css/1.css"
70
+
71
+ assert_not_equal asset1.base, asset2.base
72
+ assert_not_equal asset1.base, resolver.base
73
+ assert_equal asset2.base, resolver.base
74
+ end
75
+ end
76
+ end
@@ -0,0 +1,370 @@
1
+ # -*- coding: utf-8 -*-
2
+
3
+ require "test_helper"
4
+ require "juicer/asset/path"
5
+
6
+ class AssetPathTest < Test::Unit::TestCase
7
+ context "initializing asset" do
8
+ should "use default options" do
9
+ asset = Juicer::Asset::Path.new "../images/logo.png"
10
+
11
+ assert_equal Dir.pwd, asset.base
12
+ assert_equal [], asset.hosts
13
+ assert_nil asset.document_root
14
+ end
15
+
16
+ should "override options" do
17
+ base = "/home/me/project/awesome-site/public/stylesheets"
18
+ asset = Juicer::Asset::Path.new "../images/logo.png", :base => base
19
+
20
+ assert_equal base, asset.base
21
+ end
22
+
23
+ should "not nil base option" do
24
+ asset = Juicer::Asset::Path.new "../images/logo.png", :base => nil
25
+
26
+ assert_equal Dir.pwd, asset.base
27
+ end
28
+
29
+ should "accept a single host" do
30
+ asset = Juicer::Asset::Path.new "../images/logo.png", :hosts => "http://localhost"
31
+
32
+ assert_equal ["http://localhost"], asset.hosts
33
+ end
34
+
35
+ should "accept array of hosts" do
36
+ asset = Juicer::Asset::Path.new "../images/logo.png", :hosts => ["http://localhost", "http://dev.server"]
37
+
38
+ assert_equal ["http://localhost", "http://dev.server"], asset.hosts
39
+ end
40
+
41
+ should "strip trailing slash in hosts" do
42
+ asset = Juicer::Asset::Path.new "../images/logo.png", :hosts => ["http://localhost/", "http://dev.server"]
43
+
44
+ assert_equal ["http://localhost", "http://dev.server"], asset.hosts
45
+ end
46
+
47
+ should "strip add scheme for hosts if missing" do
48
+ asset = Juicer::Asset::Path.new "../images/logo.png", :hosts => ["localhost", "http://dev.server"]
49
+
50
+ assert_equal ["http://localhost", "http://dev.server"], asset.hosts
51
+ end
52
+
53
+ should "strip trailing slash and add scheme in hosts" do
54
+ asset = Juicer::Asset::Path.new "../images/logo.png", :hosts => ["localhost/", "http://dev.server", "some.server/"]
55
+
56
+ assert_equal ["http://localhost", "http://dev.server", "http://some.server"], asset.hosts
57
+ end
58
+ end
59
+
60
+ context "asset absolute path" do
61
+ should "raise exception without document root" do
62
+ asset = Juicer::Asset::Path.new "../images/logo.png"
63
+
64
+ assert_raise ArgumentError do
65
+ asset.absolute_path
66
+ end
67
+ end
68
+
69
+ should "return absolute path from relative path and document root" do
70
+ base = "/var/www/public/stylesheets"
71
+ document_root = "/var/www/public"
72
+ asset = Juicer::Asset::Path.new "../images/logo.png", :base => base, :document_root => document_root
73
+
74
+ assert_equal "/images/logo.png", asset.absolute_path
75
+ end
76
+
77
+ should "return absolute path from absolute path" do
78
+ base = "/var/www/public/stylesheets"
79
+ document_root = "/var/www/public"
80
+ path = "/images/logo.png"
81
+ asset = Juicer::Asset::Path.new path, { :base => base, :document_root => document_root }
82
+
83
+ assert_equal path, asset.absolute_path
84
+ end
85
+
86
+ context "with host" do
87
+ setup do
88
+ base = "/var/www/public/stylesheets"
89
+ document_root = "/var/www/public"
90
+ options = { :base => base, :document_root => document_root }
91
+ @asset = Juicer::Asset::Path.new "../images/logo.png", options
92
+ end
93
+
94
+ should "return absolute path with host" do
95
+ assert_equal "http://localhost/images/logo.png", @asset.absolute_path(:host => "http://localhost")
96
+ end
97
+
98
+ should "strip trailing slash from absolute path host" do
99
+ assert_equal "http://localhost/images/logo.png", @asset.absolute_path(:host => "http://localhost/")
100
+ end
101
+
102
+ should "ensure scheme in absolute path host" do
103
+ assert_equal "http://localhost/images/logo.png", @asset.absolute_path(:host => "localhost")
104
+ end
105
+
106
+ should "strip trailing slash and ensure scheme in absolute path host" do
107
+ assert_equal "http://localhost/images/logo.png", @asset.absolute_path(:host => "localhost/")
108
+ end
109
+ end
110
+
111
+ context "with cache buster" do
112
+ setup do
113
+ @filename = "tmp.asset.txt"
114
+ file = File.open(@filename, "w") { |f| f.puts "Testing" }
115
+ @asset = Juicer::Asset::Path.new @filename, :document_root => Dir.pwd
116
+ end
117
+
118
+ teardown do
119
+ File.delete(@filename)
120
+ end
121
+
122
+ should "return URL with mtime query parameter and default parameter name" do
123
+ mtime = File.mtime(@filename).to_i
124
+ assert_equal "/#@filename?jcb=#{mtime}", @asset.absolute_path(:cache_buster_type => :soft)
125
+ end
126
+
127
+ should "return URL with mtime query parameter" do
128
+ mtime = File.mtime(@filename).to_i
129
+ assert_equal "/#@filename?#{mtime}", @asset.absolute_path(:cache_buster => nil)
130
+ end
131
+
132
+ should "return URL with mtime embedded" do
133
+ mtime = File.mtime(@filename).to_i
134
+ assert_equal "/#{@filename.sub(/\.txt/, '')}-jcb#{mtime}.txt", @asset.absolute_path(:cache_buster => :jcb, :cache_buster_type => :hard)
135
+ end
136
+ end
137
+ end
138
+
139
+ context "relative path" do
140
+ should "return relative path from relative path" do
141
+ path = "../images/logo.png"
142
+ asset = Juicer::Asset::Path.new path, :base => "/var/www/public/stylesheets"
143
+
144
+ assert_equal path, asset.relative_path
145
+ end
146
+
147
+ should "return relative path from absolute path" do
148
+ path = "/images/logo.png"
149
+ asset = Juicer::Asset::Path.new path, :document_root => "/var/www/public", :base => "/var/www/public/stylesheets"
150
+
151
+ assert_equal "..#{path}", asset.relative_path
152
+ end
153
+
154
+ context "with cache buster" do
155
+ setup do
156
+ @filename = "tmp.asset.txt"
157
+ file = File.open(@filename, "w") { |f| f.puts "Testing" }
158
+ @asset = Juicer::Asset::Path.new @filename, :document_root => Dir.pwd
159
+ end
160
+
161
+ teardown do
162
+ File.delete(@filename)
163
+ end
164
+
165
+ should "return URL with mtime query parameter and default parameter name" do
166
+ mtime = File.mtime(@filename).to_i
167
+ result = "#@filename?jcb=#{mtime}"
168
+ Juicer::CacheBuster.stubs(:soft).with(File.expand_path(@filename)).returns(result)
169
+
170
+ assert_equal result, @asset.relative_path(:cache_buster_type => :soft)
171
+ end
172
+
173
+ should "return URL with mtime query parameter" do
174
+ mtime = File.mtime(@filename).to_i
175
+ assert_equal "#@filename?#{mtime}", @asset.relative_path(:cache_buster => nil)
176
+ end
177
+
178
+ should "return URL with mtime embedded" do
179
+ mtime = File.mtime(@filename).to_i
180
+ assert_equal "#{@filename.sub(/\.txt/, '')}-jcb#{mtime}.txt", @asset.relative_path(:cache_buster => :jcb, :cache_buster_type => :hard)
181
+ end
182
+ end
183
+ end
184
+
185
+ context "original path" do
186
+ should "preserve relative path" do
187
+ path = "../images/logo.png"
188
+ asset = Juicer::Asset::Path.new path
189
+
190
+ assert_equal path, asset.path
191
+ end
192
+
193
+ should "preserve absolute path" do
194
+ path = "/images/logo.png"
195
+ asset = Juicer::Asset::Path.new path
196
+
197
+ assert_equal path, asset.path
198
+ end
199
+
200
+ should "preserve absolute path with host" do
201
+ path = "http://localhost/images/logo.png"
202
+ asset = Juicer::Asset::Path.new path
203
+
204
+ assert_equal path, asset.path
205
+ end
206
+
207
+ context "with cache buster" do
208
+ setup do
209
+ @filename = "tmp.asset.txt"
210
+ file = File.open(@filename, "w") { |f| f.puts "Testing" }
211
+ end
212
+
213
+ teardown do
214
+ File.delete(@filename)
215
+ end
216
+
217
+ should "return original relative path with mtime query parameter and default parameter name" do
218
+ asset = Juicer::Asset::Path.new @filename, :document_root => Dir.pwd
219
+ mtime = File.mtime(@filename).to_i
220
+ assert_equal "#@filename?jcb=#{mtime}", asset.path(:cache_buster_type => :soft)
221
+ end
222
+
223
+ should "return original absolute path with mtime query parameter and default parameter name" do
224
+ asset = Juicer::Asset::Path.new "/#@filename", :document_root => Dir.pwd
225
+ mtime = File.mtime(@filename).to_i
226
+ assert_equal "/#@filename?jcb=#{mtime}", asset.path(:cache_buster_type => :soft)
227
+ end
228
+ end
229
+ end
230
+
231
+ context "asset filename" do
232
+ should "raise exception with absolute path without document root" do
233
+ asset = Juicer::Asset::Path.new "/images/logo.png", :document_root => nil
234
+
235
+ assert_raise ArgumentError do
236
+ asset.filename
237
+ end
238
+ end
239
+
240
+ should "raise exception with absolute path with host without document root" do
241
+ asset = Juicer::Asset::Path.new "http://localhost/images/logo.png", :document_root => nil
242
+
243
+ assert_raise ArgumentError do
244
+ asset.filename
245
+ end
246
+ end
247
+
248
+ should "raise exception with absolute path with host without hosts" do
249
+ options = { :document_root => "/var/project" }
250
+ asset = Juicer::Asset::Path.new "http://localhost/images/logo.png", options
251
+
252
+ assert_raise ArgumentError do
253
+ begin
254
+ asset.filename
255
+ rescue ArgumentError => err
256
+ assert_match /No hosts served/, err.message
257
+ raise err
258
+ end
259
+ end
260
+ end
261
+
262
+ should "raise exception with mismatching hosts" do
263
+ options = { :document_root => "/var/project", :hosts => %w[example.com site.com] }
264
+ asset = Juicer::Asset::Path.new "http://localhost/images/logo.png", options
265
+
266
+ assert_raise ArgumentError do
267
+ begin
268
+ asset.filename
269
+ rescue ArgumentError => err
270
+ assert_match /No matching host/, err.message
271
+ raise err
272
+ end
273
+ end
274
+ end
275
+
276
+ should "return filename from relative path and base" do
277
+ asset = Juicer::Asset::Path.new "../images/logo.png", :base => "/var/www/public/stylesheets"
278
+
279
+ assert_equal "/var/www/public/images/logo.png", asset.filename
280
+ end
281
+
282
+ should "return filename from absolute path and document root" do
283
+ asset = Juicer::Asset::Path.new "/images/logo.png", :document_root => "/var/www/public"
284
+
285
+ assert_equal "/var/www/public/images/logo.png", asset.filename
286
+ end
287
+
288
+ should "return filename from absolute path with host and document root" do
289
+ asset = Juicer::Asset::Path.new "http://localhost/images/logo.png", :document_root => "/var/www/public", :hosts => "localhost"
290
+
291
+ assert_equal "/var/www/public/images/logo.png", asset.filename
292
+ end
293
+
294
+ should "raise exception when hosts match but schemes don't" do
295
+ options = { :document_root => "/var/www/public", :hosts => "http://localhost" }
296
+ asset = Juicer::Asset::Path.new "https://localhost/images/logo.png", options
297
+
298
+ assert_raise(ArgumentError) { asset.filename }
299
+ end
300
+
301
+ should "return filename from absolute path with hosts and document root" do
302
+ options = { :document_root => "/var/www/public", :hosts => %w[example.com localhost https://localhost] }
303
+ asset = Juicer::Asset::Path.new "https://localhost/images/logo.png", options
304
+
305
+ assert_equal "/var/www/public/images/logo.png", asset.filename
306
+ end
307
+ end
308
+
309
+ context "file helpers" do
310
+ should "return file basename" do
311
+ base = "/var/www/public/"
312
+ asset = Juicer::Asset::Path.new "images/logo.png", :base => base
313
+
314
+ assert_equal "logo.png", asset.basename
315
+ end
316
+
317
+ should "return file dirname" do
318
+ base = "/var/www/public/"
319
+ asset = Juicer::Asset::Path.new "images/logo.png", :base => base
320
+
321
+ assert_equal "#{base}images", asset.dirname
322
+ end
323
+
324
+ should "verify that file does not exist" do
325
+ base = "/var/www/public/"
326
+ asset = Juicer::Asset::Path.new "images/logo.png", :base => base
327
+
328
+ assert !asset.exists?
329
+ end
330
+
331
+ context "existing file" do
332
+ setup { File.open("somefile.css", "w") { |f| f.puts "/* Test */" } }
333
+ teardown { File.delete("somefile.css") }
334
+
335
+ should "verify that file exists" do
336
+ asset = Juicer::Asset::Path.new "somefile.css"
337
+
338
+ assert asset.exists?
339
+ end
340
+ end
341
+ end
342
+
343
+ context "rebase path" do
344
+ should "return new asset with shifted base" do
345
+ base = "/var/www/project/public"
346
+ asset = Juicer::Asset::Path.new "../images/logo.png", :base => "#{base}/stylesheets"
347
+ rebased_asset = asset.rebase(base)
348
+
349
+ assert_equal "images/logo.png", rebased_asset.relative_path
350
+ end
351
+
352
+ should "preserve all options but base context" do
353
+ base = "/var/www/project/public"
354
+ options = { :base => "#{base}/stylesheets", :hosts => ["localhost"], :document_root => base }
355
+ asset = Juicer::Asset::Path.new "../images/logo.png", options
356
+ rebased_asset = asset.rebase(base)
357
+
358
+ assert_equal asset.document_root, rebased_asset.document_root
359
+ assert_equal asset.hosts, rebased_asset.hosts
360
+ end
361
+
362
+ should "return same absolute path" do
363
+ base = "/var/www/project/public"
364
+ asset = Juicer::Asset::Path.new "../images/logo.png", :base => "#{base}/stylesheets", :document_root => base
365
+ rebased_asset = asset.rebase(base)
366
+
367
+ assert_equal asset.absolute_path, rebased_asset.absolute_path
368
+ end
369
+ end
370
+ end