From b0efe93fbebc37a308e7ed31f1446de08bee017e Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 7 Apr 2013 21:03:30 -0400 Subject: [PATCH 01/89] Allows the user to ignore properties and selectors when matching --- CHANGELOG.md | 4 ++++ lib/csscss/cli.rb | 24 ++++++++++++++++++------ lib/csscss/redundancy_analyzer.rb | 11 +++++++++-- test/csscss/redundancy_analyzer_test.rb | 24 +++++++++++++++++++++--- 4 files changed, 52 insertions(+), 11 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 90aca2e..00387a1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## (Unreleased) ## + +* Allows the user to specify ignored properties and selectors + ## 0.2.1 - 3/28/2013 ## * Changes coloring to the selectors and declarations diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index aed4007..16d28fb 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -1,11 +1,13 @@ module Csscss class CLI def initialize(argv) - @argv = argv - @verbose = false - @color = true - @minimum = 3 - @compass = false + @argv = argv + @verbose = false + @color = true + @minimum = 3 + @compass = false + @ignored_properties = [] + @ignored_selectors = [] end def run @@ -40,7 +42,9 @@ def execute open(filename) {|f| f.read } end - RedundancyAnalyzer.new(contents).redundancies(@minimum) + RedundancyAnalyzer.new(contents).redundancies(minimum: @minimum, + ignored_properties: @ignored_properties, + ignored_selectors: @ignored_selectors) end combined_redundancies = all_redundancies.inject({}) do |combined, redundancies| @@ -83,6 +87,14 @@ def parse(argv) @minimum = n end + opts.on("--ignore-properties property1,property2,...", Array, "Ignore these properties when finding matches") do |ignored_properties| + @ignored_properties = ignored_properties + end + + opts.on('--ignore-selectors "selector1","selector2",...', Array, "Ignore these selectors when finding matches") do |ignored_selectors| + @ignored_selectors = ignored_selectors + end + opts.on("-V", "--version", "Show version") do |v| puts opts.ver exit diff --git a/lib/csscss/redundancy_analyzer.rb b/lib/csscss/redundancy_analyzer.rb index e58344e..04a1109 100644 --- a/lib/csscss/redundancy_analyzer.rb +++ b/lib/csscss/redundancy_analyzer.rb @@ -5,13 +5,20 @@ def initialize(raw_css) @raw_css = raw_css end - def redundancies(minimum = nil) + def redundancies(opts = {}) + minimum = opts[:minimum] + ignored_properties = opts[:ignored_properties] || [] + ignored_selectors = opts[:ignored_selectors] || [] + rule_sets = Parser::Css.parse(@raw_css) matches = {} parents = {} rule_sets.each do |rule_set| + next if ignored_selectors.include?(rule_set.selectors.selectors) + sel = rule_set.selectors + rule_set.declarations.each do |dec| - sel = rule_set.selectors + next if ignored_properties.include?(dec.property) if parser = shorthand_parser(dec.property) if new_decs = parser.parse(dec.property, dec.value) diff --git a/test/csscss/redundancy_analyzer_test.rb b/test/csscss/redundancy_analyzer_test.rb index ba17ba3..efc8bfd 100644 --- a/test/csscss/redundancy_analyzer_test.rb +++ b/test/csscss/redundancy_analyzer_test.rb @@ -22,7 +22,7 @@ module Csscss [sel(".bar"), sel("h1, h2")] , [dec("outline", "none"), dec("position", "relative")] ] - RedundancyAnalyzer.new(css).redundancies(2).must_equal({ + RedundancyAnalyzer.new(css).redundancies(minimum:2).must_equal({ [sel(".bar"), sel("h1, h2")] => [dec("outline", "none"), dec("position", "relative")] }) end @@ -88,7 +88,7 @@ module Csscss } $ - redundancies = RedundancyAnalyzer.new(css).redundancies(3) + redundancies = RedundancyAnalyzer.new(css).redundancies(minimum:3) redundancies[[sel(".bar"), sel(".bar2"), sel(".baz")]].size.must_equal(5) end @@ -230,7 +230,7 @@ module Csscss [sel(".bar"), sel(".baz"), sel(".foo")] => [dec("border-style", "solid"), dec("border-width", "4px")] }) - RedundancyAnalyzer.new(css).redundancies(2).must_equal({ + RedundancyAnalyzer.new(css).redundancies(minimum:2).must_equal({ [sel(".bar"), sel(".baz"), sel(".foo")] => [dec("border-style", "solid"), dec("border-width", "4px")] }) end @@ -248,6 +248,24 @@ module Csscss }) end + it "ignores specific properties" do + css = %$ + h1, h2 { display: none; position: relative; outline:none} + .foo { DISPLAY: none; width: 1px } + .bar { position: relative; width: 1px; outline: none } + .baz { display: none } + $ + + RedundancyAnalyzer.new(css).redundancies(ignored_properties:%w(display outline)).must_equal({ + [sel(".bar"), sel("h1, h2")] => [dec("position", "relative")], + [sel(".bar"), sel(".foo")] => [dec("width", "1px")], + }) + + RedundancyAnalyzer.new(css).redundancies(ignored_properties:%w(display outline), ignored_selectors:%w(.foo)).must_equal({ + [sel(".bar"), sel("h1, h2")] => [dec("position", "relative")] + }) + end + # TODO: someday # it "reports duplication within the same selector" do # css = %$ From 323ce45cb9454dc61857ad51dfd3ba47bc3df4db Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 7 Apr 2013 21:10:42 -0400 Subject: [PATCH 02/89] Better parser error messages --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 9 +++++++-- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 00387a1..222317f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,7 @@ ## (Unreleased) ## * Allows the user to specify ignored properties and selectors +* Better parse error messages ## 0.2.1 - 3/28/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 16d28fb..0dae221 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -65,8 +65,13 @@ def execute end rescue Parslet::ParseFailed => e - puts "Had a problem parsing the css" - puts e.cause.ascii_tree + line, column = e.cause.source.line_and_column + puts "Had a problem parsing the css at line: #{line}, column: #{column}".red + if ENV['CSSCSS_DEBUG'] == 'true' + puts e.cause.ascii_tree.red + else + puts "Run with CSSCSS_DEBUG=true for verbose parser errors".red + end exit 1 end From 701d2b32ca23b26bbf142489e9b1eafb3731534c Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 7 Apr 2013 23:04:05 -0400 Subject: [PATCH 03/89] Bumping version to 1.0 --- CHANGELOG.md | 2 +- Gemfile.lock | 2 +- lib/csscss/version.rb | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 222317f..c044bb1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,4 @@ -## (Unreleased) ## +## 1.0.0 - 4/7/2013 ## * Allows the user to specify ignored properties and selectors * Better parse error messages diff --git a/Gemfile.lock b/Gemfile.lock index 2795a01..3f99f6d 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - csscss (0.2.1) + csscss (1.0.0) colorize parslet (~> 1.5) diff --git a/lib/csscss/version.rb b/lib/csscss/version.rb index 731f27b..626f701 100644 --- a/lib/csscss/version.rb +++ b/lib/csscss/version.rb @@ -1,3 +1,3 @@ module Csscss - VERSION = "0.2.1" + VERSION = "1.0.0" end From 268677fd8a1a84cf6bba69931406b43b658fb5ff Mon Sep 17 00:00:00 2001 From: Steve Richert Date: Tue, 9 Apr 2013 08:01:51 -0300 Subject: [PATCH 04/89] Adds Code Climate badge to the README --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index 372db46..a0bfa51 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,5 @@ [![Build Status](https://travis-ci.org/zmoazeni/csscss.png?branch=master)](https://travis-ci.org/zmoazeni/csscss) +[![Code Climate](https://codeclimate.com/github/zmoazeni/csscss.png)](https://codeclimate.com/github/zmoazeni/csscss) ## What is it? ## From 7d653e670fa3812c92a80e452632821607e9d29d Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Wed, 10 Apr 2013 08:42:29 -0400 Subject: [PATCH 05/89] Fixes bug where --no-color isn't respected Fixes #17 --- CHANGELOG.md | 4 ++++ lib/csscss/cli.rb | 2 +- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index c044bb1..780cd2e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## (Unreleased) ## + +* Fixes bug where CLI --no-color wasn't respected + ## 1.0.0 - 4/7/2013 ## * Allows the user to specify ignored properties and selectors diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 0dae221..88b5c86 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -60,7 +60,7 @@ def execute if @json puts JSONReporter.new(combined_redundancies).report else - report = Reporter.new(combined_redundancies).report(verbose:@verbose, color:true) + report = Reporter.new(combined_redundancies).report(verbose:@verbose, color:@color) puts report unless report.empty? end From 5a710819b6463b28305398118a986ca0ac6c2da0 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Wed, 10 Apr 2013 08:44:12 -0400 Subject: [PATCH 06/89] Formatting --- lib/csscss/cli.rb | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 88b5c86..8f387b8 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -42,9 +42,11 @@ def execute open(filename) {|f| f.read } end - RedundancyAnalyzer.new(contents).redundancies(minimum: @minimum, - ignored_properties: @ignored_properties, - ignored_selectors: @ignored_selectors) + RedundancyAnalyzer.new(contents).redundancies( + minimum: @minimum, + ignored_properties: @ignored_properties, + ignored_selectors: @ignored_selectors + ) end combined_redundancies = all_redundancies.inject({}) do |combined, redundancies| From 7e05506c5f6862f57a096e1879bc24c40de1cca9 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Wed, 10 Apr 2013 08:45:28 -0400 Subject: [PATCH 07/89] Updates README to mention no ruby 1.8 support --- README.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/README.md b/README.md index a0bfa51..e6855bc 100644 --- a/README.md +++ b/README.md @@ -21,6 +21,9 @@ First you need to install it. It is currently packaged as a ruby gem: $ gem install csscss +Note: csscss only works on ruby 1.9.x and up. It will have trouble with ruby +1.8.x. + Then you can run it in at the command line against CSS files. $ csscss path/to/styles.css path/to/other-styles.css From ae2f22f4416bca35f903970c15aa1685a8d237cd Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Wed, 10 Apr 2013 08:48:03 -0400 Subject: [PATCH 08/89] More formatting --- README.md | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/README.md b/README.md index e6855bc..a58cea7 100644 --- a/README.md +++ b/README.md @@ -21,8 +21,7 @@ First you need to install it. It is currently packaged as a ruby gem: $ gem install csscss -Note: csscss only works on ruby 1.9.x and up. It will have trouble with ruby -1.8.x. +Note: csscss only works on ruby 1.9.x and up. It will have trouble with ruby 1.8.x. Then you can run it in at the command line against CSS files. From 1e57c9deebe038a0e05afa3485c180e894b1f704 Mon Sep 17 00:00:00 2001 From: Carson McDonald Date: Thu, 11 Apr 2013 13:02:28 -0400 Subject: [PATCH 09/89] Add a required version of ruby to the gemspec. --- csscss.gemspec | 2 ++ 1 file changed, 2 insertions(+) diff --git a/csscss.gemspec b/csscss.gemspec index c085f2e..bde9976 100644 --- a/csscss.gemspec +++ b/csscss.gemspec @@ -17,6 +17,8 @@ Gem::Specification.new do |gem| gem.test_files = gem.files.grep(%r{^(test|spec|features)/}) gem.require_paths = ["lib"] + gem.required_ruby_version = ">= 1.9.2" + gem.add_dependency "parslet", "~> 1.5" gem.add_dependency "colorize" end From cdd4edb73cc5be6cd2d21d1a8b722af0edf86ded Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Thu, 11 Apr 2013 23:14:26 -0400 Subject: [PATCH 10/89] Dropping the ruby version requirement to all 1.9+ I'm fairly sure I don't need to specify the patch level. We'll see if I'm wrong More info can be found here http://guides.rubygems.org/specification-reference/#required_ruby_version= --- csscss.gemspec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/csscss.gemspec b/csscss.gemspec index bde9976..3cde362 100644 --- a/csscss.gemspec +++ b/csscss.gemspec @@ -17,7 +17,7 @@ Gem::Specification.new do |gem| gem.test_files = gem.files.grep(%r{^(test|spec|features)/}) gem.require_paths = ["lib"] - gem.required_ruby_version = ">= 1.9.2" + gem.required_ruby_version = ">= 1.9" gem.add_dependency "parslet", "~> 1.5" gem.add_dependency "colorize" From 215392b0059ae1b6acfa54388e461ba5d8a234f7 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Thu, 11 Apr 2013 23:17:42 -0400 Subject: [PATCH 11/89] Adds a CONTRIBUTORS file --- CHANGELOG.md | 2 ++ CONTRIBUTORS.md | 2 ++ 2 files changed, 4 insertions(+) create mode 100644 CONTRIBUTORS.md diff --git a/CHANGELOG.md b/CHANGELOG.md index 780cd2e..ae7ae39 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,8 @@ ## (Unreleased) ## * Fixes bug where CLI --no-color wasn't respected +* Added ruby version requirement for >= 1.9 +* Added CONTRIBUTORS.md ## 1.0.0 - 4/7/2013 ## diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md new file mode 100644 index 0000000..853b9a4 --- /dev/null +++ b/CONTRIBUTORS.md @@ -0,0 +1,2 @@ +* Zach Moazeni @zmoazeni +* Carson McDonald @carsonmcdonald From c4c687d77f591f9741b8eb05ce2bffd7d556560b Mon Sep 17 00:00:00 2001 From: Carson McDonald Date: Thu, 11 Apr 2013 07:06:56 -0400 Subject: [PATCH 12/89] Accept dashes and numbers in http urls. Add some tests for http urls with dashes and numbers in them. --- lib/csscss/parser/common.rb | 2 +- test/csscss/parser/common_test.rb | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/lib/csscss/parser/common.rb b/lib/csscss/parser/common.rb index 18116c4..e1ed9fb 100644 --- a/lib/csscss/parser/common.rb +++ b/lib/csscss/parser/common.rb @@ -18,7 +18,7 @@ module Common rule(:nada) { any.repeat.as(:nada) } rule(:http) { - (match['a-zA-Z.:/'] | str('\(') | str('\)')).repeat >> space? + (match['a-zA-Z0-9.:/\-'] | str('\(') | str('\)')).repeat >> space? } rule(:url) { diff --git a/test/csscss/parser/common_test.rb b/test/csscss/parser/common_test.rb index 0087976..bb53955 100644 --- a/test/csscss/parser/common_test.rb +++ b/test/csscss/parser/common_test.rb @@ -115,6 +115,10 @@ class CommonTest @parser.http.must_parse 'foo\(bar\).jpg' @parser.http.must_parse 'http://foo\(bar\).jpg' @parser.http.must_parse 'http://foo.com/baz/\(bar\).jpg' + @parser.http.must_parse '//foo.com/foo.jpg' + @parser.http.must_parse 'https://foo.com/foo.jpg' + @parser.http.must_parse 'http://foo100.com/foo.jpg' + @parser.http.must_parse 'http://foo-bar.com/foo.jpg' end it "parses urls" do From 082513978dcebb36f3894e4cd66661d0cde57c38 Mon Sep 17 00:00:00 2001 From: Carson McDonald Date: Thu, 11 Apr 2013 07:11:12 -0400 Subject: [PATCH 13/89] Accept data urls as valid urls. Add tests for data urls. --- lib/csscss/parser/common.rb | 5 +++++ test/csscss/parser/common_test.rb | 6 ++++++ 2 files changed, 11 insertions(+) diff --git a/lib/csscss/parser/common.rb b/lib/csscss/parser/common.rb index e1ed9fb..4a3d965 100644 --- a/lib/csscss/parser/common.rb +++ b/lib/csscss/parser/common.rb @@ -21,9 +21,14 @@ module Common (match['a-zA-Z0-9.:/\-'] | str('\(') | str('\)')).repeat >> space? } + rule(:data) { + stri("data:") >> match['a-zA-Z0-9.:/+;,=\-'].repeat >> space? + } + rule(:url) { stri("url") >> parens do (any_quoted { http } >> space?) | + (any_quoted { data } >> space?) | http end } diff --git a/test/csscss/parser/common_test.rb b/test/csscss/parser/common_test.rb index bb53955..75fbde6 100644 --- a/test/csscss/parser/common_test.rb +++ b/test/csscss/parser/common_test.rb @@ -121,6 +121,11 @@ class CommonTest @parser.http.must_parse 'http://foo-bar.com/foo.jpg' end + it "parses data" do + @parser.data.must_parse 'data:image/jpg;base64,IMGDATAGOESHERE==' + @parser.data.must_parse 'data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==' + end + it "parses urls" do @parser.url.must_parse "url(foo.jpg)" @parser.url.must_parse "url( foo.jpg )" @@ -128,6 +133,7 @@ class CommonTest @parser.url.must_parse "url('foo.jpg')" @parser.url.must_parse "url('foo.jpg' )" @parser.url.must_parse 'url(foo\(bar\).jpg)' + @parser.url.must_parse "url('data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==')" end end end From d540beed1c52751868c563d9e27ee5e6b13c64bd Mon Sep 17 00:00:00 2001 From: Carson McDonald Date: Thu, 11 Apr 2013 07:07:15 -0400 Subject: [PATCH 14/89] Fix broken test by removing incorrectly identified duplicate. --- test/csscss/redundancy_analyzer_test.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/csscss/redundancy_analyzer_test.rb b/test/csscss/redundancy_analyzer_test.rb index efc8bfd..d37283a 100644 --- a/test/csscss/redundancy_analyzer_test.rb +++ b/test/csscss/redundancy_analyzer_test.rb @@ -68,7 +68,7 @@ module Csscss .baz { margin: 3px 3px 30px 3px; padding: 10px 30px; - background: white url(images/bg-bolt-inactive.png) no-repeat 99% 5px; + background: blue url(images/bg-bolt-inactive.png) no-repeat 99% 5px; -webkit-border-radius: 4px; -moz-border-radius: 4px; From e7a2be9133efcbd3492ced15f4b72a64460c52d4 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Thu, 11 Apr 2013 23:27:15 -0400 Subject: [PATCH 15/89] Updates CHANGELOG with url bug fixes This is a modified pull request from https://github.com/zmoazeni/csscss/pull/31 that squashes some code/test commits. Thanks @carsonmcdonald for the hand. --- CHANGELOG.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index ae7ae39..9020bf8 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,8 @@ * Fixes bug where CLI --no-color wasn't respected * Added ruby version requirement for >= 1.9 * Added CONTRIBUTORS.md +* Fixes bugs with urls that have dashes in them +* Fixes bugs with urls containing encoded data (usually images) ## 1.0.0 - 4/7/2013 ## From 6036abefe1373b8eb4d8cd5a2b679682574982da Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Thu, 11 Apr 2013 23:41:05 -0400 Subject: [PATCH 16/89] Deprecates CSSCSS_DEBUG in favor of --show-parser-errors refs: #9 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 13 +++++++++++-- 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9020bf8..5d31823 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ * Added CONTRIBUTORS.md * Fixes bugs with urls that have dashes in them * Fixes bugs with urls containing encoded data (usually images) +* Deprecates CSSCSS_DEBUG in favor of --show-parser-errors ## 1.0.0 - 4/7/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 8f387b8..634ebc7 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -16,6 +16,7 @@ def run end def execute + warn_old_debug_flag if ENV["CSSCSS_DEBUG"] all_redundancies = @argv.map do |filename| contents = if %w(.scss .sass).include?(File.extname(filename).downcase) && !(filename =~ URI.regexp) @@ -69,10 +70,10 @@ def execute rescue Parslet::ParseFailed => e line, column = e.cause.source.line_and_column puts "Had a problem parsing the css at line: #{line}, column: #{column}".red - if ENV['CSSCSS_DEBUG'] == 'true' + if @show_parser_errors || ENV['CSSCSS_DEBUG'] == 'true' puts e.cause.ascii_tree.red else - puts "Run with CSSCSS_DEBUG=true for verbose parser errors".red + puts "Run with --show-parser-errors for verbose parser errors".red end exit 1 end @@ -122,6 +123,10 @@ def parse(argv) @json = j end + opts.on("--show-parser-errors", "Print verbose parser errors") do |show_parser_errors| + @show_parser_errors = show_parser_errors + end + opts.on_tail("-h", "--help", "Show this message") do print_help(opts) end @@ -139,6 +144,10 @@ def print_help(opts) exit end + def warn_old_debug_flag + $stderr.puts "CSSCSS_DEBUG is now deprecated. Use --show-parser-errors instead".red + end + class << self def run(argv) new(argv).run From 071ed0b4ff4fa605564c49b256d96ff6b27725cf Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Thu, 11 Apr 2013 23:44:07 -0400 Subject: [PATCH 17/89] Tweaks some help language --- lib/csscss/cli.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 634ebc7..38df2a8 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -87,7 +87,7 @@ def parse(argv) @verbose = v end - opts.on("--[no-]color", "Colorizes output") do |c| + opts.on("--[no-]color", "Colorize output (default is true)") do |c| @color = c end @@ -108,7 +108,7 @@ def parse(argv) exit end - opts.on("--[no-]compass", "Enables compass extensions when parsing sass/scss") do |compass| + opts.on("--[no-]compass", "Enable compass extensions when parsing sass/scss (default is false)") do |compass| if @compass = compass begin require "compass" From 7ccd982babdd6e139190b1501bec648842ca93e7 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Thu, 11 Apr 2013 23:48:44 -0400 Subject: [PATCH 18/89] Fixes line/column output with typical parse errors refs: #9 --- lib/csscss/cli.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 38df2a8..531f63a 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -68,7 +68,7 @@ def execute end rescue Parslet::ParseFailed => e - line, column = e.cause.source.line_and_column + line, column = e.cause.source.line_and_column(e.cause.pos) puts "Had a problem parsing the css at line: #{line}, column: #{column}".red if @show_parser_errors || ENV['CSSCSS_DEBUG'] == 'true' puts e.cause.ascii_tree.red From 26cfc692418b8ae9d88f222791d3920d33e92be9 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Thu, 11 Apr 2013 23:49:54 -0400 Subject: [PATCH 19/89] Updates CHANGELOG for previous commit Dangit. Wish I had paused before pushing --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 5d31823..69c44d4 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,7 @@ * Fixes bugs with urls that have dashes in them * Fixes bugs with urls containing encoded data (usually images) * Deprecates CSSCSS_DEBUG in favor of --show-parser-errors +* Fixes line/column output during parser errors ## 1.0.0 - 4/7/2013 ## From f5d239954fae157ca2b4c714d015a2d7ec2a00e6 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 00:13:17 -0400 Subject: [PATCH 20/89] Using abort() instead of explicit print/exit --- lib/csscss/cli.rb | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 531f63a..170e064 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -23,8 +23,7 @@ def execute begin require "sass" rescue LoadError - puts "Must install sass gem before parsing sass/scss files" - exit 1 + abort "Must install sass gem before parsing sass/scss files" end sass_options = {cache:false} From e6c3b80cb226225a6a40a5f31deceeb35e7988e7 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 00:16:01 -0400 Subject: [PATCH 21/89] --compass now pulls in default config.rb and adds --compass-with-config I'm assuming that "config.rb" is a standard compass config name. If not this needs to change up. refs: #13 --- CHANGELOG.md | 2 ++ CONTRIBUTORS.md | 1 + lib/csscss/cli.rb | 26 ++++++++++++++++++-------- 3 files changed, 21 insertions(+), 8 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 69c44d4..8eaddae 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,8 @@ * Fixes bugs with urls containing encoded data (usually images) * Deprecates CSSCSS_DEBUG in favor of --show-parser-errors * Fixes line/column output during parser errors +* --compass now grabs config.rb by default if it exists +* Adds --compass-with-config that lets users specify a config ## 1.0.0 - 4/7/2013 ## diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md index 853b9a4..cd60c0a 100644 --- a/CONTRIBUTORS.md +++ b/CONTRIBUTORS.md @@ -1,2 +1,3 @@ * Zach Moazeni @zmoazeni * Carson McDonald @carsonmcdonald +* Martin Kuckert @MKuckert diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 170e064..05b2179 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -108,14 +108,12 @@ def parse(argv) end opts.on("--[no-]compass", "Enable compass extensions when parsing sass/scss (default is false)") do |compass| - if @compass = compass - begin - require "compass" - rescue LoadError - puts "Must install compass gem before enabling its extensions" - exit 1 - end - end + enable_compass if @compass = compass + end + + opts.on("--compass-with-config config", "Enable compass extensions when parsing sass/scss and pass config file") do |config| + @compass = true + enable_compass(config) end opts.on("-j", "--[no-]json", "Output results in JSON") do |j| @@ -147,6 +145,18 @@ def warn_old_debug_flag $stderr.puts "CSSCSS_DEBUG is now deprecated. Use --show-parser-errors instead".red end + def enable_compass(config = nil) + require "compass" + + if config + Compass.add_configuration(config) + else + Compass.add_configuration("config.rb") if File.exist?("config.rb") + end + rescue LoadError + abort "Must install compass gem before enabling its extensions" + end + class << self def run(argv) new(argv).run From 236552e26af5ea5ee088fd6003951d7e7f2c7c37 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 00:25:40 -0400 Subject: [PATCH 22/89] Fixes parser error bug when trying to parse blank files This fix is a little hokey but it'll do for now. refs: #37 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 14 +++++++++----- 2 files changed, 10 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 8eaddae..6dd7fe4 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -9,6 +9,7 @@ * Fixes line/column output during parser errors * --compass now grabs config.rb by default if it exists * Adds --compass-with-config that lets users specify a config +* Fixes parser error bug when trying to parse blank files ## 1.0.0 - 4/7/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 05b2179..be035ce 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -42,11 +42,15 @@ def execute open(filename) {|f| f.read } end - RedundancyAnalyzer.new(contents).redundancies( - minimum: @minimum, - ignored_properties: @ignored_properties, - ignored_selectors: @ignored_selectors - ) + if contents.strip.empty? + {} + else + RedundancyAnalyzer.new(contents).redundancies( + minimum: @minimum, + ignored_properties: @ignored_properties, + ignored_selectors: @ignored_selectors + ) + end end combined_redundancies = all_redundancies.inject({}) do |combined, redundancies| From c80ad2a0143f5214ca4a795b4a8154d5583841d9 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 01:01:01 -0400 Subject: [PATCH 23/89] Compares rules across files Previously some comparisons were dropped due to minimums within a file refs: #16 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 38 +++++++++++++------------------------- 2 files changed, 14 insertions(+), 25 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6dd7fe4..d0abc57 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ * --compass now grabs config.rb by default if it exists * Adds --compass-with-config that lets users specify a config * Fixes parser error bug when trying to parse blank files +* Fixes bug where rules from multiple files aren't consolidated ## 1.0.0 - 4/7/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index be035ce..dca2e13 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -18,8 +18,8 @@ def run def execute warn_old_debug_flag if ENV["CSSCSS_DEBUG"] - all_redundancies = @argv.map do |filename| - contents = if %w(.scss .sass).include?(File.extname(filename).downcase) && !(filename =~ URI.regexp) + all_contents = @argv.map do |filename| + if %w(.scss .sass).include?(File.extname(filename).downcase) && !(filename =~ URI.regexp) begin require "sass" rescue LoadError @@ -41,35 +41,23 @@ def execute else open(filename) {|f| f.read } end + end.join("\n") - if contents.strip.empty? - {} - else - RedundancyAnalyzer.new(contents).redundancies( - minimum: @minimum, - ignored_properties: @ignored_properties, - ignored_selectors: @ignored_selectors - ) - end - end + unless all_contents.strip.empty? + redundancies = RedundancyAnalyzer.new(all_contents).redundancies( + minimum: @minimum, + ignored_properties: @ignored_properties, + ignored_selectors: @ignored_selectors + ) - combined_redundancies = all_redundancies.inject({}) do |combined, redundancies| - if combined.empty? - redundancies + if @json + puts JSONReporter.new(redundancies).report else - combined.merge(redundancies) do |_, v1, v2| - (v1 + v2).uniq - end + report = Reporter.new(redundancies).report(verbose:@verbose, color:@color) + puts report unless report.empty? end end - if @json - puts JSONReporter.new(combined_redundancies).report - else - report = Reporter.new(combined_redundancies).report(verbose:@verbose, color:@color) - puts report unless report.empty? - end - rescue Parslet::ParseFailed => e line, column = e.cause.source.line_and_column(e.cause.pos) puts "Had a problem parsing the css at line: #{line}, column: #{column}".red From 16918da674b261adbdeb40614394e16c31a01357 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 01:15:51 -0400 Subject: [PATCH 24/89] Adds --no-match-shorthand so users can opt out of shorthand matching I'm fine with keeping shorthand matching the default, but I respect some people don't like it. refs: #20 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 8 +++++++- lib/csscss/redundancy_analyzer.rb | 3 ++- test/csscss/redundancy_analyzer_test.rb | 9 +++++++++ 4 files changed, 19 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index d0abc57..412c94e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -11,6 +11,7 @@ * Adds --compass-with-config that lets users specify a config * Fixes parser error bug when trying to parse blank files * Fixes bug where rules from multiple files aren't consolidated +* Adds --no-match-shorthand to allow users to opt out of shorthand matching ## 1.0.0 - 4/7/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index dca2e13..54aebb2 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -8,6 +8,7 @@ def initialize(argv) @compass = false @ignored_properties = [] @ignored_selectors = [] + @match_shorthand = true end def run @@ -47,7 +48,8 @@ def execute redundancies = RedundancyAnalyzer.new(all_contents).redundancies( minimum: @minimum, ignored_properties: @ignored_properties, - ignored_selectors: @ignored_selectors + ignored_selectors: @ignored_selectors, + match_shorthand: @match_shorthand ) if @json @@ -108,6 +110,10 @@ def parse(argv) enable_compass(config) end + opts.on("--[no-]match-shorthand", "Expands shorthand rules and matches on explicit rules (default is true)") do |match_shorthand| + @match_shorthand = match_shorthand + end + opts.on("-j", "--[no-]json", "Output results in JSON") do |j| @json = j end diff --git a/lib/csscss/redundancy_analyzer.rb b/lib/csscss/redundancy_analyzer.rb index 04a1109..fd0773c 100644 --- a/lib/csscss/redundancy_analyzer.rb +++ b/lib/csscss/redundancy_analyzer.rb @@ -9,6 +9,7 @@ def redundancies(opts = {}) minimum = opts[:minimum] ignored_properties = opts[:ignored_properties] || [] ignored_selectors = opts[:ignored_selectors] || [] + match_shorthand = opts.fetch(:match_shorthand, true) rule_sets = Parser::Css.parse(@raw_css) matches = {} @@ -20,7 +21,7 @@ def redundancies(opts = {}) rule_set.declarations.each do |dec| next if ignored_properties.include?(dec.property) - if parser = shorthand_parser(dec.property) + if match_shorthand && parser = shorthand_parser(dec.property) if new_decs = parser.parse(dec.property, dec.value) if dec.property == "border" %w(border-top border-right border-bottom border-left).each do |property| diff --git a/test/csscss/redundancy_analyzer_test.rb b/test/csscss/redundancy_analyzer_test.rb index d37283a..7de8b88 100644 --- a/test/csscss/redundancy_analyzer_test.rb +++ b/test/csscss/redundancy_analyzer_test.rb @@ -184,6 +184,15 @@ module Csscss }) end + it "doesn't match shorthand when explicitly turned off" do + css = %$ + .foo { background-color: #fff } + .bar { background: #fff } + $ + + RedundancyAnalyzer.new(css).redundancies(match_shorthand:false).must_equal({}) + end + it "3-way case consolidation" do css = %$ .bar { background: #fff } From cc55bd38946e54ca2d1a3101d2ad89afea644a2a Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 01:18:36 -0400 Subject: [PATCH 25/89] Adds @kopipejst to CONTRIBUTORS for his help Especially for #20 --- CONTRIBUTORS.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md index cd60c0a..f877ddf 100644 --- a/CONTRIBUTORS.md +++ b/CONTRIBUTORS.md @@ -1,3 +1,4 @@ * Zach Moazeni @zmoazeni * Carson McDonald @carsonmcdonald * Martin Kuckert @MKuckert +* Ivan Lazarevic @kopipejst From cb91c5e62c93d12727e73253092cd7f9a949bd16 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 01:22:55 -0400 Subject: [PATCH 26/89] Fixes URL now that github changed the github pages domain More info: https://github.com/blog/1452-new-github-pages-domain-github-io --- csscss.gemspec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/csscss.gemspec b/csscss.gemspec index 3cde362..07a2f31 100644 --- a/csscss.gemspec +++ b/csscss.gemspec @@ -10,7 +10,7 @@ Gem::Specification.new do |gem| gem.email = ["zach.moazeni@gmail.com"] gem.summary = %q{A CSS redundancy analyzer that analyzes redundancy.} gem.description = %q{csscss will parse any CSS files you give it and let you know which rulesets have duplicated declarations.} - gem.homepage = "http://zmoazeni.github.com/csscss/" + gem.homepage = "http://zmoazeni.github.io/csscss/" gem.files = `git ls-files`.split($/) gem.executables = gem.files.grep(%r{^bin/}).map{ |f| File.basename(f) } From ccc7ddb10f4d1952f5df70722af69695fb563906 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 12 Apr 2013 01:24:02 -0400 Subject: [PATCH 27/89] Bumping version to 1.1.0 for release --- CHANGELOG.md | 2 +- Gemfile.lock | 2 +- lib/csscss/version.rb | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 412c94e..572ebbc 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,4 @@ -## (Unreleased) ## +## 1.1.0 - 4/12/2013 ## * Fixes bug where CLI --no-color wasn't respected * Added ruby version requirement for >= 1.9 diff --git a/Gemfile.lock b/Gemfile.lock index 3f99f6d..ffb5e38 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - csscss (1.0.0) + csscss (1.1.0) colorize parslet (~> 1.5) diff --git a/lib/csscss/version.rb b/lib/csscss/version.rb index 626f701..b32754b 100644 --- a/lib/csscss/version.rb +++ b/lib/csscss/version.rb @@ -1,3 +1,3 @@ module Csscss - VERSION = "1.0.0" + VERSION = "1.1.0" end From d5ba00f9b6dbcc0d21d35c7ccf01efaac14adf75 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 13 Apr 2013 11:48:36 -0400 Subject: [PATCH 28/89] Matches lengths with just 0 or 0-with-unit as duplicates Most of this work was by @mduvall Some stackoverflow discussion: http://stackoverflow.com/a/935113/410759 refs: #42, #32 --- CHANGELOG.md | 4 ++++ CONTRIBUTORS.md | 1 + lib/csscss/parser/common.rb | 24 +++++++++++++----------- lib/csscss/redundancy_analyzer.rb | 1 - lib/csscss/types.rb | 13 +++++++++++-- test/csscss/parser/common_test.rb | 2 ++ test/csscss/redundancy_analyzer_test.rb | 12 ++++++++++++ test/csscss/types_test.rb | 8 ++++++++ 8 files changed, 51 insertions(+), 14 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 572ebbc..37d797d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## (Unreleased) + +* 0 and 0px are now reconciled as redundancies + ## 1.1.0 - 4/12/2013 ## * Fixes bug where CLI --no-color wasn't respected diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md index f877ddf..2cb044a 100644 --- a/CONTRIBUTORS.md +++ b/CONTRIBUTORS.md @@ -2,3 +2,4 @@ * Carson McDonald @carsonmcdonald * Martin Kuckert @MKuckert * Ivan Lazarevic @kopipejst +* Matt DuVall @mduvall twitter:@mduvall_ diff --git a/lib/csscss/parser/common.rb b/lib/csscss/parser/common.rb index 4a3d965..50ff07a 100644 --- a/lib/csscss/parser/common.rb +++ b/lib/csscss/parser/common.rb @@ -5,17 +5,19 @@ module Common UNITS = %w(px em ex in cm mm pt pc) - rule(:space) { match['\s'].repeat(1) } - rule(:space?) { space.maybe } - rule(:number) { match["0-9"] } - rule(:numbers) { number.repeat(1) } - rule(:decimal) { numbers >> str(".").maybe >> numbers.maybe } - rule(:percent) { decimal >> stri("%") >> space? } - rule(:length) { decimal >> stri_list(UNITS) >> space? } - rule(:identifier) { match["a-zA-Z"].repeat(1) } - rule(:inherit) { stri("inherit") } - rule(:eof) { any.absent? } - rule(:nada) { any.repeat.as(:nada) } + rule(:space) { match['\s'].repeat(1) } + rule(:space?) { space.maybe } + rule(:number) { match["0-9"] } + rule(:numbers) { number.repeat(1) } + rule(:decimal) { numbers >> str(".").maybe >> numbers.maybe } + rule(:percent) { decimal >> stri("%") >> space? } + rule(:non_zero_length) { decimal >> stri_list(UNITS) >> space? } + rule(:zero_length) { match["0"] } + rule(:length) { zero_length | non_zero_length } + rule(:identifier) { match["a-zA-Z"].repeat(1) } + rule(:inherit) { stri("inherit") } + rule(:eof) { any.absent? } + rule(:nada) { any.repeat.as(:nada) } rule(:http) { (match['a-zA-Z0-9.:/\-'] | str('\(') | str('\)')).repeat >> space? diff --git a/lib/csscss/redundancy_analyzer.rb b/lib/csscss/redundancy_analyzer.rb index fd0773c..be9de91 100644 --- a/lib/csscss/redundancy_analyzer.rb +++ b/lib/csscss/redundancy_analyzer.rb @@ -65,7 +65,6 @@ def redundancies(opts = {}) end end - # trims any derivative declarations alongside shorthand inverted_matches.each do |selectors, declarations| redundant_derivatives = declarations.select do |dec| diff --git a/lib/csscss/types.rb b/lib/csscss/types.rb index 0cbcd74..cfdb727 100644 --- a/lib/csscss/types.rb +++ b/lib/csscss/types.rb @@ -30,14 +30,14 @@ def without_parents def ==(other) if other.respond_to?(:property) && other.respond_to?(:value) - property == other.property && value == other.value + eql?(other) else false end end def hash - [property, value].hash + [property, normalize_value(value)].hash end def eql?(other) @@ -67,6 +67,15 @@ def inspect "<#{self.class} #{to_s}>" end end + + private + def normalize_value(value) + if value =~ /^0(#{Csscss::Parser::Common::UNITS.join("|")}|%)$/ + "0" + else + value + end + end end class Selector < Struct.new(:selectors) diff --git a/test/csscss/parser/common_test.rb b/test/csscss/parser/common_test.rb index 75fbde6..aac34f0 100644 --- a/test/csscss/parser/common_test.rb +++ b/test/csscss/parser/common_test.rb @@ -106,6 +106,8 @@ class CommonTest @parser.length.must_parse "123px" @parser.length.must_parse "123EM" @parser.length.must_parse "1.23Pt" + @parser.length.must_parse "0" + @parser.length.wont_parse "1" end end diff --git a/test/csscss/redundancy_analyzer_test.rb b/test/csscss/redundancy_analyzer_test.rb index 7de8b88..8f72e25 100644 --- a/test/csscss/redundancy_analyzer_test.rb +++ b/test/csscss/redundancy_analyzer_test.rb @@ -275,6 +275,18 @@ module Csscss }) end + it "matches 0 and 0px" do + css = %$ + .bar { padding: 0; } + .foo { padding: 0px; } + $ + + RedundancyAnalyzer.new(css).redundancies.must_equal({ + [sel(".bar"), sel(".foo")] => [dec("padding", "0")] + }) + end + + # TODO: someday # it "reports duplication within the same selector" do # css = %$ diff --git a/test/csscss/types_test.rb b/test/csscss/types_test.rb index de80520..b2dca94 100644 --- a/test/csscss/types_test.rb +++ b/test/csscss/types_test.rb @@ -69,5 +69,13 @@ module Csscss h[dec2].must_equal true h[dec3].must_equal true end + + it "equates 0 length with and without units" do + Declaration.new("padding", "0px").must_equal Declaration.new("padding", "0") + Declaration.new("padding", "0%").must_equal Declaration.new("padding", "0") + Declaration.new("padding", "0").must_equal Declaration.new("padding", "0em") + + Declaration.new("padding", "1").wont_equal Declaration.new("padding", "1px") + end end end From c18e8d47fb663e31b7be39c9c75292c72bc482fe Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 13 Apr 2013 11:58:50 -0400 Subject: [PATCH 29/89] Disables color support on windows env where ruby < 2.0 I've gotten a report that color support on windows && ruby 2.0 just works. So let's try and only disable it in window && ruby 1.9 refs: #48, #44 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 8 ++++++-- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 37d797d..6c639d7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,7 @@ ## (Unreleased) * 0 and 0px are now reconciled as redundancies +* Disables color support by default for windows & ruby < 2.0 ## 1.1.0 - 4/12/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 54aebb2..afb217d 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -3,7 +3,7 @@ class CLI def initialize(argv) @argv = argv @verbose = false - @color = true + @color = !windows_1_9 @minimum = 3 @compass = false @ignored_properties = [] @@ -80,7 +80,7 @@ def parse(argv) @verbose = v end - opts.on("--[no-]color", "Colorize output (default is true)") do |c| + opts.on("--[no-]color", "Colorize output (default is #{@color})") do |c| @color = c end @@ -155,6 +155,10 @@ def enable_compass(config = nil) abort "Must install compass gem before enabling its extensions" end + def windows_1_9 + RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/ && RUBY_VERSION =~ /^1\.9/ + end + class << self def run(argv) new(argv).run From e39fb6b6cc8c2862ce557d13f0836a4ff8d60fcb Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 13 Apr 2013 12:22:20 -0400 Subject: [PATCH 30/89] Fixes bug where unquoted url(data..) wasn't being parsed refs: #46 --- CHANGELOG.md | 1 + lib/csscss/parser/common.rb | 2 +- test/csscss/parser/common_test.rb | 14 ++++++++------ 3 files changed, 10 insertions(+), 7 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6c639d7..fc7d722 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,7 @@ * 0 and 0px are now reconciled as redundancies * Disables color support by default for windows & ruby < 2.0 +* Fixes bug where unquoted url(data...) isn't parsed correctly ## 1.1.0 - 4/12/2013 ## diff --git a/lib/csscss/parser/common.rb b/lib/csscss/parser/common.rb index 50ff07a..84abb82 100644 --- a/lib/csscss/parser/common.rb +++ b/lib/csscss/parser/common.rb @@ -31,7 +31,7 @@ module Common stri("url") >> parens do (any_quoted { http } >> space?) | (any_quoted { data } >> space?) | - http + data | http end } diff --git a/test/csscss/parser/common_test.rb b/test/csscss/parser/common_test.rb index aac34f0..41c4b92 100644 --- a/test/csscss/parser/common_test.rb +++ b/test/csscss/parser/common_test.rb @@ -117,15 +117,16 @@ class CommonTest @parser.http.must_parse 'foo\(bar\).jpg' @parser.http.must_parse 'http://foo\(bar\).jpg' @parser.http.must_parse 'http://foo.com/baz/\(bar\).jpg' - @parser.http.must_parse '//foo.com/foo.jpg' - @parser.http.must_parse 'https://foo.com/foo.jpg' - @parser.http.must_parse 'http://foo100.com/foo.jpg' - @parser.http.must_parse 'http://foo-bar.com/foo.jpg' + @parser.http.must_parse "//foo.com/foo.jpg" + @parser.http.must_parse "https://foo.com/foo.jpg" + @parser.http.must_parse "http://foo100.com/foo.jpg" + @parser.http.must_parse "http://foo-bar.com/foo.jpg" end it "parses data" do - @parser.data.must_parse 'data:image/jpg;base64,IMGDATAGOESHERE==' - @parser.data.must_parse 'data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==' + @parser.data.must_parse "data:image/jpg;base64,IMGDATAGOESHERE==" + @parser.data.must_parse "data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==" + @parser.data.must_parse "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC" end it "parses urls" do @@ -135,6 +136,7 @@ class CommonTest @parser.url.must_parse "url('foo.jpg')" @parser.url.must_parse "url('foo.jpg' )" @parser.url.must_parse 'url(foo\(bar\).jpg)' + @parser.url.must_parse "url(data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==)" @parser.url.must_parse "url('data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==')" end end From 828d4c801a5a9266d261ae2a770d1991cb46303b Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 13 Apr 2013 19:46:56 -0400 Subject: [PATCH 31/89] Fixes semicolon parsing within a url The dynamic block is pretty hookey, but I think it might work. It is doing a manual lookbehind to see if there is an open parenthesis. Not the prettiest code, but it should work. It is also downcasing the base64 encoded data, which could cause collision issues, but encoded images are so uncommon that I don't think it will be a big issue. For now. refs: #46 --- lib/csscss/parser/css.rb | 16 +++++++++++++++- test/csscss/parser/css_test.rb | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+), 1 deletion(-) diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index a9025bc..a3de861 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -25,7 +25,21 @@ class Parser < Parslet::Parser rule(:attribute) { match["^:{}"].repeat(1).as(:property) >> str(":") >> - match["^;}"].repeat(1).as(:value) >> + dynamic {|source, context| + pos = source.pos + matcher = match["^;}"].repeat(1) + success, result = matcher.apply(source, context) + source.pos = pos + result ||= [] + left_paren = result.rindex("(") + right_paren = result.rindex(")") || -1 + + if success && left_paren && left_paren > right_paren + matcher >> str(";") >> matcher + else + matcher + end + }.as(:value) >> str(";").maybe >> space? } diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index e6a956a..91ca4bb 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -134,6 +134,39 @@ module Css rs(sel("h1"), [dec("display", "none")]) ]) end + + it "parses attributes with encoded data that include semicolons" do + trans(%$ + .foo1 { + background: rgb(123, 123, 123) url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x; + display: block; + } + + .foo2 { + background: white url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x + } + + .foo3 { + outline: 1px; + background: white url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x; + display: block; + } + + .foo4 { + background: blue url(images/bg-bolt-inactive.png) no-repeat 99% 5px; + display: block; + } + $).must_equal([ + rs(sel(".foo1"), [dec("background", "rgb(123, 123, 123) url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x"), + dec("display", "block")]), + rs(sel(".foo2"), [dec("background", "white url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x")]), + rs(sel(".foo3"), [dec("outline", "1px"), + dec("background", "white url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x"), + dec("display", "block")]), + rs(sel(".foo4"), [dec("background", "blue url(images/bg-bolt-inactive.png) no-repeat 99% 5px"), + dec("display", "block")]) + ]) + end end end end From d5586858cdf9551c7ce00a5a73893ca049edaa65 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 13 Apr 2013 20:05:29 -0400 Subject: [PATCH 32/89] Revert "Fixes semicolon parsing within a url" This reverts commit 828d4c801a5a9266d261ae2a770d1991cb46303b. While this fixes the parser, it tanks performance. Need to figure out a better solution --- lib/csscss/parser/css.rb | 16 +--------------- test/csscss/parser/css_test.rb | 33 --------------------------------- 2 files changed, 1 insertion(+), 48 deletions(-) diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index a3de861..a9025bc 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -25,21 +25,7 @@ class Parser < Parslet::Parser rule(:attribute) { match["^:{}"].repeat(1).as(:property) >> str(":") >> - dynamic {|source, context| - pos = source.pos - matcher = match["^;}"].repeat(1) - success, result = matcher.apply(source, context) - source.pos = pos - result ||= [] - left_paren = result.rindex("(") - right_paren = result.rindex(")") || -1 - - if success && left_paren && left_paren > right_paren - matcher >> str(";") >> matcher - else - matcher - end - }.as(:value) >> + match["^;}"].repeat(1).as(:value) >> str(";").maybe >> space? } diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index 91ca4bb..e6a956a 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -134,39 +134,6 @@ module Css rs(sel("h1"), [dec("display", "none")]) ]) end - - it "parses attributes with encoded data that include semicolons" do - trans(%$ - .foo1 { - background: rgb(123, 123, 123) url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x; - display: block; - } - - .foo2 { - background: white url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x - } - - .foo3 { - outline: 1px; - background: white url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x; - display: block; - } - - .foo4 { - background: blue url(images/bg-bolt-inactive.png) no-repeat 99% 5px; - display: block; - } - $).must_equal([ - rs(sel(".foo1"), [dec("background", "rgb(123, 123, 123) url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x"), - dec("display", "block")]), - rs(sel(".foo2"), [dec("background", "white url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x")]), - rs(sel(".foo3"), [dec("outline", "1px"), - dec("background", "white url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x"), - dec("display", "block")]), - rs(sel(".foo4"), [dec("background", "blue url(images/bg-bolt-inactive.png) no-repeat 99% 5px"), - dec("display", "block")]) - ]) - end end end end From 226a081be7500aad28224bce90bf783ce9e38a17 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 14 Apr 2013 08:18:03 -0400 Subject: [PATCH 33/89] Adds support for LESS css This support behaves very similar to the SASS support. It will attempt to compile the css prior to checking for redundancies. For c-versions of ruby, therubyracer is required. For jruby, therubyrhino. More information can be found at http://lesscss.org/ refs: #52, #10 --- CHANGELOG.md | 1 + CONTRIBUTORS.md | 1 + Gemfile | 2 ++ Gemfile.lock | 10 ++++++ README.md | 11 ++++++- lib/csscss/cli.rb | 77 +++++++++++++++++++++++++++++++++-------------- 6 files changed, 78 insertions(+), 24 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index fc7d722..5a7a89f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,7 @@ * 0 and 0px are now reconciled as redundancies * Disables color support by default for windows & ruby < 2.0 * Fixes bug where unquoted url(data...) isn't parsed correctly +* Adds support for LESS files ## 1.1.0 - 4/12/2013 ## diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md index 2cb044a..492bdb3 100644 --- a/CONTRIBUTORS.md +++ b/CONTRIBUTORS.md @@ -3,3 +3,4 @@ * Martin Kuckert @MKuckert * Ivan Lazarevic @kopipejst * Matt DuVall @mduvall twitter:@mduvall_ +* Mekka Okereke @mekka @mekkaokereke diff --git a/Gemfile b/Gemfile index fa46110..46e2ea9 100644 --- a/Gemfile +++ b/Gemfile @@ -6,6 +6,8 @@ gemspec # optional runtime dependencies gem "sass" gem "compass" +gem "less" +gem "therubyracer", :platform => :mri gem "rake", :require => false gem "debugger" diff --git a/Gemfile.lock b/Gemfile.lock index ffb5e38..626e8d9 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -12,6 +12,7 @@ GEM chunky_png (1.2.7) colorize (0.5.8) columnize (0.3.6) + commonjs (0.2.6) compass (0.12.2) chunky_png (~> 1.2) fssm (>= 0.2.7) @@ -23,6 +24,9 @@ GEM debugger-linecache (1.2.0) debugger-ruby_core_source (1.2.0) fssm (0.2.10) + less (2.3.1) + commonjs (~> 0.2.6) + libv8 (3.11.8.17) m (1.3.1) method_source (>= 0.6.7) rake (>= 0.9.2.2) @@ -32,8 +36,12 @@ GEM parslet (1.5.0) blankslate (~> 2.0) rake (10.0.3) + ref (1.0.4) ruby-prof (0.13.0) sass (3.2.7) + therubyracer (0.11.4) + libv8 (~> 3.11.8.12) + ref PLATFORMS ruby @@ -42,9 +50,11 @@ DEPENDENCIES compass csscss! debugger + less m minitest minitest-rg rake ruby-prof sass + therubyracer diff --git a/README.md b/README.md index a58cea7..217d55b 100644 --- a/README.md +++ b/README.md @@ -45,11 +45,20 @@ rulesets that have fewer matches. $ csscss -n 10 -v path/to/style.css # ignores rulesets with < 10 matches -If you prefer writing in sass, you can also parse your sass/scss files. +If you prefer writing in [sass](http://sass-lang.com/), you can also parse your sass/scss files. $ gem install sass $ csscss path/to/style.scss +If you prefer writing in [LESS](http://lesscss.org/), you can also parse your LESS files. + + $ gem install less + $ csscss path/to/style.less + +LESS requires an additional javascript runtime. +[v8/therubyracer](https://rubygems.org/gems/therubyracer) on most +rubies, and [therubyrhino](https://rubygems.org/gems/therubyrhino) on +jruby. ## I found bugs ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index afb217d..9eaf195 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -8,7 +8,7 @@ def initialize(argv) @compass = false @ignored_properties = [] @ignored_selectors = [] - @match_shorthand = true + @match_shorthand = true end def run @@ -16,31 +16,22 @@ def run execute end + private def execute warn_old_debug_flag if ENV["CSSCSS_DEBUG"] - all_contents = @argv.map do |filename| - if %w(.scss .sass).include?(File.extname(filename).downcase) && !(filename =~ URI.regexp) - begin - require "sass" - rescue LoadError - abort "Must install sass gem before parsing sass/scss files" - end - - sass_options = {cache:false} - sass_options[:load_paths] = Compass.configuration.sass_load_paths if @compass - begin - Sass::Engine.for_file(filename, sass_options).render - rescue Sass::SyntaxError => e - if e.message =~ /compass/ && !@compass - puts "Enable --compass option to use compass's extensions" - exit 1 - else - raise e - end - end + all_contents= @argv.map do |filename| + if filename =~ URI.regexp + load_css_file(filename) else - open(filename) {|f| f.read } + case File.extname(filename).downcase + when ".scss", ".sass" + load_sass_file(filename) + when ".less" + load_less_file(filename) + else + load_css_file(filename) + end end end.join("\n") @@ -133,7 +124,6 @@ def parse(argv) print_help(opts) end - private def print_help(opts) puts opts exit @@ -159,6 +149,47 @@ def windows_1_9 RbConfig::CONFIG['host_os'] =~ /mswin|mingw|cygwin/ && RUBY_VERSION =~ /^1\.9/ end + def gem_installed?(gem_name) + begin + require gem_name + true + rescue LoadError + false + end + end + + def load_sass_file(filename) + if !gem_installed?("sass") then + abort 'Must install the "sass" gem before parsing sass/scss files' + end + + sass_options = {cache:false} + sass_options[:load_paths] = Compass.configuration.sass_load_paths if @compass + begin + Sass::Engine.for_file(filename, sass_options).render + rescue Sass::SyntaxError => e + if e.message =~ /compass/ && !@compass + puts "Enable --compass option to use compass's extensions" + exit 1 + else + raise e + end + end + end + + def load_less_file(filename) + if !gem_installed?("less") then + abort 'Must install the "less" gem before parsing less files' + end + + contents = load_css_file(filename) + Less::Parser.new.parse(contents).to_css + end + + def load_css_file(filename) + open(filename) {|f| f.read } + end + class << self def run(argv) new(argv).run From a443956008a083c9d7360aa9b105edca466fb9f9 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 14 Apr 2013 09:06:33 -0400 Subject: [PATCH 34/89] Fixes semicolon parsing within a url This is a different implementation than 828d4c801a5a9266d261ae2a770d1991cb46303b It is also downcasing the base64 encoded data, which could cause collision issues, but encoded images are so uncommon that I don't think it will be a big issue. For now. refs: #46 --- lib/csscss/parser/css.rb | 8 +++++++- test/csscss/parser/css_test.rb | 33 +++++++++++++++++++++++++++++++++ 2 files changed, 40 insertions(+), 1 deletion(-) diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index a9025bc..82a38e6 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -25,7 +25,13 @@ class Parser < Parslet::Parser rule(:attribute) { match["^:{}"].repeat(1).as(:property) >> str(":") >> - match["^;}"].repeat(1).as(:value) >> + (match["^;}"].repeat(1).capture(:stuff) >> dynamic {|source, context| + if context.captures[:stuff].to_s =~ /data:/ + str(";") >> match["^;}"].repeat(1) + else + any.present? + end + }).as(:value) >> str(";").maybe >> space? } diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index e6a956a..91ca4bb 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -134,6 +134,39 @@ module Css rs(sel("h1"), [dec("display", "none")]) ]) end + + it "parses attributes with encoded data that include semicolons" do + trans(%$ + .foo1 { + background: rgb(123, 123, 123) url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x; + display: block; + } + + .foo2 { + background: white url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x + } + + .foo3 { + outline: 1px; + background: white url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAEAAACECAYAAABRaEHiAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAHRJREFUeNqkUjESwCAIw+T/X/UHansdkLTQDnXgCAHNEW2tZbDz/Aq994bzqoY5Z8wEwiEcmmfwiRK+EGOMTVBrtz4mY9kEAyz6+E3sJ7MWBs1PaUy1lHLLmgTqElltNxLiINTBbWi0Vj5DZC9CaqZEOwQYAPhxY/7527NfAAAAAElFTkSuQmCC) repeat-x; + display: block; + } + + .foo4 { + background: blue url(images/bg-bolt-inactive.png) no-repeat 99% 5px; + display: block; + } + $).must_equal([ + rs(sel(".foo1"), [dec("background", "rgb(123, 123, 123) url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x"), + dec("display", "block")]), + rs(sel(".foo2"), [dec("background", "white url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x")]), + rs(sel(".foo3"), [dec("outline", "1px"), + dec("background", "white url(data:image/png;base64,ivborw0kggoaaaansuheugaaaaeaaacecayaaabraehiaaaagxrfwhrtb2z0d2fyzqbbzg9izsbjbwfnzvjlywr5ccllpaaaahrjrefuenqkujeswcaiw+t/x/uhansdkltqdnxgcahnew2tzbdz/aq994bzqoy5z8wewiecmmfwirk+egomtvbrtz4my9keayz6+e3sj7mwbs1pauy1lhllmgtqelltnxliintbbwi0vj5dzc9caqzeowqyaphxy/7527nfaaaaaelftksuqmcc) repeat-x"), + dec("display", "block")]), + rs(sel(".foo4"), [dec("background", "blue url(images/bg-bolt-inactive.png) no-repeat 99% 5px"), + dec("display", "block")]) + ]) + end end end end From 2be0c3d65d0b123117b7f67cac028eeffbd00c35 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 14 Apr 2013 09:17:39 -0400 Subject: [PATCH 35/89] Fixes massive performance issue when using eql? Not sure if it's due to constructing the array and calling #hash on it or what, but the previous implementation is terrible on performance refs: #42, #32 --- lib/csscss/types.rb | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/lib/csscss/types.rb b/lib/csscss/types.rb index cfdb727..32afd3a 100644 --- a/lib/csscss/types.rb +++ b/lib/csscss/types.rb @@ -30,7 +30,8 @@ def without_parents def ==(other) if other.respond_to?(:property) && other.respond_to?(:value) - eql?(other) + # using eql? tanks performance + property == other.property && normalize_value(value) == normalize_value(other.value) else false end From a4de41c5bde67a41dd90c7fbd420b955ca7be783 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 14 Apr 2013 09:21:24 -0400 Subject: [PATCH 36/89] Bumping version to 1.2.0 for release --- CHANGELOG.md | 2 +- Gemfile.lock | 2 +- lib/csscss/version.rb | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 5a7a89f..e25f012 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,4 @@ -## (Unreleased) +## 1.2.0 - 4/14/2013 ## * 0 and 0px are now reconciled as redundancies * Disables color support by default for windows & ruby < 2.0 diff --git a/Gemfile.lock b/Gemfile.lock index 626e8d9..742d2f9 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - csscss (1.1.0) + csscss (1.2.0) colorize parslet (~> 1.5) diff --git a/lib/csscss/version.rb b/lib/csscss/version.rb index b32754b..b6411dc 100644 --- a/lib/csscss/version.rb +++ b/lib/csscss/version.rb @@ -1,3 +1,3 @@ module Csscss - VERSION = "1.1.0" + VERSION = "1.2.0" end From f0008a8761c98076d82ab4eef9562b640f1bcdc2 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 12:40:32 -0400 Subject: [PATCH 37/89] Adding _site to gitignore --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index af6864a..4288db2 100644 --- a/.gitignore +++ b/.gitignore @@ -15,3 +15,4 @@ spec/reports test/tmp test/version_tmp tmp +_site From d55ca7cc05a9773ec81f43356dc7788a6c428749 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 12:46:24 -0400 Subject: [PATCH 38/89] Adds --require switch to allow user specific config This will allow people to configure bundler, sass plugins, special configurations, etc. refs: #54 --- CHANGELOG.md | 4 ++++ lib/csscss/cli.rb | 4 ++++ 2 files changed, 8 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index e25f012..93e69f3 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## (Unreleased) ## + +* Adds --require switch for user configuration + ## 1.2.0 - 4/14/2013 ## * 0 and 0px are now reconciled as redundancies diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 9eaf195..860b112 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -101,6 +101,10 @@ def parse(argv) enable_compass(config) end + opts.on("--require file.rb", "Load ruby file before running csscss.", "Great for bootstrapping requires/configurations") do |file| + load file + end + opts.on("--[no-]match-shorthand", "Expands shorthand rules and matches on explicit rules (default is true)") do |match_shorthand| @match_shorthand = match_shorthand end From 0726e0d176b8a4640b6121d1e1ee4123a40a06f7 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 12:53:50 -0400 Subject: [PATCH 39/89] Deprecates --compass-with-config I knew that was a bad decision. --require will be a lot simpler refs: #54 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 11 +++++++---- 2 files changed, 8 insertions(+), 4 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 93e69f3..38ede5a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,7 @@ ## (Unreleased) ## * Adds --require switch for user configuration +* Deprecates --compass-with-config config.rb in favor of --compass --require config.rb ## 1.2.0 - 4/14/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 860b112..8d3da8c 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -18,7 +18,7 @@ def run private def execute - warn_old_debug_flag if ENV["CSSCSS_DEBUG"] + deprecate("Use --show-parser-errors instead of CSSCSS_DEBUG") if ENV["CSSCSS_DEBUG"] all_contents= @argv.map do |filename| if filename =~ URI.regexp @@ -96,7 +96,10 @@ def parse(argv) enable_compass if @compass = compass end - opts.on("--compass-with-config config", "Enable compass extensions when parsing sass/scss and pass config file") do |config| + opts.on("--compass-with-config config", "Enable compass extensions when parsing sass/scss and pass config file", + "DEPRECATED: use --compass --require path/to/config.rb instead." + ) do |config| + deprecate("Use --compass --require #{config} instead of --compass-with-config #{config}") @compass = true enable_compass(config) end @@ -133,8 +136,8 @@ def print_help(opts) exit end - def warn_old_debug_flag - $stderr.puts "CSSCSS_DEBUG is now deprecated. Use --show-parser-errors instead".red + def deprecate(message) + $stderr.puts("DEPRECATED: #{message}".yellow) end def enable_compass(config = nil) From da43eb6d141786788848f6289dce3c8d7d654986 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 13:15:23 -0400 Subject: [PATCH 40/89] Parses and ignores @import statements Users will need to run csscss on those specific files. This also fixes a bug where comments were being merged with selectors. refs: #41, #57, #58 --- CHANGELOG.md | 1 + lib/csscss/parser/css.rb | 18 +++++++++++++++++- test/csscss/parser/css_test.rb | 23 ++++++++++++++++++++++- 3 files changed, 40 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 38ede5a..d335573 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,7 @@ * Adds --require switch for user configuration * Deprecates --compass-with-config config.rb in favor of --compass --require config.rb +* Ignores @import statements. Users will need to run csscss on those directly ## 1.2.0 - 4/14/2013 ## diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index 82a38e6..49d9dd2 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -58,8 +58,22 @@ class Parser < Parslet::Parser ).as(:nested_ruleset) } + rule(:import) { + ( + stri("@import") >> + match["^;"].repeat(1) >> + str(";") >> + space? + ).as(:import) + } + rule(:blocks) { - space? >> (comment | nested_ruleset | ruleset).repeat(1).as(:blocks) >> space? + space? >> ( + comment | + import | + nested_ruleset | + ruleset + ).repeat(1).as(:blocks) >> space? } root(:blocks) @@ -70,6 +84,8 @@ class Transformer < Parslet::Transform rulesets } + rule(import: simple(:import)) { [] } + rule(comment: simple(:comment)) { nil } rule(ruleset: { diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index 91ca4bb..57dbe43 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -104,7 +104,7 @@ module Css ]) end - it "recognizes media queries" do + it "recognizes @media queries" do css = %$ @media only screen { /* some comment */ @@ -129,6 +129,27 @@ module Css ]) end + it "ignores @import statements" do + css = %$ + @import "foo.css"; + @import "bar.css"; + + /* + .x { + padding: 3px; + } + */ + + h1 { + outline: 1px; + } + $ + + trans(css).must_equal([ + rs(sel("h1"), [dec("outline", "1px")]) + ]) + end + it "ignores double semicolons" do trans("h1 { display:none;;}").must_equal([ rs(sel("h1"), [dec("display", "none")]) From 69f0c0f83dfa5158530fbe59768d4bb3525f2263 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 13:23:27 -0400 Subject: [PATCH 41/89] Formatting the switches a little --- lib/csscss/cli.rb | 30 +++++++++++++++--------------- 1 file changed, 15 insertions(+), 15 deletions(-) diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 8d3da8c..3b9a0d6 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -71,25 +71,20 @@ def parse(argv) @verbose = v end - opts.on("--[no-]color", "Colorize output (default is #{@color})") do |c| + opts.on("--[no-]color", "Colorize output", "(default is #{@color})") do |c| @color = c end - opts.on("-n", "--num N", Integer, "Print matches with at least this many rules. Defaults to 3") do |n| + opts.on("-n", "--num N", Integer, "Print matches with at least this many rules.", "(default is 3)") do |n| @minimum = n end - opts.on("--ignore-properties property1,property2,...", Array, "Ignore these properties when finding matches") do |ignored_properties| - @ignored_properties = ignored_properties - end - - opts.on('--ignore-selectors "selector1","selector2",...', Array, "Ignore these selectors when finding matches") do |ignored_selectors| - @ignored_selectors = ignored_selectors + opts.on("--[no-]match-shorthand", "Expand shorthand rules and matches on explicit rules", "(default is true)") do |match_shorthand| + @match_shorthand = match_shorthand end - opts.on("-V", "--version", "Show version") do |v| - puts opts.ver - exit + opts.on("-j", "--[no-]json", "Output results in JSON") do |j| + @json = j end opts.on("--[no-]compass", "Enable compass extensions when parsing sass/scss (default is false)") do |compass| @@ -108,18 +103,23 @@ def parse(argv) load file end - opts.on("--[no-]match-shorthand", "Expands shorthand rules and matches on explicit rules (default is true)") do |match_shorthand| - @match_shorthand = match_shorthand + opts.on("--ignore-properties property1,property2,...", Array, "Ignore these properties when finding matches") do |ignored_properties| + @ignored_properties = ignored_properties end - opts.on("-j", "--[no-]json", "Output results in JSON") do |j| - @json = j + opts.on('--ignore-selectors "selector1","selector2",...', Array, "Ignore these selectors when finding matches") do |ignored_selectors| + @ignored_selectors = ignored_selectors end opts.on("--show-parser-errors", "Print verbose parser errors") do |show_parser_errors| @show_parser_errors = show_parser_errors end + opts.on("-V", "--version", "Show version") do |v| + puts opts.ver + exit + end + opts.on_tail("-h", "--help", "Show this message") do print_help(opts) end From ff861351de959fde31290a28ee2e8f9320748740 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 13:30:59 -0400 Subject: [PATCH 42/89] Cleans up some require/abort lines --- lib/csscss/cli.rb | 13 +++---------- 1 file changed, 3 insertions(+), 10 deletions(-) diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 3b9a0d6..498c5c1 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -141,15 +141,13 @@ def deprecate(message) end def enable_compass(config = nil) - require "compass" + abort 'Must install the "compass" gem before enabling its extensions' unless gem_installed?("compass") if config Compass.add_configuration(config) else Compass.add_configuration("config.rb") if File.exist?("config.rb") end - rescue LoadError - abort "Must install compass gem before enabling its extensions" end def windows_1_9 @@ -166,9 +164,7 @@ def gem_installed?(gem_name) end def load_sass_file(filename) - if !gem_installed?("sass") then - abort 'Must install the "sass" gem before parsing sass/scss files' - end + abort 'Must install the "sass" gem before parsing sass/scss files' unless gem_installed?("sass") sass_options = {cache:false} sass_options[:load_paths] = Compass.configuration.sass_load_paths if @compass @@ -185,10 +181,7 @@ def load_sass_file(filename) end def load_less_file(filename) - if !gem_installed?("less") then - abort 'Must install the "less" gem before parsing less files' - end - + abort 'Must install the "less" gem before parsing less files' unless gem_installed?("less") contents = load_css_file(filename) Less::Parser.new.parse(contents).to_css end From e2c2b6551d3b6308ef3034f10043fe3775819266 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 15:00:54 -0400 Subject: [PATCH 43/89] Adds an experimental flag to ignore sass mixin declarations Users can now do this with --ignore-sass-mixins. This is a heavily requested feature. Some users don't care about duplication coming from sass mixins. So this will inject a special comment before/after the properties from the mixin and the parser will ignore it. This will mess with reporting selector line numbers if I implement that in the future. I'm not sold on this being the default yet. refs: #25, #59 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 14 ++++++- lib/csscss/parser/css.rb | 21 +++++++++- lib/csscss/sass_include_extensions.rb | 19 +++++++++ test/csscss/parser/css_test.rb | 22 ++++++++++ test/csscss/sass_include_extensions_test.rb | 45 +++++++++++++++++++++ 6 files changed, 120 insertions(+), 2 deletions(-) create mode 100644 lib/csscss/sass_include_extensions.rb create mode 100644 test/csscss/sass_include_extensions_test.rb diff --git a/CHANGELOG.md b/CHANGELOG.md index d335573..966173d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,7 @@ * Adds --require switch for user configuration * Deprecates --compass-with-config config.rb in favor of --compass --require config.rb * Ignores @import statements. Users will need to run csscss on those directly +* Adds --ignore-sass-mixins which won't match declarations coming from sass mixins ## 1.2.0 - 4/14/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 498c5c1..ae2469c 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -9,6 +9,7 @@ def initialize(argv) @ignored_properties = [] @ignored_selectors = [] @match_shorthand = true + @ignore_sass_mixins = false end def run @@ -87,6 +88,12 @@ def parse(argv) @json = j end + opts.on("--ignore-sass-mixins", "EXPERIMENTAL: Ignore matches that come from including sass/scss mixins", + "This is an experimental feature and may not be included in future releases", + "(default is false)") do |ignore| + @ignore_sass_mixins = ignore + end + opts.on("--[no-]compass", "Enable compass extensions when parsing sass/scss (default is false)") do |compass| enable_compass if @compass = compass end @@ -169,7 +176,12 @@ def load_sass_file(filename) sass_options = {cache:false} sass_options[:load_paths] = Compass.configuration.sass_load_paths if @compass begin - Sass::Engine.for_file(filename, sass_options).render + tree = Sass::Engine.for_file(filename, sass_options).to_tree + if @ignore_sass_mixins + require "csscss/sass_include_extensions" + Csscss::SassMixinVisitor.visit(tree) + end + tree.render rescue Sass::SyntaxError => e if e.message =~ /compass/ && !@compass puts "Enable --compass option to use compass's extensions" diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index 49d9dd2..c056519 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -36,12 +36,30 @@ class Parser < Parslet::Parser space? } + rule(:mixin_attributes) { + ( + str('/* CSSCSS START MIXIN') >> + (str('*/').absent? >> any).repeat >> + str('*/') >> + (str('/* CSSCSS END MIXIN').absent? >> any).repeat >> + str('/* CSSCSS END MIXIN') >> + (str('*/').absent? >> any).repeat >> + str('*/') >> + space? + ).as(:mixin) + } + rule(:ruleset) { ( match["^{}"].repeat(1).as(:selector) >> str("{") >> space? >> - (comment | attribute | blank_attribute).repeat(0).as(:properties) >> + ( + mixin_attributes | + comment | + attribute | + blank_attribute + ).repeat(0).as(:properties) >> str("}") >> space? ).as(:ruleset) @@ -85,6 +103,7 @@ class Transformer < Parslet::Transform } rule(import: simple(:import)) { [] } + rule(mixin: simple(:mixin)) { nil } rule(comment: simple(:comment)) { nil } diff --git a/lib/csscss/sass_include_extensions.rb b/lib/csscss/sass_include_extensions.rb new file mode 100644 index 0000000..681af5c --- /dev/null +++ b/lib/csscss/sass_include_extensions.rb @@ -0,0 +1,19 @@ +require "sass" + +module Csscss + class SassMixinVisitor < Sass::Tree::Visitors::Base + def self.visit(root) + new.send(:visit, root) + end + + def visit_mixindef(node) + begin_comment = Sass::Tree::CommentNode.new(["/* CSSCSS START MIXIN: #{node.name} */"], :normal) + end_comment = Sass::Tree::CommentNode.new(["/* CSSCSS END MIXIN: #{node.name} */"], :normal) + + begin_comment.options = end_comment.options = {} + + node.children.unshift(begin_comment) + node.children.push(end_comment) + end + end +end diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index 57dbe43..651b7f0 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -156,6 +156,28 @@ module Css ]) end + it "ignores mixin selectors" do + css = %$ + h1 { + /* CSSCSS START MIXIN: foo */ + font-family: serif; + font-size: 10px; + display: block; + /* CSSCSS END MIXIN: foo */ + + /* CSSCSS START MIXIN: bar */ + outline: 1px; + /* CSSCSS END MIXIN: bar */ + + float: left; + } + $ + + trans(css).must_equal([ + rs(sel("h1"), [dec("float", "left")]) + ]) + end + it "parses attributes with encoded data that include semicolons" do trans(%$ .foo1 { diff --git a/test/csscss/sass_include_extensions_test.rb b/test/csscss/sass_include_extensions_test.rb new file mode 100644 index 0000000..4a4c9d3 --- /dev/null +++ b/test/csscss/sass_include_extensions_test.rb @@ -0,0 +1,45 @@ +require "test_helper" +require "csscss/sass_include_extensions" + +module Csscss + describe "sass import extensions" do + it "should do something" do + scss =<<-SCSS + @mixin foo { + font: { + family: serif; + size: 10px; + } + + display: block; + } + + @mixin bar { + outline: 1px; + } + + h1 { + @include foo; + @include bar; + } + SCSS + + + css =<<-CSS +h1 { + /* CSSCSS START MIXIN: foo */ + font-family: serif; + font-size: 10px; + display: block; + /* CSSCSS END MIXIN: foo */ + /* CSSCSS START MIXIN: bar */ + outline: 1px; + /* CSSCSS END MIXIN: bar */ } + CSS + + tree = Sass::Engine.new(scss, syntax: :scss).to_tree + Csscss::SassMixinVisitor.visit(tree) + tree.render.must_equal(css) + end + end +end From 2c2e3fd9d32c8207bbf5e215b5ef4b9c03265e73 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 15:12:50 -0400 Subject: [PATCH 44/89] Bumping version for 1.3.0 release --- CHANGELOG.md | 2 +- Gemfile.lock | 2 +- lib/csscss/version.rb | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 966173d..240a484 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,4 @@ -## (Unreleased) ## +## 1.3.0 - 4/20/2013 ## * Adds --require switch for user configuration * Deprecates --compass-with-config config.rb in favor of --compass --require config.rb diff --git a/Gemfile.lock b/Gemfile.lock index 742d2f9..cc2ad82 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - csscss (1.2.0) + csscss (1.3.0) colorize parslet (~> 1.5) diff --git a/lib/csscss/version.rb b/lib/csscss/version.rb index b6411dc..ba349a0 100644 --- a/lib/csscss/version.rb +++ b/lib/csscss/version.rb @@ -1,3 +1,3 @@ module Csscss - VERSION = "1.2.0" + VERSION = "1.3.0" end From 654e9501ab770bb0a18cecc58ee00eedcbf079ca Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 15:16:49 -0400 Subject: [PATCH 45/89] Updates README with --ignore-sass-mixins info --- README.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 217d55b..8966e58 100644 --- a/README.md +++ b/README.md @@ -45,11 +45,14 @@ rulesets that have fewer matches. $ csscss -n 10 -v path/to/style.css # ignores rulesets with < 10 matches -If you prefer writing in [sass](http://sass-lang.com/), you can also parse your sass/scss files. +If you prefer writing in [Sass](http://sass-lang.com/), you can also parse your sass/scss files. $ gem install sass $ csscss path/to/style.scss +Sass users may be interested in the `--ignore-sass-mixins` +experimental flag that won't match duplicate declarations from including mixins. + If you prefer writing in [LESS](http://lesscss.org/), you can also parse your LESS files. $ gem install less From f455293bbe40407ac29ef7a02b5c25a3110c9490 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 15:40:52 -0400 Subject: [PATCH 46/89] No need for such a long example --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 8966e58..b229466 100644 --- a/README.md +++ b/README.md @@ -29,7 +29,7 @@ Then you can run it in at the command line against CSS files. {.contact .content .primary} and {article, #comments} share 5 rules {.profile-picture}, {.screenshot img} and {a.blurb img} share 4 rules - {.work h2:first-child, .archive h2:first-child, .missing h2:first-child, .about h2, .contact h2} and {body.home h2} share 4 rules + {.work h2:first-child, .contact h2} and {body.home h2} share 4 rules {article.blurb:hover} and {article:hover} share 3 rules Run it in a verbose mode to see all the duplicated styles. From 17c8c68564c530e8aeeebebe1e60a2c7dbe34aa5 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 21:19:31 -0400 Subject: [PATCH 47/89] whoops --- test/csscss/sass_include_extensions_test.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/csscss/sass_include_extensions_test.rb b/test/csscss/sass_include_extensions_test.rb index 4a4c9d3..c8e902c 100644 --- a/test/csscss/sass_include_extensions_test.rb +++ b/test/csscss/sass_include_extensions_test.rb @@ -3,7 +3,7 @@ module Csscss describe "sass import extensions" do - it "should do something" do + it "should add comments before and after mixin properties" do scss =<<-SCSS @mixin foo { font: { From d8e5da3defba41be92253e92ecc744218705e03b Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 23:04:07 -0400 Subject: [PATCH 48/89] Fixes bug where --ignore-sass-mixins isn't respected in @imports There is a `@children.empty?` edgecase that I can't recreate in the tests but I'm seeing on a private codebase. It would be nice to red/green test that bit of the conditional. refs: #62 --- CHANGELOG.md | 4 +++ lib/csscss/cli.rb | 8 ++---- lib/csscss/sass_include_extensions.rb | 23 ++++++++-------- test/csscss/sass_include_extensions_test.rb | 29 ++++++++++++++++++--- 4 files changed, 44 insertions(+), 20 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 240a484..807d708 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## 1.3.1 - 4/20/2013 ## + +* Fixes --ignore-sass-mixins bug with @importing + ## 1.3.0 - 4/20/2013 ## * Adds --require switch for user configuration diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index ae2469c..9ca13fa 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -172,16 +172,12 @@ def gem_installed?(gem_name) def load_sass_file(filename) abort 'Must install the "sass" gem before parsing sass/scss files' unless gem_installed?("sass") + require "csscss/sass_include_extensions" if @ignore_sass_mixins sass_options = {cache:false} sass_options[:load_paths] = Compass.configuration.sass_load_paths if @compass begin - tree = Sass::Engine.for_file(filename, sass_options).to_tree - if @ignore_sass_mixins - require "csscss/sass_include_extensions" - Csscss::SassMixinVisitor.visit(tree) - end - tree.render + Sass::Engine.for_file(filename, sass_options).render rescue Sass::SyntaxError => e if e.message =~ /compass/ && !@compass puts "Enable --compass option to use compass's extensions" diff --git a/lib/csscss/sass_include_extensions.rb b/lib/csscss/sass_include_extensions.rb index 681af5c..5b4360c 100644 --- a/lib/csscss/sass_include_extensions.rb +++ b/lib/csscss/sass_include_extensions.rb @@ -1,19 +1,20 @@ require "sass" -module Csscss - class SassMixinVisitor < Sass::Tree::Visitors::Base - def self.visit(root) - new.send(:visit, root) - end +Sass::Tree::MixinDefNode.class_eval do + def children + first_child = @children.first - def visit_mixindef(node) - begin_comment = Sass::Tree::CommentNode.new(["/* CSSCSS START MIXIN: #{node.name} */"], :normal) - end_comment = Sass::Tree::CommentNode.new(["/* CSSCSS END MIXIN: #{node.name} */"], :normal) + # not sure why/how we can get here with empty children, but it + # causes issues + unless @children.empty? || (first_child.is_a?(Sass::Tree::CommentNode) && first_child.value.first =~ /CSSCSS START/) + begin_comment = Sass::Tree::CommentNode.new(["/* CSSCSS START MIXIN: #{name} */"], :normal) + end_comment = Sass::Tree::CommentNode.new(["/* CSSCSS END MIXIN: #{name} */"], :normal) begin_comment.options = end_comment.options = {} - - node.children.unshift(begin_comment) - node.children.push(end_comment) + @children.unshift(begin_comment) + @children.push(end_comment) end + + @children end end diff --git a/test/csscss/sass_include_extensions_test.rb b/test/csscss/sass_include_extensions_test.rb index c8e902c..76ace2e 100644 --- a/test/csscss/sass_include_extensions_test.rb +++ b/test/csscss/sass_include_extensions_test.rb @@ -1,4 +1,5 @@ require "test_helper" +require "tempfile" require "csscss/sass_include_extensions" module Csscss @@ -37,9 +38,31 @@ module Csscss /* CSSCSS END MIXIN: bar */ } CSS - tree = Sass::Engine.new(scss, syntax: :scss).to_tree - Csscss::SassMixinVisitor.visit(tree) - tree.render.must_equal(css) + Sass::Engine.new(scss, syntax: :scss, cache: false).render.must_equal(css) + end + + it "should insert comments even with imported stylesheets" do + Tempfile.open(['foo', '.scss']) do |f| + f << <<-SCSS + @mixin foo { + outline: 1px; + } + + h1 { + @include foo; + } + SCSS + f.close + + css =<<-CSS +h1 { + /* CSSCSS START MIXIN: foo */ + outline: 1px; + /* CSSCSS END MIXIN: foo */ } + CSS + + Sass::Engine.new("@import '#{f.path}'", syntax: :scss, cache: false).render.must_equal(css) + end end end end From 787fb7b8601ea6fd16abd7e37d210a10c45e66ea Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 20 Apr 2013 23:06:23 -0400 Subject: [PATCH 49/89] Bumping version to 1.3.1 --- Gemfile.lock | 2 +- lib/csscss/version.rb | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Gemfile.lock b/Gemfile.lock index cc2ad82..8a089c2 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - csscss (1.3.0) + csscss (1.3.1) colorize parslet (~> 1.5) diff --git a/lib/csscss/version.rb b/lib/csscss/version.rb index ba349a0..b122c60 100644 --- a/lib/csscss/version.rb +++ b/lib/csscss/version.rb @@ -1,3 +1,3 @@ module Csscss - VERSION = "1.3.0" + VERSION = "1.3.1" end From 2f54e7909080fbfb45ee614e5d810cffc72d44c1 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 21 Apr 2013 00:01:39 -0400 Subject: [PATCH 50/89] Fixes attribute parsing bug where comments include braces Also refactored out the dynamic bit in favor of present?/absent? logic. Slowly getting the hang of those conditionals. refs: #29 --- CHANGELOG.md | 4 ++++ lib/csscss/parser/css.rb | 22 +++++++++------------- test/csscss/parser/css_test.rb | 10 ++++++---- 3 files changed, 19 insertions(+), 17 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 807d708..08b367d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## (Unreleased) ## + +* Fixes attribute parsing bug that includes comments with braces + ## 1.3.1 - 4/20/2013 ## * Fixes --ignore-sass-mixins bug with @importing diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index c056519..7a954c7 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -12,26 +12,22 @@ def parse(source) class Parser < Parslet::Parser include Common - rule(:comment) { - (space? >> str('/*') >> (str('*/').absent? >> any).repeat >> str('*/') >> space?).as(:comment) - } - - rule(:css_space?) { - comment.repeat(1) | space? + rule(:raw_comment) { + space? >> str('/*') >> (str('*/').absent? >> any).repeat >> str('*/') >> space? } + rule(:comment) { raw_comment.as(:comment) } rule(:blank_attribute) { str(";") >> space? } + rule(:attribute_value) { (str('/*').absent? >> match["^;}"]) | raw_comment } + rule(:attribute) { match["^:{}"].repeat(1).as(:property) >> str(":") >> - (match["^;}"].repeat(1).capture(:stuff) >> dynamic {|source, context| - if context.captures[:stuff].to_s =~ /data:/ - str(";") >> match["^;}"].repeat(1) - else - any.present? - end - }).as(:value) >> + ( + (stri("data:").absent? >> attribute_value) | + (stri("data:").present? >> attribute_value.repeat(1) >> str(";") >> attribute_value.repeat(1)) + ).repeat(1).as(:value) >> str(";").maybe >> space? } diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index 651b7f0..ad0c45b 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -23,14 +23,14 @@ module Css end it "parses comments" do - @parser.css_space?.must_parse "/* foo */" - @parser.css_space?.must_parse %$ + @parser.comment.must_parse "/* foo */" + @parser.comment.must_parse %$ /* foo * bar */ $ - @parser.css_space?.must_parse %$ + @parser.comment.repeat(1).must_parse %$ /* foo */ /* bar */ $ @@ -63,11 +63,13 @@ module Css */ .bar { border: 1px solid black /* sdflk */ } .baz { background: white /* sdflk */ } + .baz2 { background: white /* {sdflk} */ } $ trans(css).must_equal([ rs(sel(".bar"), [dec("border", "1px solid black /* sdflk */")]), - rs(sel(".baz"), [dec("background", "white /* sdflk */")]) + rs(sel(".baz"), [dec("background", "white /* sdflk */")]), + rs(sel(".baz2"), [dec("background", "white /* {sdflk} */")]) ]) end From 90bca96cd982666116007c81eee87aa786777ed5 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 27 Apr 2013 20:41:24 -0400 Subject: [PATCH 51/89] Adds ruby-version This is rvm and rbenv agnostic --- .ruby-version | 1 + 1 file changed, 1 insertion(+) create mode 100644 .ruby-version diff --git a/.ruby-version b/.ruby-version new file mode 100644 index 0000000..9a5700d --- /dev/null +++ b/.ruby-version @@ -0,0 +1 @@ +ruby-2.0.0-p0 From 1e3b3b7fecef96480e6437920c9c69aef29a2bec Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sun, 28 Apr 2013 09:11:08 -0400 Subject: [PATCH 52/89] Added blurb on why csscss doesn't remove duplications --- README.md | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/README.md b/README.md index b229466..e835212 100644 --- a/README.md +++ b/README.md @@ -63,6 +63,13 @@ LESS requires an additional javascript runtime. rubies, and [therubyrhino](https://rubygems.org/gems/therubyrhino) on jruby. +## Why doesn't csscss automatically remove duplications for me? ## + +I have been asked this a lot, but csscss is intentionally designed this +way. Check out [this +post](http://connectionrequired.com/blog/2013/04/why-csscss-doesnt-remove-duplication-for-you/) +for my reasoning. + ## I found bugs ## This is still a new and evolving project. I heartily welcome feedback. From c3e18363d73c2467e72b258f0ec1e615b6d1c4bd Mon Sep 17 00:00:00 2001 From: Carson McDonald Date: Fri, 3 May 2013 06:39:54 -0400 Subject: [PATCH 53/89] Add tests for empty nested rulesets. --- test/csscss/parser/css_test.rb | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index ad0c45b..f8838db 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -131,6 +131,27 @@ module Css ]) end + it "recognizes empty @media queries with no spaces" do + css = %$ + @media (min-width: 768px) and (max-width: 979px) {} + $ + + trans(css).must_equal([ + rs(sel("@media (min-width: 768px) and (max-width: 979px)"), []), + ]) + end + + it "recognizes empty @media queries with spaces" do + css = %$ + @media (min-width: 768px) and (max-width: 979px) { + } + $ + + trans(css).must_equal([ + rs(sel("@media (min-width: 768px) and (max-width: 979px)"), []), + ]) + end + it "ignores @import statements" do css = %$ @import "foo.css"; From f5c5d3b78e1c7625beeb559a7af404d68c7701bb Mon Sep 17 00:00:00 2001 From: Carson McDonald Date: Fri, 3 May 2013 06:40:53 -0400 Subject: [PATCH 54/89] Require at least one child ruleset. --- lib/csscss/parser/css.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index 7a954c7..cb799a2 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -66,7 +66,7 @@ class Parser < Parslet::Parser str("@") >> match["^{}"].repeat(1) >> str("{") >> - (comment | ruleset).repeat(0) >> + (comment | ruleset).repeat(1) >> str("}") >> space? ).as(:nested_ruleset) From d760bff29ec4229b797417171b5fa7430f109108 Mon Sep 17 00:00:00 2001 From: Paul Simpson Date: Fri, 3 May 2013 22:42:01 -0700 Subject: [PATCH 55/89] Added contribution guidelines --- CONTRIBUTING.md | 39 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 39 insertions(+) create mode 100644 CONTRIBUTING.md diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 0000000..f43e190 --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,39 @@ +# Contributing to csscss + +First of all: thanks! + +The main way to contribute to csscss is to write some code! Here's how: + +1. Fork csscss +2. Create a topic branch - `git checkout -b my_branch` +3. Push to your branch - `git push origin my_branch` +4. Create a [Pull Request](http://help.github.com/pull-requests/) from your + branch +5. That's it! + +If you're not doing some sort of refactoring, a CHANGELOG entry is appropriate. +Please include them in pull requests adding features or fixing bugs. + +## Tests + +csscss uses minitest for testing. + +A simple `bundle exec rake` will run all the tests. Make sure they pass when +you submit a pull request. + +Please include tests with your pull request. + +## Bugs & Feature Requests + +You can file bugs on the [issues +tracker](https://github.com/zmoazeni/csscss/issues), and tag them with 'bug'. Feel free to discuss features there, too. + +### Good report structure + +Please include the following four things in your report: + +1. What you did. +2. What you expected to happen. +3. What happened instead. + +The more information the better. From e2a75c6776ae5c73cffe81ecac47f26542b0b60d Mon Sep 17 00:00:00 2001 From: JoseLuis Torres Date: Tue, 14 May 2013 22:44:04 -0500 Subject: [PATCH 56/89] adding the validation for single special character in attribute #70 --- lib/csscss/parser/css.rb | 4 ++-- test/csscss/parser/common_test.rb | 6 ++++++ test/csscss/parser/css_test.rb | 33 +++++++++++++++++++++++++++++++ 3 files changed, 41 insertions(+), 2 deletions(-) diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index 7a954c7..986d8f3 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -19,14 +19,14 @@ class Parser < Parslet::Parser rule(:blank_attribute) { str(";") >> space? } - rule(:attribute_value) { (str('/*').absent? >> match["^;}"]) | raw_comment } + rule(:attribute_value) { (str('"') >> any >> str('"')) | (str('/*').absent? >> match["^;}"]) | raw_comment } rule(:attribute) { match["^:{}"].repeat(1).as(:property) >> str(":") >> ( (stri("data:").absent? >> attribute_value) | - (stri("data:").present? >> attribute_value.repeat(1) >> str(";") >> attribute_value.repeat(1)) + (stri("data:").present? >> attribute_value.repeat(1) >> str(";") >> attribute_value.repeat(1)) ).repeat(1).as(:value) >> str(";").maybe >> space? diff --git a/test/csscss/parser/common_test.rb b/test/csscss/parser/common_test.rb index 41c4b92..43c0f15 100644 --- a/test/csscss/parser/common_test.rb +++ b/test/csscss/parser/common_test.rb @@ -139,6 +139,12 @@ class CommonTest @parser.url.must_parse "url(data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==)" @parser.url.must_parse "url('data:image/svg+xml;base64,IMGDATAGOESHERE4/5/h/1+==')" end + + it "parses specials characters" do + @parser.between('"', '"') { @parser.symbol("{") }.must_parse '"{"' + @parser.between('"', '"') { @parser.symbol("}") }.must_parse '"}"' + @parser.between('"', '"') { @parser.symbol("%") }.must_parse '"%"' + end end end end diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index ad0c45b..bf0dd7e 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -212,6 +212,39 @@ module Css dec("display", "block")]) ]) end + + it "parses attributes with special characters" do + css = %$ + + #menu a::before { + content: "{"; + left: -6px; + } + + #menu a::after { + content: "}"; + right: -6px; + } + + #menu a::weird { + content: "@"; + up: -2px; + } + + $ + + trans(css).must_equal([ + rs(sel("#menu a::before"), [dec("content", '"{"'), + dec("left", "-6px") + ]), + rs(sel("#menu a::after"), [dec("content", '"}"'), + dec("right", "-6px") + ]), + rs(sel("#menu a::weird"), [dec("content", '"@"'), + dec("up", "-2px") + ]) + ]) + end end end end From 6370bfe5ae0bc5df8028e41c3412527a97b5f07d Mon Sep 17 00:00:00 2001 From: JoseLuis Torres Date: Wed, 15 May 2013 21:21:04 -0500 Subject: [PATCH 57/89] adding the any quoted to the fix #70 --- lib/csscss/parser/css.rb | 2 +- test/csscss/parser/common_test.rb | 2 ++ test/csscss/parser/css_test.rb | 8 ++++++++ 3 files changed, 11 insertions(+), 1 deletion(-) diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index 986d8f3..245241e 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -19,7 +19,7 @@ class Parser < Parslet::Parser rule(:blank_attribute) { str(";") >> space? } - rule(:attribute_value) { (str('"') >> any >> str('"')) | (str('/*').absent? >> match["^;}"]) | raw_comment } + rule(:attribute_value) { (any_quoted {any}) | (str('/*').absent? >> match["^;}"]) | raw_comment } rule(:attribute) { match["^:{}"].repeat(1).as(:property) >> diff --git a/test/csscss/parser/common_test.rb b/test/csscss/parser/common_test.rb index 43c0f15..c803bce 100644 --- a/test/csscss/parser/common_test.rb +++ b/test/csscss/parser/common_test.rb @@ -144,6 +144,8 @@ class CommonTest @parser.between('"', '"') { @parser.symbol("{") }.must_parse '"{"' @parser.between('"', '"') { @parser.symbol("}") }.must_parse '"}"' @parser.between('"', '"') { @parser.symbol("%") }.must_parse '"%"' + @parser.double_quoted { @parser.symbol("{") }.must_parse %("{") + @parser.single_quoted { @parser.symbol('{') }.must_parse %('{') end end end diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index bf0dd7e..3c1f7df 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -231,6 +231,11 @@ module Css up: -2px; } + #menu a::after_all { + content: '{'; + right: -6px; + } + $ trans(css).must_equal([ @@ -242,6 +247,9 @@ module Css ]), rs(sel("#menu a::weird"), [dec("content", '"@"'), dec("up", "-2px") + ]), + rs(sel("#menu a::after_all"), [dec("content", "'{'"), + dec("right", "-6px") ]) ]) end From 8b68d5e263bdec85670dde0d277642898a820010 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 16:32:33 -0400 Subject: [PATCH 58/89] Adds a CHANGELOG entry for Carson's change refs: #67 --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 08b367d..3db20bf 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,7 @@ ## (Unreleased) ## * Fixes attribute parsing bug that includes comments with braces +* Fixes parsing bug with empty media selectors ## 1.3.1 - 4/20/2013 ## From 90f875d27621ef0110bb2601b295d13e6eb00cbd Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 16:44:19 -0400 Subject: [PATCH 59/89] Removes unnecessary parens and whitespace --- lib/csscss/parser/css.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index a30a307..947995c 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -19,14 +19,14 @@ class Parser < Parslet::Parser rule(:blank_attribute) { str(";") >> space? } - rule(:attribute_value) { (any_quoted {any}) | (str('/*').absent? >> match["^;}"]) | raw_comment } + rule(:attribute_value) { any_quoted { any } | (str('/*').absent? >> match["^;}"]) | raw_comment } rule(:attribute) { match["^:{}"].repeat(1).as(:property) >> str(":") >> ( (stri("data:").absent? >> attribute_value) | - (stri("data:").present? >> attribute_value.repeat(1) >> str(";") >> attribute_value.repeat(1)) + (stri("data:").present? >> attribute_value.repeat(1) >> str(";") >> attribute_value.repeat(1)) ).repeat(1).as(:value) >> str(";").maybe >> space? From 9962f1d877e02e519ab15068274aaf2e0d234804 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 16:46:31 -0400 Subject: [PATCH 60/89] Adds CHANGELOG entry for Jose's bug fix and lists him in CONTRIBUTORS --- CHANGELOG.md | 3 ++- CONTRIBUTORS.md | 1 + 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 3db20bf..ceda421 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,7 +1,8 @@ ## (Unreleased) ## * Fixes attribute parsing bug that includes comments with braces -* Fixes parsing bug with empty media selectors +* Fixes parsing bug with empty media selectors #67 +* Fixes parsing bug with quoted brackets #72 ## 1.3.1 - 4/20/2013 ## diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md index 492bdb3..d190464 100644 --- a/CONTRIBUTORS.md +++ b/CONTRIBUTORS.md @@ -4,3 +4,4 @@ * Ivan Lazarevic @kopipejst * Matt DuVall @mduvall twitter:@mduvall_ * Mekka Okereke @mekka @mekkaokereke +* JoseLuis Torres @joseluistorres twitter:@joseluis_torres From 7e7e9fd64659819c040636a31f87ac825d02f5c2 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 16:47:16 -0400 Subject: [PATCH 61/89] Bump ruby version to latest v2 --- .ruby-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.ruby-version b/.ruby-version index 9a5700d..95a5ad2 100644 --- a/.ruby-version +++ b/.ruby-version @@ -1 +1 @@ -ruby-2.0.0-p0 +ruby-2.0.0-p195 From 23c53af07ec2db1275011c78fbf8e38ef83209e7 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 16:54:20 -0400 Subject: [PATCH 62/89] Upgrade debugger version This is failing in travisci, I assume it's because it's using an older version --- Gemfile.lock | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Gemfile.lock b/Gemfile.lock index 8a089c2..ee979b8 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -17,12 +17,12 @@ GEM chunky_png (~> 1.2) fssm (>= 0.2.7) sass (~> 3.1) - debugger (1.5.0) + debugger (1.6.0) columnize (>= 0.3.1) debugger-linecache (~> 1.2.0) - debugger-ruby_core_source (~> 1.2.0) + debugger-ruby_core_source (~> 1.2.1) debugger-linecache (1.2.0) - debugger-ruby_core_source (1.2.0) + debugger-ruby_core_source (1.2.2) fssm (0.2.10) less (2.3.1) commonjs (~> 0.2.6) From 78013bf3b725bd317a3e239b3c23c34588141a7b Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 17:28:07 -0400 Subject: [PATCH 63/89] Fixes a bug with nested media queries There was a double issue, one with spacing and apparently media queries can be nested. --- CHANGELOG.md | 1 + lib/csscss/parser/css.rb | 7 ++++--- test/csscss/parser/css_test.rb | 12 ++++++++++++ 3 files changed, 17 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index ceda421..9fff4f6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,6 +3,7 @@ * Fixes attribute parsing bug that includes comments with braces * Fixes parsing bug with empty media selectors #67 * Fixes parsing bug with quoted brackets #72 +* Fixes parsing bug with nested media queries #73 ## 1.3.1 - 4/20/2013 ## diff --git a/lib/csscss/parser/css.rb b/lib/csscss/parser/css.rb index 947995c..d0c6973 100644 --- a/lib/csscss/parser/css.rb +++ b/lib/csscss/parser/css.rb @@ -66,7 +66,8 @@ class Parser < Parslet::Parser str("@") >> match["^{}"].repeat(1) >> str("{") >> - (comment | ruleset).repeat(1) >> + space? >> + (comment | ruleset | nested_ruleset).repeat(1) >> str("}") >> space? ).as(:nested_ruleset) @@ -94,8 +95,8 @@ class Parser < Parslet::Parser end class Transformer < Parslet::Transform - rule(nested_ruleset: sequence(:rulesets)) { - rulesets + rule(nested_ruleset: subtree(:rulesets)) { |context| + context[:rulesets].flatten } rule(import: simple(:import)) { [] } diff --git a/test/csscss/parser/css_test.rb b/test/csscss/parser/css_test.rb index 72d3133..68e25d1 100644 --- a/test/csscss/parser/css_test.rb +++ b/test/csscss/parser/css_test.rb @@ -119,6 +119,15 @@ module Css } } + @media only screen { + @-webkit-keyframes webkitSiblingBugfix { + from { position: relative; } + to { position: relative; } + } + + a { position: relative } + } + h1 { outline: 1px; } @@ -127,6 +136,9 @@ module Css trans(css).must_equal([ rs(sel("#foo"), [dec("background-color", "black")]), rs(sel("#bar"), [dec("display", "none")]), + rs(sel("from"), [dec("position", "relative")]), + rs(sel("to"), [dec("position", "relative")]), + rs(sel("a"), [dec("position", "relative")]), rs(sel("h1"), [dec("outline", "1px")]) ]) end From 0609a87356daa0ffd935b3eb780b33172576d578 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 17:35:26 -0400 Subject: [PATCH 64/89] Removes --compass-with-config deprecation The config file that is passed in needs to run in the Compass context, so it's not just a normal ruby load/require. (Sorta) fixes #63 --- CHANGELOG.md | 1 + lib/csscss/cli.rb | 5 +---- 2 files changed, 2 insertions(+), 4 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 9fff4f6..816d938 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,7 @@ * Fixes parsing bug with empty media selectors #67 * Fixes parsing bug with quoted brackets #72 * Fixes parsing bug with nested media queries #73 +* Removes --compass-with-config deprecation ## 1.3.1 - 4/20/2013 ## diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 9ca13fa..0adec9e 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -98,10 +98,7 @@ def parse(argv) enable_compass if @compass = compass end - opts.on("--compass-with-config config", "Enable compass extensions when parsing sass/scss and pass config file", - "DEPRECATED: use --compass --require path/to/config.rb instead." - ) do |config| - deprecate("Use --compass --require #{config} instead of --compass-with-config #{config}") + opts.on("--compass-with-config config", "Enable compass extensions when parsing sass/scss and pass config file") do |config| @compass = true enable_compass(config) end From beb449eee16b108b8e5ca739c390cc054b11da4b Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 17:47:46 -0400 Subject: [PATCH 65/89] Expanding Paul's original contributing doc --- CHANGELOG.md | 1 + CONTRIBUTING.md | 68 +++++++++++++++++++++++++++++-------------------- CONTRIBUTORS.md | 1 + 3 files changed, 43 insertions(+), 27 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 816d938..abef3ca 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ * Fixes parsing bug with quoted brackets #72 * Fixes parsing bug with nested media queries #73 * Removes --compass-with-config deprecation +* Adds a CONTRIBUTING.md file with instructions ## 1.3.1 - 4/20/2013 ## diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index f43e190..fc1d02f 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -1,39 +1,53 @@ # Contributing to csscss -First of all: thanks! - -The main way to contribute to csscss is to write some code! Here's how: - -1. Fork csscss -2. Create a topic branch - `git checkout -b my_branch` -3. Push to your branch - `git push origin my_branch` -4. Create a [Pull Request](http://help.github.com/pull-requests/) from your - branch -5. That's it! - -If you're not doing some sort of refactoring, a CHANGELOG entry is appropriate. -Please include them in pull requests adding features or fixing bugs. - -## Tests - -csscss uses minitest for testing. - -A simple `bundle exec rake` will run all the tests. Make sure they pass when -you submit a pull request. - -Please include tests with your pull request. +First of all: Thanks! ## Bugs & Feature Requests You can file bugs on the [issues -tracker](https://github.com/zmoazeni/csscss/issues), and tag them with 'bug'. Feel free to discuss features there, too. +tracker](https://github.com/zmoazeni/csscss/issues), and tag them with +'bug'. Feel free to discuss features there, too. -### Good report structure +## Good report structure Please include the following four things in your report: -1. What you did. -2. What you expected to happen. -3. What happened instead. +1. The smallest CSS snippet to explain the problem. +2. What you did. +3. What you expected to happen. +4. What happened instead. The more information the better. + +## Contributing Code + +It's easy to contribute code to csscss: + +1. Fork csscss. +2. Create a topic branch - `git checkout -b my_branch` +3. Push to your branch - `git push origin my_branch` +4. Make sure the code follows the contributing guidelines below. +5. Create a [Pull Request](http://help.github.com/pull-requests/) from your + branch. +6. That's it! + +## First Time OSS Contributors + +Submitting your first pull request can be a little daunting. If this is +your first Open Source contribution, please mention it in your pull +request and I'll help guide you through the process. + +## Contributing Guidelines + +* Make sure your code follows typical [ruby +conventions](https://github.com/bbatsov/ruby-style-guide). +* Make sure the test suite is green. A simple `bundle exec rake test` +will run all the tests. +* Include a CHANGELOG entry with your change. Add an `(Unreleased)` +section at the top if one doesn't exist. +* Try to keep the git commits squashed and concise. Keep tests and code +changes together in the same commit. Keep only logical changes together +in a single commit. +* I strongly encourage [well written git commit +messages](http://tbaggery.com/2008/04/19/a-note-about-git-commit-messages.html). +* Make sure all whitespace is trimmed from the end of lines. diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md index d190464..30a5a63 100644 --- a/CONTRIBUTORS.md +++ b/CONTRIBUTORS.md @@ -5,3 +5,4 @@ * Matt DuVall @mduvall twitter:@mduvall_ * Mekka Okereke @mekka @mekkaokereke * JoseLuis Torres @joseluistorres twitter:@joseluis_torres +* Paul Simpson @prsimp From 5efdb3b00690c6d99285948274326674ae6a2417 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 17:50:48 -0400 Subject: [PATCH 66/89] Bumping version to v1.3.2 and updating the CHANGELOG --- CHANGELOG.md | 2 +- lib/csscss/version.rb | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index abef3ca..36f85cf 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,4 @@ -## (Unreleased) ## +## 1.3.2 - 6/22/2013 ## * Fixes attribute parsing bug that includes comments with braces * Fixes parsing bug with empty media selectors #67 diff --git a/lib/csscss/version.rb b/lib/csscss/version.rb index b122c60..aec9959 100644 --- a/lib/csscss/version.rb +++ b/lib/csscss/version.rb @@ -1,3 +1,3 @@ module Csscss - VERSION = "1.3.1" + VERSION = "1.3.2" end From 138c53002a46ad946a47b3eea9e723a3773ace87 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Sat, 22 Jun 2013 17:51:18 -0400 Subject: [PATCH 67/89] I'm never going to remember this bump --- Gemfile.lock | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Gemfile.lock b/Gemfile.lock index ee979b8..62004dd 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - csscss (1.3.1) + csscss (1.3.2) colorize parslet (~> 1.5) From cc640c678e5d0b31d91e59d955722a59e8a6b42a Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 15 Oct 2013 12:30:35 -0400 Subject: [PATCH 68/89] Adds section for extensions --- README.md | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/README.md b/README.md index e835212..b829e1c 100644 --- a/README.md +++ b/README.md @@ -63,6 +63,13 @@ LESS requires an additional javascript runtime. rubies, and [therubyrhino](https://rubygems.org/gems/therubyrhino) on jruby. +## Are there any community extensions? ## + +* [compass-csscss](https://github.com/Comcast/compass-csscss) integrates csscss with compass projects. +* [grunt-csscss](https://github.com/peterkeating/grunt-csscss) a [grunt](http://gruntjs.com/) task to automatically run csscss. + +_Please submit [an issue](https://github.com/zmoazeni/csscss/issues/new) if you know of any others._ + ## Why doesn't csscss automatically remove duplications for me? ## I have been asked this a lot, but csscss is intentionally designed this From 69118a8e6499ba1d60a8dfc8d15c78d03e6cf741 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 15 Oct 2013 12:33:05 -0400 Subject: [PATCH 69/89] Link to compass --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index b829e1c..4e51efb 100644 --- a/README.md +++ b/README.md @@ -65,7 +65,7 @@ jruby. ## Are there any community extensions? ## -* [compass-csscss](https://github.com/Comcast/compass-csscss) integrates csscss with compass projects. +* [compass-csscss](https://github.com/Comcast/compass-csscss) integrates csscss with [compass](http://compass-style.org/) projects. * [grunt-csscss](https://github.com/peterkeating/grunt-csscss) a [grunt](http://gruntjs.com/) task to automatically run csscss. _Please submit [an issue](https://github.com/zmoazeni/csscss/issues/new) if you know of any others._ From f34468d0eb19004f7ac423bdaa82fcc02ceadfe3 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:08:31 -0400 Subject: [PATCH 70/89] Use v2.1.2 for dev --- .ruby-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.ruby-version b/.ruby-version index 95a5ad2..ec6b00f 100644 --- a/.ruby-version +++ b/.ruby-version @@ -1 +1 @@ -ruby-2.0.0-p195 +ruby-2.1.2 From acd9093ad94fbfdc42596760a2813c6e4588f978 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:10:23 -0400 Subject: [PATCH 71/89] Dump debugger for byebug --- Gemfile | 20 ++++++++++---------- Gemfile.lock | 12 +++++------- test/just_parse.rb | 2 +- test/test_helper.rb | 12 ++++++------ 4 files changed, 22 insertions(+), 24 deletions(-) diff --git a/Gemfile b/Gemfile index 46e2ea9..f34d154 100644 --- a/Gemfile +++ b/Gemfile @@ -4,16 +4,16 @@ source 'https://rubygems.org' gemspec # optional runtime dependencies -gem "sass" -gem "compass" -gem "less" -gem "therubyracer", :platform => :mri +gem 'sass' +gem 'compass' +gem 'less' +gem 'therubyracer', :platform => :mri -gem "rake", :require => false -gem "debugger" +gem 'rake', :require => false +gem 'byebug' -gem "minitest" -gem "m" -gem "minitest-rg" +gem 'minitest' +gem 'm' +gem 'minitest-rg' -gem "ruby-prof" +gem 'ruby-prof' diff --git a/Gemfile.lock b/Gemfile.lock index 62004dd..a790aad 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -9,20 +9,18 @@ GEM remote: https://rubygems.org/ specs: blankslate (2.1.2.4) + byebug (3.1.2) + columnize (~> 0.8) + debugger-linecache (~> 1.2) chunky_png (1.2.7) colorize (0.5.8) - columnize (0.3.6) + columnize (0.8.9) commonjs (0.2.6) compass (0.12.2) chunky_png (~> 1.2) fssm (>= 0.2.7) sass (~> 3.1) - debugger (1.6.0) - columnize (>= 0.3.1) - debugger-linecache (~> 1.2.0) - debugger-ruby_core_source (~> 1.2.1) debugger-linecache (1.2.0) - debugger-ruby_core_source (1.2.2) fssm (0.2.10) less (2.3.1) commonjs (~> 0.2.6) @@ -47,9 +45,9 @@ PLATFORMS ruby DEPENDENCIES + byebug compass csscss! - debugger less m minitest diff --git a/test/just_parse.rb b/test/just_parse.rb index ef9f1f6..47c7249 100644 --- a/test/just_parse.rb +++ b/test/just_parse.rb @@ -1,6 +1,6 @@ #! /usr/bin/env ruby -require "debugger" +require "byebug" require "csscss" raise "need a file name" unless ARGV[0] diff --git a/test/test_helper.rb b/test/test_helper.rb index d0c7ea5..4679d7a 100644 --- a/test/test_helper.rb +++ b/test/test_helper.rb @@ -1,11 +1,11 @@ -require "rubygems" -require "bundler/setup" +require 'rubygems' +require 'bundler/setup' -require "minitest/autorun" -require "minitest/rg" -require "debugger" +require 'minitest/autorun' +require 'minitest/rg' +require 'byebug' -require "csscss" +require 'csscss' module TypeHelpers def sel(s) From e838aafa8aceb608bc48865363f7f94b49be4da8 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:18:28 -0400 Subject: [PATCH 72/89] Upgrade parslet to at least v1.6.1 It includes the optimization fixes so we don't need to monkey patch it anymore v1.6.1 and my optimization monkey patch do not play well with each other, so lets use at least v1.6.1 and dump it --- Gemfile.lock | 6 +-- csscss.gemspec | 2 +- lib/csscss.rb | 1 - lib/csscss/parslet_optimizations.rb | 77 ----------------------------- 4 files changed, 4 insertions(+), 82 deletions(-) delete mode 100644 lib/csscss/parslet_optimizations.rb diff --git a/Gemfile.lock b/Gemfile.lock index a790aad..9b33215 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -3,7 +3,7 @@ PATH specs: csscss (1.3.2) colorize - parslet (~> 1.5) + parslet (>= 1.6.1, < 2.0) GEM remote: https://rubygems.org/ @@ -13,7 +13,7 @@ GEM columnize (~> 0.8) debugger-linecache (~> 1.2) chunky_png (1.2.7) - colorize (0.5.8) + colorize (0.7.3) columnize (0.8.9) commonjs (0.2.6) compass (0.12.2) @@ -31,7 +31,7 @@ GEM method_source (0.8.1) minitest (2.12.1) minitest-rg (1.1.0) - parslet (1.5.0) + parslet (1.6.1) blankslate (~> 2.0) rake (10.0.3) ref (1.0.4) diff --git a/csscss.gemspec b/csscss.gemspec index 07a2f31..85304e8 100644 --- a/csscss.gemspec +++ b/csscss.gemspec @@ -19,6 +19,6 @@ Gem::Specification.new do |gem| gem.required_ruby_version = ">= 1.9" - gem.add_dependency "parslet", "~> 1.5" + gem.add_dependency "parslet", ">= 1.6.1", "< 2.0" gem.add_dependency "colorize" end diff --git a/lib/csscss.rb b/lib/csscss.rb index 29076ff..62f3d42 100644 --- a/lib/csscss.rb +++ b/lib/csscss.rb @@ -5,7 +5,6 @@ require "colorize" require "parslet" -require "csscss/parslet_optimizations" require "csscss/version" require "csscss/cli" diff --git a/lib/csscss/parslet_optimizations.rb b/lib/csscss/parslet_optimizations.rb deleted file mode 100644 index 32b7130..0000000 --- a/lib/csscss/parslet_optimizations.rb +++ /dev/null @@ -1,77 +0,0 @@ -# These are my multibyte optimizations for parslet. -# More information can be found: -# https://github.com/kschiess/parslet/issues/73 -# https://github.com/kschiess/parslet/pull/74 -# https://github.com/zmoazeni/parslet/tree/optimized-multibyte-parsing - -require 'strscan' -require 'forwardable' - -module Parslet - class Source - extend Forwardable - - def initialize(str) - raise ArgumentError unless str.respond_to?(:to_str) - - @str = StringScanner.new(str) - - @line_cache = LineCache.new - @line_cache.scan_for_line_endings(0, str) - end - - def matches?(pattern) - regexp = pattern.is_a?(String) ? Regexp.new(Regexp.escape(pattern)) : pattern - !@str.match?(regexp).nil? - end - alias match matches? - - def consume(n) - original_pos = @str.pos - slice_str = n.times.map { @str.getch }.join - slice = Parslet::Slice.new( - slice_str, - original_pos, - @line_cache) - - return slice - end - - def chars_left - @str.rest_size - end - - def_delegator :@str, :pos - def pos=(n) - if n > @str.string.bytesize - @str.pos = @str.string.bytesize - else - @str.pos = n - end - end - - - class LineCache - def scan_for_line_endings(start_pos, buf) - return unless buf - - buf = StringScanner.new(buf) - return unless buf.exist?(/\n/) - - ## If we have already read part or all of buf, we already know about - ## line ends in that portion. remove it and correct cur (search index) - if @last_line_end && start_pos < @last_line_end - # Let's not search the range from start_pos to last_line_end again. - buf.pos = @last_line_end - start_pos - end - - ## Scan the string for line endings; store the positions of all endings - ## in @line_ends. - while buf.skip_until(/\n/) - @last_line_end = start_pos + buf.pos - @line_ends << @last_line_end - end - end - end - end -end From affde6e9f6ce5b062c3b04de7eee0ab6943f65e0 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:35:24 -0400 Subject: [PATCH 73/89] update changelog --- CHANGELOG.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 36f85cf..4ee940b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,7 @@ +## (unreleased) + +* Upgrades parslet dependency to v1.6.1 and drops optimization monkeypatch + ## 1.3.2 - 6/22/2013 ## * Fixes attribute parsing bug that includes comments with braces From 0630d341252dd4e576151f7fa228432655ab92f8 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:39:43 -0400 Subject: [PATCH 74/89] Use correct terminology --- CHANGELOG.md | 1 + lib/csscss/reporter.rb | 2 +- test/csscss/reporter_test.rb | 12 ++++++------ 3 files changed, 8 insertions(+), 7 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4ee940b..39e3e4f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,7 @@ ## (unreleased) * Upgrades parslet dependency to v1.6.1 and drops optimization monkeypatch +* Use correct terminology "declartions" instead of "rules" in the output ## 1.3.2 - 6/22/2013 ## diff --git a/lib/csscss/reporter.rb b/lib/csscss/reporter.rb index 8509872..96f428c 100644 --- a/lib/csscss/reporter.rb +++ b/lib/csscss/reporter.rb @@ -13,7 +13,7 @@ def report(options = {}) selector_groups = selector_groups.map {|selectors| "{#{maybe_color(selectors, :red, should_color)}}" } last_selector = selector_groups.pop count = declarations.size - io.puts %Q(#{selector_groups.join(", ")} AND #{last_selector} share #{maybe_color(count, :red, should_color)} rule#{"s" if count > 1}) + io.puts %Q(#{selector_groups.join(", ")} AND #{last_selector} share #{maybe_color(count, :red, should_color)} declaration#{"s" if count > 1}) if verbose declarations.each {|dec| io.puts(" - #{maybe_color(dec, :yellow, should_color)}") } end diff --git a/test/csscss/reporter_test.rb b/test/csscss/reporter_test.rb index 17d3607..eb8fcbf 100644 --- a/test/csscss/reporter_test.rb +++ b/test/csscss/reporter_test.rb @@ -12,19 +12,19 @@ module Csscss }) expected =<<-EXPECTED -{.foo} AND {.bar} share 2 rules -{h1, h2}, {.foo} AND {.baz} share 1 rule -{h1, h2} AND {.bar} share 1 rule +{.foo} AND {.bar} share 2 declarations +{h1, h2}, {.foo} AND {.baz} share 1 declaration +{h1, h2} AND {.bar} share 1 declaration EXPECTED reporter.report(color:false).must_equal expected expected =<<-EXPECTED -{.foo} AND {.bar} share 2 rules +{.foo} AND {.bar} share 2 declarations - width: 1px - border: black -{h1, h2}, {.foo} AND {.baz} share 1 rule +{h1, h2}, {.foo} AND {.baz} share 1 declaration - display: none -{h1, h2} AND {.bar} share 1 rule +{h1, h2} AND {.bar} share 1 declaration - position: relative EXPECTED reporter.report(verbose:true, color:false).must_equal expected From 10248693b620b366a716318a037a30c3d7e0903c Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:40:34 -0400 Subject: [PATCH 75/89] Bump version for release --- CHANGELOG.md | 2 +- Gemfile.lock | 2 +- lib/csscss/version.rb | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 39e3e4f..024f5ee 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,4 +1,4 @@ -## (unreleased) +## 1.3.3 - 5/30/2014 ## * Upgrades parslet dependency to v1.6.1 and drops optimization monkeypatch * Use correct terminology "declartions" instead of "rules" in the output diff --git a/Gemfile.lock b/Gemfile.lock index 9b33215..ded9c99 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,7 +1,7 @@ PATH remote: . specs: - csscss (1.3.2) + csscss (1.3.3) colorize parslet (>= 1.6.1, < 2.0) diff --git a/lib/csscss/version.rb b/lib/csscss/version.rb index aec9959..7623093 100644 --- a/lib/csscss/version.rb +++ b/lib/csscss/version.rb @@ -1,3 +1,3 @@ module Csscss - VERSION = "1.3.2" + VERSION = "1.3.3" end From f6059f3d0728ff639ef283f4de3798795f392e06 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:41:14 -0400 Subject: [PATCH 76/89] Test against 2.1.2 --- .travis.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.travis.yml b/.travis.yml index 222078e..7f4a405 100644 --- a/.travis.yml +++ b/.travis.yml @@ -2,3 +2,4 @@ language: ruby rvm: - 1.9.3 - 2.0.0 + - 2.1.2 From d88a744f328dea516be0bfbca22ff3851c0b9c23 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 30 May 2014 20:42:03 -0400 Subject: [PATCH 77/89] Stop testing against 1.9.3 --- .travis.yml | 1 - 1 file changed, 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 7f4a405..4d1ff2e 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,5 +1,4 @@ language: ruby rvm: - - 1.9.3 - 2.0.0 - 2.1.2 From 691fe8aceb6e49c7c401fb709a5bedf177b35728 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Fri, 29 Aug 2014 15:50:07 -0400 Subject: [PATCH 78/89] Adds gulp to the list --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index 4e51efb..5367f7e 100644 --- a/README.md +++ b/README.md @@ -67,6 +67,7 @@ jruby. * [compass-csscss](https://github.com/Comcast/compass-csscss) integrates csscss with [compass](http://compass-style.org/) projects. * [grunt-csscss](https://github.com/peterkeating/grunt-csscss) a [grunt](http://gruntjs.com/) task to automatically run csscss. +* [gulp-csscss](https://www.npmjs.org/package/gulp-csscss/) a [gulp](http://gulpjs.com/) task to automatically run csscss. _Please submit [an issue](https://github.com/zmoazeni/csscss/issues/new) if you know of any others._ From 6d2ac0301335412249c590418dadadae58923a20 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Mon, 26 Nov 2018 14:26:37 -0500 Subject: [PATCH 79/89] A couple Readme tweaks --- README.md | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/README.md b/README.md index 5367f7e..ea7df7d 100644 --- a/README.md +++ b/README.md @@ -75,7 +75,7 @@ _Please submit [an issue](https://github.com/zmoazeni/csscss/issues/new) if you I have been asked this a lot, but csscss is intentionally designed this way. Check out [this -post](http://connectionrequired.com/blog/2013/04/why-csscss-doesnt-remove-duplication-for-you/) +post](https://connectionrequired.com/blog/2013/04/why-csscss-doesnt-remove-duplication-for-you) for my reasoning. ## I found bugs ## @@ -87,12 +87,6 @@ If you find any issues, please report them on Please include the smallest CSS snippet to describe the issue and the output you expect to see. -## Who are you? ## - -My name is [Zach Moazeni](https://twitter.com/zmoazeni). I work for [an -awesome company](http://www.getharvest.com/). And [we're -hiring!](http://www.getharvest.com/careers) - ## I'm a dev, I can help ## Awesome! Thanks! Here are the steps I ask: From 00664a60fcf90646820af13cdee4b609aed2a08d Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Mon, 26 Nov 2018 18:32:23 -0500 Subject: [PATCH 80/89] Relocking the dependencies --- Gemfile.lock | 54 +++++++++++++++++++++++++++++----------------------- 1 file changed, 30 insertions(+), 24 deletions(-) diff --git a/Gemfile.lock b/Gemfile.lock index ded9c99..33ae5c4 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -8,37 +8,40 @@ PATH GEM remote: https://rubygems.org/ specs: - blankslate (2.1.2.4) - byebug (3.1.2) - columnize (~> 0.8) - debugger-linecache (~> 1.2) - chunky_png (1.2.7) - colorize (0.7.3) - columnize (0.8.9) - commonjs (0.2.6) + byebug (10.0.2) + chunky_png (1.3.11) + colorize (0.8.1) + commonjs (0.2.7) compass (0.12.2) chunky_png (~> 1.2) fssm (>= 0.2.7) sass (~> 3.1) - debugger-linecache (1.2.0) + ffi (1.9.25) fssm (0.2.10) - less (2.3.1) - commonjs (~> 0.2.6) - libv8 (3.11.8.17) - m (1.3.1) + less (2.6.0) + commonjs (~> 0.2.7) + libv8 (3.16.14.19) + m (1.5.1) method_source (>= 0.6.7) rake (>= 0.9.2.2) - method_source (0.8.1) - minitest (2.12.1) - minitest-rg (1.1.0) - parslet (1.6.1) - blankslate (~> 2.0) - rake (10.0.3) - ref (1.0.4) - ruby-prof (0.13.0) - sass (3.2.7) - therubyracer (0.11.4) - libv8 (~> 3.11.8.12) + method_source (0.9.2) + minitest (5.11.3) + minitest-rg (5.2.0) + minitest (~> 5.0) + parslet (1.8.2) + rake (12.3.1) + rb-fsevent (0.10.3) + rb-inotify (0.9.10) + ffi (>= 0.5.0, < 2) + ref (2.0.0) + ruby-prof (0.17.0) + sass (3.7.2) + sass-listen (~> 4.0.0) + sass-listen (4.0.0) + rb-fsevent (~> 0.9, >= 0.9.4) + rb-inotify (~> 0.9, >= 0.9.7) + therubyracer (0.12.3) + libv8 (~> 3.16.14.15) ref PLATFORMS @@ -56,3 +59,6 @@ DEPENDENCIES ruby-prof sass therubyracer + +BUNDLED WITH + 1.16.4 From 414f7c759a5f54639f14994c8232161e92c9bc96 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Mon, 26 Nov 2018 18:32:56 -0500 Subject: [PATCH 81/89] Fixes test --- test/csscss/sass_include_extensions_test.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/csscss/sass_include_extensions_test.rb b/test/csscss/sass_include_extensions_test.rb index 76ace2e..13f0ea8 100644 --- a/test/csscss/sass_include_extensions_test.rb +++ b/test/csscss/sass_include_extensions_test.rb @@ -61,7 +61,7 @@ module Csscss /* CSSCSS END MIXIN: foo */ } CSS - Sass::Engine.new("@import '#{f.path}'", syntax: :scss, cache: false).render.must_equal(css) + Sass::Engine.new("@import '#{File.basename(f.path)}'", syntax: :scss, cache: false, load_paths: ["/tmp"]).render.must_equal(css) end end end From b8b03c35576eb0e409845d8ecd317abcd2a0e7aa Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Mon, 26 Nov 2018 18:35:52 -0500 Subject: [PATCH 82/89] Bump version file --- .ruby-version | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.ruby-version b/.ruby-version index ec6b00f..73462a5 100644 --- a/.ruby-version +++ b/.ruby-version @@ -1 +1 @@ -ruby-2.1.2 +2.5.1 From 37e5e331a4b465ba433a9e4ae1515b8cbe43bc25 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 27 Nov 2018 09:53:49 -0500 Subject: [PATCH 83/89] Use best practice when declaring structs --- lib/csscss/types.rb | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/lib/csscss/types.rb b/lib/csscss/types.rb index 32afd3a..976475b 100644 --- a/lib/csscss/types.rb +++ b/lib/csscss/types.rb @@ -1,5 +1,5 @@ module Csscss - class Declaration < Struct.new(:property, :value, :parents) + Declaration = Struct.new(:property, :value, :parents) do def self.from_csspool(dec) new(dec.property.to_s.downcase, dec.expressions.join(" ").downcase) end @@ -79,7 +79,7 @@ def normalize_value(value) end end - class Selector < Struct.new(:selectors) + Selector = Struct.new(:selectors) do def self.from_parser(selectors) new(selectors.to_s.strip) end @@ -97,6 +97,5 @@ def inspect end end - class Ruleset < Struct.new(:selectors, :declarations) - end + Ruleset = Struct.new(:selectors, :declarations) end From 97c0941966434e407e51a9d62ef7c3046e96c733 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 27 Nov 2018 09:58:03 -0500 Subject: [PATCH 84/89] Add docker-ruby command --- docker-ruby | 2 ++ 1 file changed, 2 insertions(+) create mode 100755 docker-ruby diff --git a/docker-ruby b/docker-ruby new file mode 100755 index 0000000..9c06fbd --- /dev/null +++ b/docker-ruby @@ -0,0 +1,2 @@ +#!/bin/bash +docker run -it --rm -v $(pwd):/app -v csscss_gem_data:/usr/local/bundle -w /app ruby $@ From 709fb6aeed31b46177d25adb5aa4f5bc99edd91c Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 27 Nov 2018 09:58:55 -0500 Subject: [PATCH 85/89] Remove unnecessary method --- lib/csscss/types.rb | 4 ---- 1 file changed, 4 deletions(-) diff --git a/lib/csscss/types.rb b/lib/csscss/types.rb index 976475b..3d01f4d 100644 --- a/lib/csscss/types.rb +++ b/lib/csscss/types.rb @@ -1,9 +1,5 @@ module Csscss Declaration = Struct.new(:property, :value, :parents) do - def self.from_csspool(dec) - new(dec.property.to_s.downcase, dec.expressions.join(" ").downcase) - end - def self.from_parser(property, value, clean = true) value = value.to_s property = property.to_s From a0c0e7e964315c521de7946e2e9f10e876357e9f Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 27 Nov 2018 10:04:01 -0500 Subject: [PATCH 86/89] Use latest ruby version --- .travis.yml | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index 4d1ff2e..b7360ae 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,4 +1,3 @@ language: ruby rvm: - - 2.0.0 - - 2.1.2 + - 2.5 From 9a503419e895039457c7194e99cfaf720c698c65 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 27 Nov 2018 10:09:07 -0500 Subject: [PATCH 87/89] Allow docker version to be changed Also test other versions in travis --- .travis.yml | 2 ++ docker-ruby | 3 ++- 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index b7360ae..9323019 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,3 +1,5 @@ language: ruby rvm: - 2.5 + - 2.4 + - 2.3 diff --git a/docker-ruby b/docker-ruby index 9c06fbd..33ea97f 100755 --- a/docker-ruby +++ b/docker-ruby @@ -1,2 +1,3 @@ #!/bin/bash -docker run -it --rm -v $(pwd):/app -v csscss_gem_data:/usr/local/bundle -w /app ruby $@ +VERSION=${VERSION:-latest} +docker run -it --rm -v $(pwd):/app -v csscss_gem_data:/usr/local/bundle -w /app ruby:$VERSION $@ From 01eb85320eda32ee4d9e77614d80bb11be45e835 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 27 Nov 2018 10:11:14 -0500 Subject: [PATCH 88/89] Fixes warning about shadowing --- lib/csscss/cli.rb | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/lib/csscss/cli.rb b/lib/csscss/cli.rb index 0adec9e..2b8430d 100644 --- a/lib/csscss/cli.rb +++ b/lib/csscss/cli.rb @@ -64,7 +64,7 @@ def execute end def parse(argv) - opts = OptionParser.new do |opts| + options = OptionParser.new do |opts| opts.banner = "Usage: csscss [files..]" opts.version = Csscss::VERSION @@ -128,11 +128,11 @@ def parse(argv) print_help(opts) end end - opts.parse!(argv) + options.parse!(argv) - print_help(opts) if argv.empty? + print_help(options) if argv.empty? rescue OptionParser::ParseError - print_help(opts) + print_help(options) end def print_help(opts) From bac3e424b2deddbeade08677b9958533c52828e6 Mon Sep 17 00:00:00 2001 From: Zach Moazeni Date: Tue, 27 Nov 2018 12:45:07 -0500 Subject: [PATCH 89/89] Ignore vscode settings --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index 4288db2..fd69015 100644 --- a/.gitignore +++ b/.gitignore @@ -16,3 +16,4 @@ test/tmp test/version_tmp tmp _site +.vscode