rake-pipeline-web-filters 0.5.0 → 0.7.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.
- data/.gitignore +2 -0
- data/Gemfile +1 -0
- data/Rakefile +8 -0
- data/lib/rake-pipeline-web-filters.rb +17 -3
- data/lib/rake-pipeline-web-filters/cache_buster_filter.rb +42 -0
- data/lib/rake-pipeline-web-filters/chained_filter.rb +116 -0
- data/lib/rake-pipeline-web-filters/coffee_script_filter.rb +41 -0
- data/lib/rake-pipeline-web-filters/filter_with_dependencies.rb +27 -0
- data/lib/rake-pipeline-web-filters/gzip_filter.rb +59 -0
- data/lib/rake-pipeline-web-filters/handlebars_filter.rb +62 -0
- data/lib/rake-pipeline-web-filters/helpers.rb +100 -18
- data/lib/rake-pipeline-web-filters/iife_filter.rb +38 -0
- data/lib/rake-pipeline-web-filters/less_filter.rb +55 -0
- data/lib/rake-pipeline-web-filters/markdown_filter.rb +70 -0
- data/lib/rake-pipeline-web-filters/minispade_filter.rb +21 -5
- data/lib/rake-pipeline-web-filters/neuter_filter.rb +110 -0
- data/lib/rake-pipeline-web-filters/sass_filter.rb +87 -0
- data/lib/rake-pipeline-web-filters/stylus_filter.rb +59 -0
- data/lib/rake-pipeline-web-filters/tilt_filter.rb +16 -3
- data/lib/rake-pipeline-web-filters/uglify_filter.rb +66 -0
- data/lib/rake-pipeline-web-filters/version.rb +1 -1
- data/lib/rake-pipeline-web-filters/yui_css_filter.rb +70 -0
- data/lib/rake-pipeline-web-filters/yui_javascript_filter.rb +59 -0
- data/rake-pipeline-web-filters.gemspec +10 -1
- data/spec/cache_buster_filter_spec.rb +105 -0
- data/spec/chained_filter_spec.rb +76 -0
- data/spec/coffee_script_filter_spec.rb +110 -0
- data/spec/gzip_filter_spec.rb +49 -0
- data/spec/handlebars_filter_spec.rb +70 -0
- data/spec/helpers_spec.rb +112 -18
- data/spec/iife_filter_spec.rb +55 -0
- data/spec/less_filter_spec.rb +59 -0
- data/spec/markdown_filter_spec.rb +86 -0
- data/spec/minispade_filter_spec.rb +47 -15
- data/spec/neuter_filter_spec.rb +204 -0
- data/spec/sass_filter_spec.rb +147 -0
- data/spec/spec_helper.rb +10 -1
- data/spec/stylus_filter_spec.rb +69 -0
- data/spec/tilt_filter_spec.rb +25 -1
- data/spec/uglify_filter_spec.rb +82 -0
- data/spec/yui_css_filter_spec.rb +88 -0
- data/spec/yui_javascript_filter_spec.rb +68 -0
- metadata +225 -19
- data/lib/rake-pipeline-web-filters/ordering_concat_filter.rb +0 -38
- data/lib/rake-pipeline-web-filters/sass_compiler.rb +0 -53
- data/spec/ordering_concat_filter_spec.rb +0 -39
- data/spec/sass_compiler_spec.rb +0 -89
@@ -1,4 +1,4 @@
|
|
1
|
-
require '
|
1
|
+
require 'rake-pipeline-web-filters/filter_with_dependencies'
|
2
2
|
|
3
3
|
module Rake::Pipeline::Web::Filters
|
4
4
|
# A filter that accepts a series of inputs and translates
|
@@ -6,6 +6,8 @@ module Rake::Pipeline::Web::Filters
|
|
6
6
|
# to guess which template language to use based on the input
|
7
7
|
# file extension.
|
8
8
|
#
|
9
|
+
# Requires {http://rubygems.org/gems/tilt/ tilt}
|
10
|
+
#
|
9
11
|
# @example
|
10
12
|
# !!!ruby
|
11
13
|
# Rake::Pipeline.build do
|
@@ -19,17 +21,24 @@ module Rake::Pipeline::Web::Filters
|
|
19
21
|
# end
|
20
22
|
# end
|
21
23
|
class TiltFilter < Rake::Pipeline::Filter
|
24
|
+
include Rake::Pipeline::Web::Filters::FilterWithDependencies
|
25
|
+
|
22
26
|
# @return [Hash] a hash of options to pass to Tilt
|
23
27
|
# when rendering.
|
24
28
|
attr_reader :options
|
25
29
|
|
30
|
+
# @return [Object] an object to use as the rendering
|
31
|
+
# context.
|
32
|
+
attr_reader :context
|
33
|
+
|
26
34
|
# @param [Hash] options options to pass to the Tilt
|
27
35
|
# template class constructor.
|
28
36
|
# @param [Proc] block a block to use as the Filter's
|
29
37
|
# {#output_name_generator}.
|
30
|
-
def initialize(options={}, &block)
|
38
|
+
def initialize(options={}, context = nil, &block)
|
31
39
|
super(&block)
|
32
40
|
@options = options
|
41
|
+
@context = context || Object.new
|
33
42
|
end
|
34
43
|
|
35
44
|
# Implement the {#generate_output} method required by
|
@@ -45,7 +54,7 @@ module Rake::Pipeline::Web::Filters
|
|
45
54
|
def generate_output(inputs, output)
|
46
55
|
inputs.each do |input|
|
47
56
|
out = if (template_class = Tilt[input.path])
|
48
|
-
template_class.new(nil, 1, options) { |t| input.read }.render
|
57
|
+
template_class.new(nil, 1, options) { |t| input.read }.render(context)
|
49
58
|
else
|
50
59
|
input.read
|
51
60
|
end
|
@@ -53,5 +62,9 @@ module Rake::Pipeline::Web::Filters
|
|
53
62
|
output.write out
|
54
63
|
end
|
55
64
|
end
|
65
|
+
|
66
|
+
def external_dependencies
|
67
|
+
[ 'tilt' ]
|
68
|
+
end
|
56
69
|
end
|
57
70
|
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
require 'rake-pipeline-web-filters/filter_with_dependencies'
|
2
|
+
|
3
|
+
module Rake::Pipeline::Web::Filters
|
4
|
+
# A filter that uses the Uglify JS compressor to compress
|
5
|
+
# JavaScript input files.
|
6
|
+
#
|
7
|
+
# Requires {http://rubygems.org/gems/uglifier uglifier}.
|
8
|
+
#
|
9
|
+
# @example
|
10
|
+
# !!!ruby
|
11
|
+
# Rake::Pipeline.build do
|
12
|
+
# input "app/assets", "**/*.js"
|
13
|
+
# output "public"
|
14
|
+
#
|
15
|
+
# # Compile each JS file under the app/assets
|
16
|
+
# # directory.
|
17
|
+
# filter Rake::Pipeline::Web::Filters::UglifyFilter
|
18
|
+
# end
|
19
|
+
class UglifyFilter < Rake::Pipeline::Filter
|
20
|
+
include Rake::Pipeline::Web::Filters::FilterWithDependencies
|
21
|
+
|
22
|
+
# @return [Hash] a hash of options to pass to Uglify
|
23
|
+
# when compiling.
|
24
|
+
attr_reader :options
|
25
|
+
|
26
|
+
# @param [Hash] options options to pass to Uglify
|
27
|
+
# @param [Proc] block a block to use as the Filter's
|
28
|
+
# {#output_name_generator}.
|
29
|
+
def initialize(options={}, &block)
|
30
|
+
block ||= proc { |input|
|
31
|
+
if input =~ %r{min.js$}
|
32
|
+
input
|
33
|
+
else
|
34
|
+
input.sub(/\.js$/, '.min.js')
|
35
|
+
end
|
36
|
+
}
|
37
|
+
|
38
|
+
super(&block)
|
39
|
+
@options = options
|
40
|
+
end
|
41
|
+
|
42
|
+
# Implement the {#generate_output} method required by
|
43
|
+
# the {Filter} API. Compiles each input file with Uglify.
|
44
|
+
#
|
45
|
+
# @param [Array<FileWrapper>] inputs an Array of
|
46
|
+
# {FileWrapper} objects representing the inputs to
|
47
|
+
# this filter.
|
48
|
+
# @param [FileWrapper] output a single {FileWrapper}
|
49
|
+
# object representing the output.
|
50
|
+
def generate_output(inputs, output)
|
51
|
+
inputs.each do |input|
|
52
|
+
if input.path =~ %r{min.js$}
|
53
|
+
output.write input.read
|
54
|
+
else
|
55
|
+
output.write Uglifier.compile(input.read, options)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
private
|
61
|
+
|
62
|
+
def external_dependencies
|
63
|
+
[ 'uglifier' ]
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
@@ -0,0 +1,70 @@
|
|
1
|
+
require 'rake-pipeline-web-filters/filter_with_dependencies'
|
2
|
+
|
3
|
+
module Rake::Pipeline::Web::Filters
|
4
|
+
# A filter that compresses CSS input files using
|
5
|
+
# the YUI CSS compressor.
|
6
|
+
#
|
7
|
+
# Requires {https://rubygems.org/gems/yui-compressor yui-compressor}
|
8
|
+
#
|
9
|
+
# @example
|
10
|
+
# !!!ruby
|
11
|
+
# Rake::Pipeline.build do
|
12
|
+
# input "app/assets", "**/*.js"
|
13
|
+
# output "public"
|
14
|
+
#
|
15
|
+
# # Compress each CSS file under the app/assets
|
16
|
+
# # directory.
|
17
|
+
# filter Rake::Pipeline::Web::Filters::YUICssFilter
|
18
|
+
# end
|
19
|
+
class YUICssFilter < Rake::Pipeline::Filter
|
20
|
+
include Rake::Pipeline::Web::Filters::FilterWithDependencies
|
21
|
+
|
22
|
+
# @return [Hash] a hash of options to pass to the
|
23
|
+
# YUI compressor when compressing.
|
24
|
+
attr_reader :options
|
25
|
+
|
26
|
+
# @param [Hash] options options to pass to the YUI
|
27
|
+
# CSS compressor.
|
28
|
+
# @param [Proc] block a block to use as the Filter's
|
29
|
+
# {#output_name_generator}.
|
30
|
+
def initialize(options={}, &block)
|
31
|
+
block ||= proc { |input|
|
32
|
+
if input =~ %r{min.css$}
|
33
|
+
input
|
34
|
+
else
|
35
|
+
input.sub /\.css$/, '.min.css'
|
36
|
+
end
|
37
|
+
}
|
38
|
+
|
39
|
+
super(&block)
|
40
|
+
@options = options
|
41
|
+
end
|
42
|
+
|
43
|
+
# Implement the {#generate_output} method required by
|
44
|
+
# the {Filter} API. Compresses each input file with
|
45
|
+
# the YUI CSS compressor.
|
46
|
+
#
|
47
|
+
# @param [Array<FileWrapper>] inputs an Array of
|
48
|
+
# {FileWrapper} objects representing the inputs to
|
49
|
+
# this filter.
|
50
|
+
# @param [FileWrapper] output a single {FileWrapper}
|
51
|
+
# object representing the output.
|
52
|
+
def generate_output(inputs, output)
|
53
|
+
compressor = YUI::CssCompressor.new(options)
|
54
|
+
inputs.each do |input|
|
55
|
+
if input.path !~ /min\.css/
|
56
|
+
output.write compressor.compress(input.read)
|
57
|
+
else
|
58
|
+
output.write input.read
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
private
|
64
|
+
|
65
|
+
def external_dependencies
|
66
|
+
[ 'yui/compressor' ]
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
@@ -0,0 +1,59 @@
|
|
1
|
+
require 'rake-pipeline-web-filters/filter_with_dependencies'
|
2
|
+
|
3
|
+
module Rake::Pipeline::Web::Filters
|
4
|
+
# A filter that compresses JavaScript input files using
|
5
|
+
# the YUI JavaScript compressor.
|
6
|
+
#
|
7
|
+
# Requires {https://rubygems.org/gems/yui-compressor yui-compressor}
|
8
|
+
#
|
9
|
+
# @example
|
10
|
+
# !!!ruby
|
11
|
+
# Rake::Pipeline.build do
|
12
|
+
# input "app/assets", "**/*.js"
|
13
|
+
# output "public"
|
14
|
+
#
|
15
|
+
# # Compress each JS file under the app/assets
|
16
|
+
# # directory.
|
17
|
+
# filter Rake::Pipeline::Web::Filters::YUIJavaScriptFilter
|
18
|
+
# end
|
19
|
+
class YUIJavaScriptFilter < Rake::Pipeline::Filter
|
20
|
+
include Rake::Pipeline::Web::Filters::FilterWithDependencies
|
21
|
+
|
22
|
+
# @return [Hash] a hash of options to pass to the
|
23
|
+
# YUI compressor when compressing.
|
24
|
+
attr_reader :options
|
25
|
+
|
26
|
+
# @param [Hash] options options to pass to the YUI
|
27
|
+
# JavaScript compressor.
|
28
|
+
# @param [Proc] block a block to use as the Filter's
|
29
|
+
# {#output_name_generator}.
|
30
|
+
def initialize(options={}, &block)
|
31
|
+
block ||= proc { |input| input.sub(/\.js$/, '.min.js') }
|
32
|
+
super(&block)
|
33
|
+
@options = options
|
34
|
+
end
|
35
|
+
|
36
|
+
# Implement the {#generate_output} method required by
|
37
|
+
# the {Filter} API. Compresses each input file with
|
38
|
+
# the YUI JavaScript compressor.
|
39
|
+
#
|
40
|
+
# @param [Array<FileWrapper>] inputs an Array of
|
41
|
+
# {FileWrapper} objects representing the inputs to
|
42
|
+
# this filter.
|
43
|
+
# @param [FileWrapper] output a single {FileWrapper}
|
44
|
+
# object representing the output.
|
45
|
+
def generate_output(inputs, output)
|
46
|
+
compressor = YUI::JavaScriptCompressor.new(options)
|
47
|
+
inputs.each do |input|
|
48
|
+
output.write compressor.compress(input.read)
|
49
|
+
end
|
50
|
+
end
|
51
|
+
|
52
|
+
private
|
53
|
+
|
54
|
+
def external_dependencies
|
55
|
+
[ 'yui/compressor' ]
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
@@ -15,10 +15,19 @@ Gem::Specification.new do |gem|
|
|
15
15
|
gem.require_paths = ["lib"]
|
16
16
|
gem.version = Rake::Pipeline::Web::Filters::VERSION
|
17
17
|
|
18
|
-
gem.add_dependency "rake-pipeline"
|
18
|
+
gem.add_dependency "rake-pipeline", "~> 0.6"
|
19
|
+
gem.add_dependency "rack"
|
19
20
|
|
20
21
|
gem.add_development_dependency "rspec"
|
21
22
|
gem.add_development_dependency "tilt"
|
22
23
|
gem.add_development_dependency "sass"
|
23
24
|
gem.add_development_dependency "compass"
|
25
|
+
gem.add_development_dependency "coffee-script"
|
26
|
+
gem.add_development_dependency "redcarpet", '~> 2.0'
|
27
|
+
gem.add_development_dependency "yui-compressor"
|
28
|
+
gem.add_development_dependency "uglifier"
|
29
|
+
gem.add_development_dependency "less"
|
30
|
+
gem.add_development_dependency "json"
|
31
|
+
gem.add_development_dependency "therubyracer"
|
32
|
+
gem.add_development_dependency "stylus"
|
24
33
|
end
|
@@ -0,0 +1,105 @@
|
|
1
|
+
describe "CacheBusterFilter" do
|
2
|
+
MemoryFileWrapper ||= Rake::Pipeline::SpecHelpers::MemoryFileWrapper
|
3
|
+
CacheBusterFilter ||= Rake::Pipeline::Web::Filters::CacheBusterFilter
|
4
|
+
|
5
|
+
let(:content) { "it doesn't matter" }
|
6
|
+
|
7
|
+
let(:input_file) {
|
8
|
+
MemoryFileWrapper.new '/path/to/input', 'file.txt', 'UTF-8', content
|
9
|
+
}
|
10
|
+
|
11
|
+
let(:output_root) {
|
12
|
+
'/path/to/output'
|
13
|
+
}
|
14
|
+
|
15
|
+
def setup_filter(filter)
|
16
|
+
filter.file_wrapper_class = MemoryFileWrapper
|
17
|
+
filter.input_files = [ input_file ]
|
18
|
+
filter.output_root = output_root
|
19
|
+
filter.rake_application = Rake::Application.new
|
20
|
+
filter
|
21
|
+
end
|
22
|
+
|
23
|
+
describe 'DEFAULT_KEY_GENERATOR' do
|
24
|
+
|
25
|
+
subject { CacheBusterFilter::DEFAULT_KEY_GENERATOR }
|
26
|
+
|
27
|
+
it "returns the MD5 hash of the input's file name and contents" do
|
28
|
+
expected = Digest::MD5.new << input_file.path << content
|
29
|
+
subject.call(input_file).should == expected
|
30
|
+
end
|
31
|
+
|
32
|
+
end
|
33
|
+
|
34
|
+
describe 'with the default cache key strategy' do
|
35
|
+
|
36
|
+
let(:output_file) {
|
37
|
+
key = CacheBusterFilter::DEFAULT_KEY_GENERATOR.call(input_file)
|
38
|
+
MemoryFileWrapper.new output_root, "file-#{key}.txt", 'UTF-8'
|
39
|
+
}
|
40
|
+
|
41
|
+
subject { setup_filter CacheBusterFilter.new }
|
42
|
+
|
43
|
+
it 'outputs to the MD5 hash of the file name and contents' do
|
44
|
+
subject.output_files.should == [ output_file ]
|
45
|
+
end
|
46
|
+
|
47
|
+
it 'passes file contents through unchanged' do
|
48
|
+
tasks = subject.generate_rake_tasks
|
49
|
+
tasks.each(&:invoke)
|
50
|
+
file = MemoryFileWrapper.files[ output_file.fullpath ]
|
51
|
+
file.body.should == content
|
52
|
+
file.encoding.should == 'UTF-8'
|
53
|
+
end
|
54
|
+
|
55
|
+
end
|
56
|
+
|
57
|
+
describe 'with a custom key strategy' do
|
58
|
+
|
59
|
+
let(:output_file) {
|
60
|
+
MemoryFileWrapper.new output_root, 'file-foo.txt', 'UTF-8'
|
61
|
+
}
|
62
|
+
|
63
|
+
subject do
|
64
|
+
setup_filter(CacheBusterFilter.new() { 'foo' })
|
65
|
+
end
|
66
|
+
|
67
|
+
it 'uses the custom key strategy' do
|
68
|
+
subject.output_files.should == [ output_file ]
|
69
|
+
end
|
70
|
+
|
71
|
+
end
|
72
|
+
|
73
|
+
describe 'for an input file with multiple dots' do
|
74
|
+
let(:input_file) {
|
75
|
+
MemoryFileWrapper.new '/path/to/input', 'my.text.file.txt', 'UTF-8', content
|
76
|
+
}
|
77
|
+
|
78
|
+
let(:output_file) {
|
79
|
+
MemoryFileWrapper.new output_root, "my.text.file-foo.txt", 'UTF-8'
|
80
|
+
}
|
81
|
+
|
82
|
+
subject { setup_filter(CacheBusterFilter.new() { 'foo' }) }
|
83
|
+
|
84
|
+
it 'appends the busting key to the penultimate part' do
|
85
|
+
subject.output_files.should == [ output_file ]
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
describe 'for an input file with no dots' do
|
90
|
+
let(:input_file) {
|
91
|
+
MemoryFileWrapper.new '/path/to/input', 'my_text_file', 'UTF-8', content
|
92
|
+
}
|
93
|
+
|
94
|
+
let(:output_file) {
|
95
|
+
MemoryFileWrapper.new output_root, "my_text_file-foo", 'UTF-8'
|
96
|
+
}
|
97
|
+
|
98
|
+
subject { setup_filter(CacheBusterFilter.new() { 'foo' }) }
|
99
|
+
|
100
|
+
it 'appends the busting key to the end of the filename' do
|
101
|
+
subject.output_files.should == [ output_file ]
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
end
|
@@ -0,0 +1,76 @@
|
|
1
|
+
describe "ChainedFilter" do
|
2
|
+
MemoryFileWrapper ||= Rake::Pipeline::SpecHelpers::MemoryFileWrapper
|
3
|
+
ChainedFilter ||= Rake::Pipeline::Web::Filters::ChainedFilter
|
4
|
+
|
5
|
+
input_file1 = MemoryFileWrapper.new("/path", "input.js.strip_asserts.erb", "UTF-8", <<-CONTENT)
|
6
|
+
assert("must be true", true);
|
7
|
+
Input = {};
|
8
|
+
<%= $chained_filter_title %> = {};
|
9
|
+
CONTENT
|
10
|
+
|
11
|
+
input_file2 = MemoryFileWrapper.new("/path", "input.js.erb.strip_asserts", "UTF-8", <<-CONTENT)
|
12
|
+
assert("must be true", true);
|
13
|
+
Input = {};
|
14
|
+
<%= $chained_filter_title %> = {};
|
15
|
+
CONTENT
|
16
|
+
|
17
|
+
EXPECTED_OUTPUT = <<-EXPECTED
|
18
|
+
|
19
|
+
Input = {};
|
20
|
+
Chained = {};
|
21
|
+
EXPECTED
|
22
|
+
|
23
|
+
let(:erb_filter) do
|
24
|
+
Class.new(Rake::Pipeline::Filter) do
|
25
|
+
def generate_output(inputs, output)
|
26
|
+
inputs.each do |input|
|
27
|
+
output.write ERB.new(input.read).result
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
let(:strip_asserts_filter) do
|
34
|
+
Class.new(Rake::Pipeline::Filter) do
|
35
|
+
def generate_output(inputs, output)
|
36
|
+
inputs.each do |input|
|
37
|
+
output.write input.read.gsub(/^assert.*$/, '')
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
before do
|
44
|
+
$chained_filter_title = "Chained"
|
45
|
+
end
|
46
|
+
|
47
|
+
after do
|
48
|
+
$chained_filter_title = nil
|
49
|
+
end
|
50
|
+
|
51
|
+
[ input_file1, input_file2 ].each do |file_wrapper|
|
52
|
+
it "should run through the filters in order" do
|
53
|
+
filter = ChainedFilter.new(
|
54
|
+
:types => {
|
55
|
+
:erb => erb_filter,
|
56
|
+
:strip_asserts => strip_asserts_filter
|
57
|
+
}
|
58
|
+
)
|
59
|
+
|
60
|
+
filter.file_wrapper_class = MemoryFileWrapper
|
61
|
+
filter.input_files = [ file_wrapper ]
|
62
|
+
filter.output_root = "/output"
|
63
|
+
filter.rake_application = Rake::Application.new
|
64
|
+
|
65
|
+
filter.output_files.should == [ MemoryFileWrapper.new("/output", "input.js", "UTF-8") ]
|
66
|
+
|
67
|
+
tasks = filter.generate_rake_tasks
|
68
|
+
tasks.each(&:invoke)
|
69
|
+
|
70
|
+
file = MemoryFileWrapper.files["/output/input.js"]
|
71
|
+
file.body.should == EXPECTED_OUTPUT
|
72
|
+
file.encoding.should == "UTF-8"
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
end
|