hamlit 2.11.1 → 2.14.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (43) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/test.yml +36 -0
  3. data/.gitignore +2 -1
  4. data/CHANGELOG.md +53 -0
  5. data/Gemfile +0 -4
  6. data/LICENSE.txt +26 -23
  7. data/README.md +9 -8
  8. data/benchmark/graph/graph.key +0 -0
  9. data/benchmark/graph/graph.png +0 -0
  10. data/bin/update-haml +125 -0
  11. data/ext/hamlit/hamlit.c +0 -1
  12. data/hamlit.gemspec +1 -1
  13. data/lib/hamlit.rb +6 -4
  14. data/lib/hamlit/attribute_builder.rb +2 -2
  15. data/lib/hamlit/attribute_compiler.rb +3 -3
  16. data/lib/hamlit/cli.rb +34 -10
  17. data/lib/hamlit/compiler/children_compiler.rb +1 -1
  18. data/lib/hamlit/compiler/comment_compiler.rb +1 -0
  19. data/lib/hamlit/filters/escaped.rb +1 -1
  20. data/lib/hamlit/filters/markdown.rb +1 -0
  21. data/lib/hamlit/filters/preserve.rb +1 -1
  22. data/lib/hamlit/filters/text_base.rb +1 -1
  23. data/lib/hamlit/filters/tilt_base.rb +1 -1
  24. data/lib/hamlit/parser.rb +6 -2
  25. data/lib/hamlit/parser/haml_attribute_builder.rb +164 -0
  26. data/lib/hamlit/parser/haml_buffer.rb +20 -130
  27. data/lib/hamlit/parser/haml_compiler.rb +1 -553
  28. data/lib/hamlit/parser/haml_error.rb +29 -25
  29. data/lib/hamlit/parser/haml_escapable.rb +1 -0
  30. data/lib/hamlit/parser/haml_generator.rb +1 -0
  31. data/lib/hamlit/parser/haml_helpers.rb +41 -59
  32. data/lib/hamlit/parser/{haml_xss_mods.rb → haml_helpers/xss_mods.rb} +20 -15
  33. data/lib/hamlit/parser/haml_options.rb +53 -66
  34. data/lib/hamlit/parser/haml_parser.rb +133 -73
  35. data/lib/hamlit/parser/haml_temple_engine.rb +123 -0
  36. data/lib/hamlit/parser/haml_util.rb +10 -40
  37. data/lib/hamlit/rails_template.rb +1 -1
  38. data/lib/hamlit/string_splitter.rb +1 -0
  39. data/lib/hamlit/version.rb +1 -1
  40. metadata +17 -12
  41. data/.travis.yml +0 -49
  42. data/lib/hamlit/parser/MIT-LICENSE +0 -20
  43. data/lib/hamlit/parser/README.md +0 -30
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 315b433bd4a2af17f13b1a8ff54787c65b25beabcbdb1274dd86b29248e75f60
4
- data.tar.gz: cd02934b413dd1cf6891f35f5cb1ee8731d68e0f82eb300bf92679b7574ec598
3
+ metadata.gz: 3a301e3719b15a8bd389c69273087c6133a0f64a50794e256106c65fb402a652
4
+ data.tar.gz: f5548a7ca946d6339a4767c13fc4dfcf8779274a95d179dccabf4ceb269aa35e
5
5
  SHA512:
6
- metadata.gz: 128daeb6d3f1d34fd33718b90b20b75117cda4147e8783d039b2daf0e019d836ac580d78fd3e01561f53f4348e442d3a04169761048cc2105ef1e3cae5c5c131
7
- data.tar.gz: 0c11bc8dce803aa8d2adfdc78c7b91274678371adb7d30a8a36d997b60ada32320349712cd39c1feec7d965f5e1bbf6b6ab878a3769d4e20ee245afd1772bf79
6
+ metadata.gz: c5858d26f7573e085d1da827a3d9eee1a6c8252e8a6a0459a8e1022dc99a2cb15cce1bd4931ffc2df26815e85a717df0fd119f3585d605aaeb67a5c7c38021df
7
+ data.tar.gz: 6fa9187e20778096808fce4e997df74c67b9d980ba4219baf55b64f9930b87c3b35b21a74c50355c6a443750e6d5465d6b6977dd322aeea5bdc7ecdb57d44519
@@ -0,0 +1,36 @@
1
+ name: test
2
+ on:
3
+ push:
4
+ branches:
5
+ - master
6
+ pull_request:
7
+ types:
8
+ - opened
9
+ - synchronize
10
+ - reopened
11
+ schedule:
12
+ - cron: "00 15 * * *" # 7:00 PST (-8), 8:00 PDT (-7)
13
+ jobs:
14
+ test:
15
+ runs-on: ubuntu-latest
16
+ container: ${{ matrix.ruby }}
17
+ strategy:
18
+ fail-fast: false
19
+ matrix:
20
+ ruby:
21
+ - ruby:2.5
22
+ - ruby:2.6
23
+ - ruby:2.7
24
+ - ruby:3.0
25
+ # TODO: add jruby and truffleruby
26
+ steps:
27
+ - uses: actions/checkout@v2
28
+ - uses: actions/cache@v2
29
+ with:
30
+ path: vendor/bundle
31
+ key: ${{ runner.os }}-${{ matrix.ruby }}-gems-${{ hashFiles('**/Gemfile.lock') }}
32
+ restore-keys: ${{ runner.os }}-gems-
33
+ - run: apt-get update && apt-get install -y nodejs # For execjs
34
+ - name: bundle install
35
+ run: bundle config path vendor/bundle && bundle install -j$(nproc) --retry 3
36
+ - run: bundle exec rake test
data/.gitignore CHANGED
@@ -7,11 +7,12 @@
7
7
  /pkg/
8
8
  /spec/reports/
9
9
  /tmp/
10
+ /haml/
10
11
  .sass-cache
11
12
  .ruby-version
12
13
  *.bundle
13
14
  *.so
14
15
  *.su
15
- *.o
16
16
  *.a
17
+ *.o
17
18
  *.swp
@@ -4,6 +4,59 @@ All notable changes to this project will be documented in this file. This
4
4
  project adheres to [Semantic Versioning](http://semver.org/). This change log is based upon
5
5
  [keep-a-changelog](https://github.com/olivierlacan/keep-a-changelog).
6
6
 
7
+ ## [2.14.1](https://github.com/k0kubun/hamlit/compare/v2.14.0...v2.14.1) - 2021-01-07
8
+
9
+ ### Added
10
+
11
+ - Add `-c` option to `hamlit compile` that works like `haml -c` [#166](https://github.com/k0kubun/hamlit/issues/166)
12
+ *Thanks to @knightq*
13
+
14
+ ## [2.14.0](https://github.com/k0kubun/hamlit/compare/v2.13.2...v2.14.0) - 2021-01-07
15
+
16
+ ### Changed
17
+
18
+ - CLI changes
19
+ - Remove `-c` shorthand of `--color`.
20
+ - Make `--color` default. Please use `--no-color` to disable it.
21
+ - `--color` uses IRB instead of Pry for syntax highlight.
22
+ - Syntax highlight of `hamlit compile` is enabled only with IRB of Ruby 2.7+.
23
+ - Syntax highlight of `hamlit parse` / `hamlit temple` is enabled only with IRB of Ruby 3.1+.
24
+
25
+ ## [2.13.2](https://github.com/k0kubun/hamlit/compare/v2.13.1...v2.13.2) - 2020-12-27
26
+
27
+ ### Added
28
+
29
+ - Speed up `hamlit` commands [#166](https://github.com/k0kubun/hamlit/issues/166)
30
+ *Thanks to @knightq*
31
+
32
+ ## [2.13.1](https://github.com/k0kubun/hamlit/compare/v2.13.0...v2.13.1) - 2020-12-27
33
+
34
+ ### Added
35
+
36
+ - Support [multiline attributes](https://github.com/haml/haml/pull/1043) of Haml 5.2.1.
37
+
38
+ ## [2.13.0](https://github.com/k0kubun/hamlit/compare/v2.12.0...v2.13.0) - 2020-10-02
39
+
40
+ ### Added
41
+
42
+ - Support `--enable-frozen-string-literal` [#162](https://github.com/k0kubun/hamlit/issues/162).
43
+ *Thanks to @aliismayilov*
44
+
45
+ ### Changed
46
+
47
+ - Upgrade the Haml parser from Haml 4.0 to 5.2 [#163](https://github.com/k0kubun/hamlit/issues/163).
48
+ - Allow `@` as tag's class name.
49
+ - Fix NameError on an `InvalidAttributeNameError` reference introduced at Hamlit v2.12.0.
50
+ - You can no longer specify `ugly` option, which has had no effect.
51
+
52
+ ## [2.12.0](https://github.com/k0kubun/hamlit/compare/v2.11.1...v2.12.0) - 2020-09-30
53
+
54
+ ### Changed
55
+
56
+ - Class names are no longer ordered alphabetically.
57
+ *Thanks to @aliismayilov*
58
+ - This is compatible with [Haml 5.2](https://github.com/haml/haml/blob/v5.2.0/CHANGELOG.md#52)
59
+
7
60
  ## [2.11.1](https://github.com/k0kubun/hamlit/compare/v2.11.0...v2.11.1) - 2020-08-25
8
61
 
9
62
  ### Fixed
data/Gemfile CHANGED
@@ -8,10 +8,6 @@ end
8
8
  # Specify your gem's dependencies in hamlit.gemspec
9
9
  gemspec
10
10
 
11
- if Gem::Version.new(RUBY_VERSION) < Gem::Version.new('2.2.2')
12
- gem 'rack', '< 2'
13
- end
14
-
15
11
  gem 'benchmark-ips', '2.3.0'
16
12
  gem 'maxitest'
17
13
  gem 'pry'
@@ -1,3 +1,29 @@
1
+ Copyright (c) 2006-2019 Hampton Catlin and Natalie Weizenbaum
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining
4
+ a copy of this software and associated documentation files (the
5
+ "Software"), to deal in the Software without restriction, including
6
+ without limitation the rights to use, copy, modify, merge, publish,
7
+ distribute, sublicense, and/or sell copies of the Software, and to
8
+ permit persons to whom the Software is furnished to do so, subject to
9
+ the following conditions:
10
+
11
+ The above copyright notice and this permission notice shall be
12
+ included in all copies or substantial portions of the Software.
13
+
14
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
15
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
16
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
17
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
18
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
19
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
20
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
21
+
22
+ ===
23
+
24
+ The above license is applied to lib/hamlit/parser/*.rb and test/haml/*.
25
+ Everything else is licensed under:
26
+
1
27
  The MIT License (MIT)
2
28
 
3
29
  Copyright (c) 2015 Takashi Kokubun
@@ -19,26 +45,3 @@ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
45
  LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
46
  OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
47
  THE SOFTWARE.
22
-
23
- lib/hamlit/parser/*.rb and test/haml/* are:
24
-
25
- Copyright (c) 2006-2009 Hampton Catlin and Natalie Weizenbaum
26
-
27
- Permission is hereby granted, free of charge, to any person obtaining
28
- a copy of this software and associated documentation files (the
29
- "Software"), to deal in the Software without restriction, including
30
- without limitation the rights to use, copy, modify, merge, publish,
31
- distribute, sublicense, and/or sell copies of the Software, and to
32
- permit persons to whom the Software is furnished to do so, subject to
33
- the following conditions:
34
-
35
- The above copyright notice and this permission notice shall be
36
- included in all copies or substantial portions of the Software.
37
-
38
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
39
- EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
40
- MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
41
- NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
42
- LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
43
- OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
44
- WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md CHANGED
@@ -2,6 +2,7 @@
2
2
 
3
3
  [![Gem Version](https://badge.fury.io/rb/hamlit.svg)](http://badge.fury.io/rb/hamlit)
4
4
  [![Build Status](https://travis-ci.org/k0kubun/hamlit.svg?branch=master)](https://travis-ci.org/k0kubun/hamlit)
5
+ [![test](https://github.com/k0kubun/hamlit/workflows/test/badge.svg)](https://github.com/k0kubun/hamlit/actions?query=workflow%3Atest)
5
6
 
6
7
  Hamlit is a high performance [Haml](https://github.com/haml/haml) implementation.
7
8
 
@@ -10,17 +11,17 @@ Hamlit is a high performance [Haml](https://github.com/haml/haml) implementation
10
11
  ### What is Hamlit?
11
12
  Hamlit is another implementation of [Haml](https://github.com/haml/haml).
12
13
  With some [limitations](REFERENCE.md#limitations) by design for performance,
13
- Hamlit is **2.39x times faster** than original haml gem in [this benchmark](benchmark/slim/run-benchmarks.rb),
14
- which is an HTML-escaped version of [slim-template/slim's one](https://github.com/slim-template/slim/blob/v3.0.8/benchmarks/run-benchmarks.rb) for fairness. ([Result on Travis](https://travis-ci.org/k0kubun/hamlit/jobs/236567391))
14
+ Hamlit is **1.94x times faster** than original haml gem in [this benchmark](benchmark/slim/run-benchmarks.rb),
15
+ which is an HTML-escaped version of [slim-template/slim's one](https://github.com/slim-template/slim/blob/4.1.0/benchmarks/run-benchmarks.rb) for fairness. ([Result on Travis](https://travis-ci.org/github/k0kubun/hamlit/jobs/732178446))
15
16
 
16
- <img src="https://i.gyazo.com/0f0c0362b6bd69f82715bec1d8caa191.png" width="600px" alt="Hamlit Benchmark"/>
17
+ <img src="https://raw.githubusercontent.com/k0kubun/hamlit/afcc2b36c4861c2f764baa09afd9530ca25eeafa/benchmark/graph/graph.png" width="600x" alt="Hamlit Benchmark" />
17
18
 
18
19
  ```
19
- hamlit v2.8.1: 131048.9 i/s
20
- erubi v1.6.0: 125445.4 i/s - 1.04x slower
21
- slim v3.0.8: 121390.4 i/s - 1.08x slower
22
- faml v0.8.1: 100750.5 i/s - 1.30x slower
23
- haml v5.0.1: 54882.6 i/s - 2.39x slower
20
+ hamlit v2.13.0: 247404.4 i/s
21
+ erubi v1.9.0: 244356.4 i/s - 1.01x slower
22
+ slim v4.1.0: 238254.3 i/s - 1.04x slower
23
+ faml v0.8.1: 197293.2 i/s - 1.25x slower
24
+ haml v5.2.0: 127834.4 i/s - 1.94x slower
24
25
  ```
25
26
 
26
27
  ### Why is Hamlit faster?
Binary file
Binary file
@@ -0,0 +1,125 @@
1
+ #!/usr/bin/env ruby
2
+ require 'fileutils'
3
+ require 'tmpdir'
4
+
5
+ HAML_REPO = 'haml/haml'
6
+ HAML_VERSION = '5.2.1'
7
+
8
+ module GitHubFetcher
9
+ def self.fetch(repo, tag:, path:)
10
+ Dir.mktmpdir do |dir|
11
+ Dir.chdir(dir) do
12
+ url = "https://github.com/#{repo}/archive/#{tag}.tar.gz"
13
+ system("curl -L --fail --retry 3 --retry-delay 1 #{url} -o - | tar zxf -")
14
+ FileUtils.mv("#{File.basename(repo)}-#{tag.sub(/\Av/, '')}", path)
15
+ end
16
+ end
17
+ end
18
+ end
19
+
20
+ class LicenseBuilder
21
+ DELIMITER = "\n==="
22
+
23
+ def initialize(haml_license:, hamlit_license:)
24
+ @haml_license = haml_license
25
+ @hamlit_license = hamlit_license
26
+ end
27
+
28
+ def build
29
+ license = [
30
+ File.read(@haml_license),
31
+ File.read(@hamlit_license).split(DELIMITER, 2).last,
32
+ ].join(DELIMITER)
33
+ File.write(@hamlit_license, license)
34
+ end
35
+ end
36
+
37
+ # Generate lib/hamlit/parser from haml
38
+ class HamlitParserBuilder
39
+ TARGET_FILES = [
40
+ 'attribute_builder.rb',
41
+ 'buffer.rb',
42
+ 'error.rb',
43
+ 'helpers.rb',
44
+ 'options.rb',
45
+ 'temple_engine.rb',
46
+ # TODO: make the upstream sharable first
47
+ # 'parser.rb',
48
+ 'util.rb',
49
+ 'helpers/xss_mods.rb',
50
+ ]
51
+
52
+ # Classes which are just referenced by Options and not really used by the parser
53
+ DUMMY_CLASSES = {
54
+ 'compiler.rb' => 'Compiler',
55
+ 'escapable.rb' => 'Escapable',
56
+ 'generator.rb' => 'Generator',
57
+ }
58
+
59
+ def initialize(haml:, hamlit_parser:)
60
+ @haml = haml
61
+ @hamlit_parser = hamlit_parser
62
+ end
63
+
64
+ def build
65
+ TARGET_FILES.each do |file|
66
+ src_path = File.join(@haml, file)
67
+ dest_path = File.join(@hamlit_parser, "haml_#{file}")
68
+
69
+ FileUtils.mkdir_p(File.dirname(dest_path))
70
+ FileUtils.cp(src_path, dest_path)
71
+
72
+ src = File.read(dest_path)
73
+ patch_source!(src, file: file)
74
+ File.write(dest_path, src)
75
+ end
76
+
77
+ DUMMY_CLASSES.each do |file, klass|
78
+ dest_path = File.join(@hamlit_parser, "haml_#{file}")
79
+ src = "class Hamlit::Haml#{klass}; end\n"
80
+ File.write(dest_path, src)
81
+ end
82
+ end
83
+
84
+ private
85
+
86
+ def patch_source!(src, file:)
87
+ # Use Hamlit::HamlFoo instead of Haml::Foo
88
+ src.gsub!(/^module Haml\n((?: #[^\n]+\n)*) (module|class) ([^ ]+)/, "module Hamlit\n\\1 \\2 Haml\\3")
89
+ src.gsub!(/\bHaml::/, 'Hamlit::Haml')
90
+
91
+ # Prefix Haml to references without Haml::
92
+ src.gsub!(/\b(AttributeBuilder|Error|InvalidAttributeNameError|Options|Parser|SyntaxError)\./, 'Haml\0')
93
+ src.gsub!(/\brescue SyntaxError /, 'rescue HamlSyntaxError ')
94
+
95
+ # Hamlit should not rely on Haml
96
+ src.gsub!(/^require 'haml\/([^']+)'/, "require 'hamlit/parser/haml_\\1'")
97
+
98
+ case file
99
+ when 'error.rb'
100
+ src.gsub!(/^ class ([^ ]+) < ([^ ]+);/, ' class Haml\1 < Haml\2;')
101
+ when 'helpers.rb'
102
+ src.gsub!(/^ def is_haml\?\n false\n end/m) { |str| str.gsub(/^ /, ' # ') } # not needed for the parser
103
+ when 'options.rb'
104
+ src.gsub!(/\.is_a\?\(Options\)/, '.is_a?(HamlOptions)')
105
+ when 'temple_engine.rb'
106
+ src.gsub!(/\buse (Generator|Escapable)$/, 'use Haml\1')
107
+ end
108
+ end
109
+ end
110
+
111
+ FileUtils.rm_rf(haml = File.expand_path('../haml', __dir__))
112
+ GitHubFetcher.fetch(HAML_REPO, tag: HAML_VERSION, path: haml)
113
+
114
+ hamlit = File.expand_path('..', __dir__)
115
+ LicenseBuilder.new(
116
+ haml_license: File.join(haml, 'MIT-LICENSE'),
117
+ hamlit_license: File.join(hamlit, 'LICENSE.txt'),
118
+ ).build
119
+
120
+ hamlit_parser = File.join(hamlit, 'lib/hamlit/parser')
121
+ # TODO: FileUtils.rm_rf(hamlit_parser = File.join(hamlit, 'lib/hamlit/parser'))
122
+ HamlitParserBuilder.new(
123
+ haml: File.join(haml, 'lib/haml'),
124
+ hamlit_parser: hamlit_parser,
125
+ ).build
@@ -152,7 +152,6 @@ hamlit_build_multi_class(VALUE escape_attrs, VALUE values)
152
152
  }
153
153
  }
154
154
 
155
- rb_ary_sort_bang(buf);
156
155
  rb_funcall(buf, id_uniq_bang, 0);
157
156
 
158
157
  return escape_attribute(escape_attrs, rb_ary_join(buf, str_space()));
@@ -37,7 +37,7 @@ Gem::Specification.new do |spec|
37
37
  spec.add_development_dependency 'haml', '>= 5'
38
38
  spec.add_development_dependency 'less'
39
39
  spec.add_development_dependency 'minitest-reporters', '~> 1.1'
40
- spec.add_development_dependency 'rails', '>= 4.0.0'
40
+ spec.add_development_dependency 'rails', '>= 4.0'
41
41
  spec.add_development_dependency 'rake'
42
42
  spec.add_development_dependency 'rake-compiler'
43
43
  spec.add_development_dependency 'sass'
@@ -4,8 +4,10 @@ require 'hamlit/error'
4
4
  require 'hamlit/version'
5
5
  require 'hamlit/template'
6
6
 
7
- begin
8
- require 'rails'
9
- require 'hamlit/railtie'
10
- rescue LoadError
7
+ if File.basename($0) != 'hamlit'
8
+ begin
9
+ require 'rails'
10
+ require 'hamlit/railtie'
11
+ rescue LoadError
12
+ end
11
13
  end
@@ -47,7 +47,7 @@ module Hamlit::AttributeBuilder
47
47
  when value.is_a?(String)
48
48
  # noop
49
49
  when value.is_a?(Array)
50
- value = value.flatten.select { |v| v }.map(&:to_s).sort.uniq.join(' ')
50
+ value = value.flatten.select { |v| v }.map(&:to_s).uniq.join(' ')
51
51
  when value
52
52
  value = value.to_s
53
53
  else
@@ -67,7 +67,7 @@ module Hamlit::AttributeBuilder
67
67
  classes << value.to_s
68
68
  end
69
69
  end
70
- escape_html(escape_attrs, classes.map(&:to_s).sort.uniq.join(' '))
70
+ escape_html(escape_attrs, classes.map(&:to_s).uniq.join(' '))
71
71
  end
72
72
 
73
73
  def build_data(escape_attrs, quote, *hashes)
@@ -17,7 +17,7 @@ module Hamlit
17
17
  if node.value[:object_ref] != :nil || !Ripper.respond_to?(:lex) # No Ripper.lex in truffleruby
18
18
  return runtime_compile(node)
19
19
  end
20
- node.value[:attributes_hashes].each do |attribute_str|
20
+ [node.value[:dynamic_attributes].new, node.value[:dynamic_attributes].old].compact.each do |attribute_str|
21
21
  hash = AttributeParser.parse(attribute_str)
22
22
  return runtime_compile(node) unless hash
23
23
  hashes << hash
@@ -28,11 +28,11 @@ module Hamlit
28
28
  private
29
29
 
30
30
  def runtime_compile(node)
31
- attrs = node.value[:attributes_hashes]
31
+ attrs = []
32
32
  attrs.unshift(node.value[:attributes].inspect) if node.value[:attributes] != {}
33
33
 
34
34
  args = [@escape_attrs.inspect, "#{@quote.inspect}.freeze", @format.inspect].push(node.value[:object_ref]) + attrs
35
- [:html, :attrs, [:dynamic, "::Hamlit::AttributeBuilder.build(#{args.join(', ')})"]]
35
+ [:html, :attrs, [:dynamic, "::Hamlit::AttributeBuilder.build(#{args.join(', ')}, #{node.value[:dynamic_attributes].to_literal})"]]
36
36
  end
37
37
 
38
38
  def static_compile(static_hash, dynamic_hashes)
@@ -13,25 +13,33 @@ module Hamlit
13
13
  def render(file)
14
14
  process_load_options
15
15
  code = generate_code(file)
16
- puts eval(code)
16
+ puts eval(code, binding, file)
17
17
  end
18
18
 
19
19
  desc 'compile HAML', 'Show compile result'
20
20
  option :actionview, type: :boolean, default: false, aliases: %w[-a]
21
- option :color, type: :boolean, default: false, aliases: %w[-c]
21
+ option :color, type: :boolean, default: true
22
+ option :check, type: :boolean, default: false, aliases: %w[-c]
22
23
  def compile(file)
23
24
  code = generate_code(file)
25
+ if options[:check]
26
+ if error = validate_ruby(code, file)
27
+ abort error.message.split("\n").first
28
+ end
29
+ puts "Syntax OK"
30
+ return
31
+ end
24
32
  puts_code(code, color: options[:color])
25
33
  end
26
34
 
27
35
  desc 'temple HAML', 'Show temple intermediate expression'
28
- option :color, type: :boolean, default: false, aliases: %w[-c]
36
+ option :color, type: :boolean, default: true
29
37
  def temple(file)
30
38
  pp_object(generate_temple(file), color: options[:color])
31
39
  end
32
40
 
33
41
  desc 'parse HAML', 'Show parse result'
34
- option :color, type: :boolean, default: false, aliases: %w[-c]
42
+ option :color, type: :boolean, default: true
35
43
  def parse(file)
36
44
  pp_object(generate_ast(file), color: options[:color])
37
45
  end
@@ -107,24 +115,40 @@ module Hamlit
107
115
  render(args.first.to_s)
108
116
  end
109
117
 
110
- def puts_code(code, color: false)
118
+ def puts_code(code, color: true)
119
+ begin
120
+ require 'irb/color'
121
+ rescue LoadError
122
+ color = false
123
+ end
111
124
  if color
112
- require 'pry'
113
- puts Pry.Code(code).highlighted
125
+ puts IRB::Color.colorize_code(code)
114
126
  else
115
127
  puts code
116
128
  end
117
129
  end
118
130
 
119
131
  # Enable colored pretty printing only for development environment.
120
- def pp_object(arg, color: false)
132
+ def pp_object(arg, color: true)
133
+ begin
134
+ require 'irb/color_printer'
135
+ rescue LoadError
136
+ color = false
137
+ end
121
138
  if color
122
- require 'pry'
123
- Pry::ColorPrinter.pp(arg)
139
+ IRB::ColorPrinter.pp(arg)
124
140
  else
125
141
  require 'pp'
126
142
  pp(arg)
127
143
  end
128
144
  end
145
+
146
+ def validate_ruby(code, file)
147
+ begin
148
+ eval("BEGIN {return nil}; #{code}", binding, file)
149
+ rescue ::SyntaxError # Not to be confused with Hamlit::SyntaxError
150
+ $!
151
+ end
152
+ end
129
153
  end
130
154
  end