ktheory-juicer 1.0.0.ktheory1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (98) hide show
  1. data/History.txt +30 -0
  2. data/Manifest.txt +58 -0
  3. data/Rakefile +96 -0
  4. data/Readme.rdoc +312 -0
  5. data/VERSION +1 -0
  6. data/bin/juicer +8 -0
  7. data/lib/juicer.rb +70 -0
  8. data/lib/juicer/asset/path.rb +275 -0
  9. data/lib/juicer/asset/path_resolver.rb +79 -0
  10. data/lib/juicer/binary.rb +171 -0
  11. data/lib/juicer/cache_buster.rb +130 -0
  12. data/lib/juicer/chainable.rb +106 -0
  13. data/lib/juicer/cli.rb +56 -0
  14. data/lib/juicer/command/install.rb +61 -0
  15. data/lib/juicer/command/list.rb +57 -0
  16. data/lib/juicer/command/merge.rb +205 -0
  17. data/lib/juicer/command/util.rb +32 -0
  18. data/lib/juicer/command/verify.rb +60 -0
  19. data/lib/juicer/css_cache_buster.rb +80 -0
  20. data/lib/juicer/datafy/datafy.rb +20 -0
  21. data/lib/juicer/dependency_resolver/css_dependency_resolver.rb +29 -0
  22. data/lib/juicer/dependency_resolver/dependency_resolver.rb +101 -0
  23. data/lib/juicer/dependency_resolver/javascript_dependency_resolver.rb +23 -0
  24. data/lib/juicer/ext/logger.rb +5 -0
  25. data/lib/juicer/ext/string.rb +47 -0
  26. data/lib/juicer/ext/symbol.rb +15 -0
  27. data/lib/juicer/image_embed.rb +136 -0
  28. data/lib/juicer/install/base.rb +186 -0
  29. data/lib/juicer/install/closure_compiler_installer.rb +69 -0
  30. data/lib/juicer/install/jslint_installer.rb +51 -0
  31. data/lib/juicer/install/rhino_installer.rb +53 -0
  32. data/lib/juicer/install/yui_compressor_installer.rb +67 -0
  33. data/lib/juicer/jslint.rb +90 -0
  34. data/lib/juicer/merger/base.rb +74 -0
  35. data/lib/juicer/merger/javascript_merger.rb +29 -0
  36. data/lib/juicer/merger/stylesheet_merger.rb +110 -0
  37. data/lib/juicer/minifyer/closure_compiler.rb +90 -0
  38. data/lib/juicer/minifyer/java_base.rb +77 -0
  39. data/lib/juicer/minifyer/yui_compressor.rb +96 -0
  40. data/test/bin/jslint-1.0.js +523 -0
  41. data/test/bin/jslint.js +523 -0
  42. data/test/bin/rhino1_7R1.zip +0 -0
  43. data/test/bin/rhino1_7R2-RC1.jar +0 -0
  44. data/test/bin/rhino1_7R2-RC1.zip +0 -0
  45. data/test/bin/yuicompressor +0 -0
  46. data/test/bin/yuicompressor-2.3.5.zip +0 -0
  47. data/test/bin/yuicompressor-2.4.2.jar +0 -0
  48. data/test/bin/yuicompressor-2.4.2.zip +0 -0
  49. data/test/data/Changelog.txt +10 -0
  50. data/test/data/a.css +3 -0
  51. data/test/data/a.js +5 -0
  52. data/test/data/a1.css +5 -0
  53. data/test/data/b.css +1 -0
  54. data/test/data/b.js +5 -0
  55. data/test/data/b1.css +5 -0
  56. data/test/data/c1.css +3 -0
  57. data/test/data/css/2.gif +1 -0
  58. data/test/data/css/test.css +11 -0
  59. data/test/data/css/test2.css +1 -0
  60. data/test/data/d1.css +3 -0
  61. data/test/data/images/1.png +1 -0
  62. data/test/data/my_app.js +2 -0
  63. data/test/data/not-ok.js +2 -0
  64. data/test/data/ok.js +3 -0
  65. data/test/data/path_test.css +5 -0
  66. data/test/data/path_test2.css +14 -0
  67. data/test/data/pkg/module/moda.js +2 -0
  68. data/test/data/pkg/module/modb.js +3 -0
  69. data/test/data/pkg/pkg.js +1 -0
  70. data/test/test_helper.rb +169 -0
  71. data/test/unit/juicer/asset/path_resolver_test.rb +76 -0
  72. data/test/unit/juicer/asset/path_test.rb +370 -0
  73. data/test/unit/juicer/cache_buster_test.rb +104 -0
  74. data/test/unit/juicer/chainable_test.rb +94 -0
  75. data/test/unit/juicer/command/install_test.rb +58 -0
  76. data/test/unit/juicer/command/list_test.rb +81 -0
  77. data/test/unit/juicer/command/merge_test.rb +162 -0
  78. data/test/unit/juicer/command/util_test.rb +58 -0
  79. data/test/unit/juicer/command/verify_test.rb +48 -0
  80. data/test/unit/juicer/css_cache_buster_test.rb +71 -0
  81. data/test/unit/juicer/datafy_test.rb +37 -0
  82. data/test/unit/juicer/dependency_resolver/css_dependency_resolver_test.rb +36 -0
  83. data/test/unit/juicer/dependency_resolver/javascript_dependency_resolver_test.rb +50 -0
  84. data/test/unit/juicer/ext/string_test.rb +59 -0
  85. data/test/unit/juicer/ext/symbol_test.rb +27 -0
  86. data/test/unit/juicer/image_embed_test.rb +271 -0
  87. data/test/unit/juicer/install/installer_base_test.rb +214 -0
  88. data/test/unit/juicer/install/jslint_installer_test.rb +54 -0
  89. data/test/unit/juicer/install/rhino_installer_test.rb +57 -0
  90. data/test/unit/juicer/install/yui_compressor_test.rb +56 -0
  91. data/test/unit/juicer/jslint_test.rb +60 -0
  92. data/test/unit/juicer/merger/base_test.rb +122 -0
  93. data/test/unit/juicer/merger/javascript_merger_test.rb +74 -0
  94. data/test/unit/juicer/merger/stylesheet_merger_test.rb +180 -0
  95. data/test/unit/juicer/minifyer/closure_compressor_test.rb +107 -0
  96. data/test/unit/juicer/minifyer/yui_compressor_test.rb +116 -0
  97. data/test/unit/juicer_test.rb +1 -0
  98. metadata +265 -0
Binary file
Binary file
Binary file
File without changes
Binary file
Binary file
Binary file
@@ -0,0 +1,10 @@
1
+ 2008.02.09 | stb-base 1.29
2
+
3
+ FEATURE: Core | Bla bla bla bla bla
4
+ FEATURE: UI: | Bla bla bla bla bla
5
+
6
+
7
+ 2008.02.09 | stb-base 1.29
8
+
9
+ FEATURE: Core | Bla bla bla bla bla
10
+ FEATURE: UI: | Bla bla bla bla bla
data/test/data/a.css ADDED
@@ -0,0 +1,3 @@
1
+ @import 'b.css';
2
+
3
+ /* Dette er a.css */
data/test/data/a.js ADDED
@@ -0,0 +1,5 @@
1
+ /**
2
+ * @depend b.js
3
+ */
4
+
5
+ /* Dette er a.js */
data/test/data/a1.css ADDED
@@ -0,0 +1,5 @@
1
+ @import 'b1.css';
2
+ @import 'c1.css';
3
+ body {
4
+ width: 800px;
5
+ }
data/test/data/b.css ADDED
@@ -0,0 +1 @@
1
+ /* Dette er b.css */
data/test/data/b.js ADDED
@@ -0,0 +1,5 @@
1
+ /**
2
+ * @depends a.js
3
+ */
4
+
5
+ /* Dette er b.css */
data/test/data/b1.css ADDED
@@ -0,0 +1,5 @@
1
+ @import 'd1.css';
2
+
3
+ html {
4
+ background: red;
5
+ }
data/test/data/c1.css ADDED
@@ -0,0 +1,3 @@
1
+ h1 {
2
+ font-size: 12px;
3
+ }
@@ -0,0 +1 @@
1
+
@@ -0,0 +1,11 @@
1
+ body {
2
+ background: url(../images/1.png);
3
+ }
4
+
5
+ h1 {
6
+ background: url(../a1.css) 0 0 no-repeat;
7
+ }
8
+
9
+ h2 {
10
+ background: url(2.gif) no-repeat;
11
+ }
@@ -0,0 +1 @@
1
+ body { background: url(/images/1.png); }
data/test/data/d1.css ADDED
@@ -0,0 +1,3 @@
1
+ h2 {
2
+ font-size: 10px;
3
+ }
@@ -0,0 +1 @@
1
+
@@ -0,0 +1,2 @@
1
+ // @depend pkg
2
+ var myApp = pkg.a;
@@ -0,0 +1,2 @@
1
+ var a = 34
2
+ b = 78;
data/test/data/ok.js ADDED
@@ -0,0 +1,3 @@
1
+ function hey() {
2
+ return "Hey";
3
+ }
@@ -0,0 +1,5 @@
1
+ @import 'css/test.css';
2
+
3
+ body {
4
+ background: url(css/2.gif) no-repeat;
5
+ }
@@ -0,0 +1,14 @@
1
+ body {
2
+ background: url(/images/1.png);
3
+ }
4
+
5
+ h1 {
6
+ background: url(/css/2.gif);
7
+ background: url(/a1.css) 0 0 no-repeat;
8
+ }
9
+
10
+ h2 {
11
+ background: url(/css/2.gif) no-repeat;
12
+ }
13
+
14
+ p { background: url(/a2.css); }
@@ -0,0 +1,2 @@
1
+ // @depend ../pkg.js
2
+ pkg.a = '';
@@ -0,0 +1,3 @@
1
+ // @depend ../pkg.js
2
+ // @depend moda.js
3
+ pkg.b = '';
@@ -0,0 +1 @@
1
+ var pkg = {};
@@ -0,0 +1,169 @@
1
+ require 'fileutils'
2
+ require 'test/unit'
3
+ require 'shoulda'
4
+ require 'mocha'
5
+ require 'open-uri'
6
+ require 'juicer'
7
+
8
+ if RUBY_VERSION < "1.9"
9
+ require 'redgreen' if ENV['TM_DIRECTORY'].nil?
10
+ end
11
+
12
+ $data_dir = File.join(File.expand_path(File.dirname(__FILE__)), "data")
13
+ Juicer.send(:remove_const, :LOGGER)
14
+ Juicer::LOGGER = Logger.new(StringIO.new)
15
+
16
+ # Prefixes paths with the data dir
17
+ def path(path)
18
+ File.join($data_dir, path)
19
+ end
20
+
21
+ # Allow for testing of private methods inside a block:
22
+ #
23
+ # MyClass.publicize_methods do
24
+ # assert MyClass.some_private_method
25
+ # end
26
+ class Class
27
+ def publicize_methods
28
+ saved_private_instance_methods = self.private_instance_methods
29
+ self.class_eval { public(*saved_private_instance_methods) }
30
+ yield
31
+ self.class_eval { private(*saved_private_instance_methods) }
32
+ end
33
+ end
34
+
35
+ #
36
+ # Intercept calls to open, and return local files
37
+ #
38
+ module Kernel
39
+ private
40
+ alias juicer_original_open open # :nodoc:
41
+
42
+ def open(name, *rest, &block)
43
+ if name =~ /http.+yuicompressor-(\d\.\d\.\d)\.zip$/
44
+ name = File.join($data_dir, "..", "bin", "yuicompressor-#{$1}.zip")
45
+ elsif name =~ /http:\/\/yuilibrary\.com\/download/
46
+ name = File.join($data_dir, "yui-download.html")
47
+ elsif name =~ /http.+yuicompressor/
48
+ name = File.join($data_dir, "..", "bin", "yuicompressor")
49
+ elsif name =~ /http.+jslint/
50
+ name = File.join($data_dir, "..", "bin", "jslint.js")
51
+ elsif name =~ /ftp.+rhino(.+)\.zip/
52
+ name = File.join($data_dir, "..", "bin", "rhino#{$1}.zip")
53
+ end
54
+
55
+ juicer_original_open(File.expand_path(name), *rest, &block)
56
+ end
57
+
58
+ module_function :open
59
+ end
60
+
61
+ module Juicer
62
+ module Test
63
+
64
+ # Alot of Juicer functionality are filesystem operations. This class sets up files
65
+ # to work on
66
+ class FileSetup
67
+ attr_reader :file_count
68
+
69
+ def initialize(dir = $data_dir)
70
+ @dir = dir
71
+ @file_count = 0
72
+ end
73
+
74
+ # Recursively deletes the data directory
75
+ def delete
76
+ res = FileUtils.rm_rf(@dir) if File.exist?(@dir)
77
+ end
78
+
79
+ # Set up files for unit tests
80
+ def create(force = false)
81
+ return if File.exist?(@dir) && !force
82
+
83
+ delete if File.exist?(@dir)
84
+ mkdir @dir
85
+ mkfile(@dir, 'a.css', "@import 'b.css';\n\n/* Dette er a.css */")
86
+ mkfile(@dir, 'a.js', "/**\n * @depend b.js\n */\n\n/* Dette er a.js */")
87
+ mkfile(@dir, 'b.css', "/* Dette er b.css */")
88
+ mkfile(@dir, 'b.js', "/**\n * @depends a.js\n */\n\n/* Dette er b.css */")
89
+ mkfile(@dir, 'a1.css', "@import 'b1.css';\n@import 'c1.css';\nbody {\n width: 800px;\n}\n")
90
+ mkfile(@dir, 'b1.css', "@import 'd1.css';\n\nhtml {\n background: red;\n}\n")
91
+ mkfile(@dir, 'c1.css', "h1 {\n font-size: 12px;\n}\n")
92
+ mkfile(@dir, 'd1.css', "h2 {\n font-size: 10px;\n}\n")
93
+ mkfile(@dir, 'ok.js', "function hey() {\n return \"Hey\";\n}\n")
94
+ mkfile(@dir, 'not-ok.js', "var a = 34\nb = 78;\n")
95
+
96
+ images = mkdir File.join(@dir, "images")
97
+ mkfile(images, '1.png', "")
98
+
99
+ css_dir = mkdir File.join(@dir, "css")
100
+ mkfile(css_dir, '2.gif', "")
101
+
102
+ css = <<-CSS
103
+ body {
104
+ background: url(../images/1.png);
105
+ }
106
+
107
+ h1 {
108
+ background: url(../a1.css) 0 0 no-repeat;
109
+ }
110
+
111
+ h2 {
112
+ background: url(2.gif) no-repeat;
113
+ }
114
+ CSS
115
+
116
+ mkfile(css_dir, 'test.css', css)
117
+ mkfile(css_dir, 'test2.css', "body { background: url(/images/1.png); }")
118
+ mkfile(@dir, 'path_test.css', "@import 'css/test.css';\n\nbody {\n background: url(css/2.gif) no-repeat;\n}\n")
119
+
120
+ css = <<-CSS
121
+ body {
122
+ background: url(/images/1.png);
123
+ }
124
+
125
+ h1 {
126
+ background: url(/css/2.gif);
127
+ background: url(/a1.css) 0 0 no-repeat;
128
+ }
129
+
130
+ h2 {
131
+ background: url(/css/2.gif) no-repeat;
132
+ }
133
+
134
+ p { background: url(/a2.css); }
135
+ CSS
136
+
137
+ mkfile(@dir, 'path_test2.css', css)
138
+
139
+ 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")
140
+
141
+ # my_app.js depends on the pkg directory
142
+ mkfile(@dir, "my_app.js", "// @depend pkg\n var myApp = pkg.a;")
143
+
144
+ # package directory contains pkg.js, module/moda.js, and module/modb.js
145
+ # moda.js depends on ../pkg.js
146
+ # modb.js depends on moda.js and ../pkg.js
147
+ pkg_dir = mkdir File.join(@dir, "pkg")
148
+ module_dir = mkdir File.join(pkg_dir, "module")
149
+ mkfile(pkg_dir, "pkg.js", "var pkg = {};")
150
+ mkfile(module_dir, "moda.js", "// @depend ../pkg.js\npkg.a = '';")
151
+ mkfile(module_dir, "modb.js", "// @depend ../pkg.js\n// @depend moda.js\npkg.b = '';")
152
+
153
+ end
154
+
155
+ private
156
+ # Create a file
157
+ def mkfile(parent, name, content)
158
+ file = File.open(File.join(parent, name), 'w+') { |f| f.puts content }
159
+ @file_count += 1
160
+ end
161
+
162
+ def mkdir(dir)
163
+ FileUtils.mkdir(dir)
164
+ @file_count += 1
165
+ dir
166
+ end
167
+ end
168
+ end
169
+ end
@@ -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