hamlit 2.13.2 → 2.14.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: cbc8030c410cd15d25db47c6a69ffb977ea32d7ce65e77cbdae3658c11456caa
4
- data.tar.gz: 922dccdfef223350790f605c76df0e8efb1f866d8d7b291a15ef1caaa4985499
3
+ metadata.gz: f7ba07071048a08ffc2c58df5987c6772236c1b895b9a301881d27c13311d318
4
+ data.tar.gz: cde3a650bcc4d06ac8909447203f90b99460ff187140347c9e528107bc62a1bc
5
5
  SHA512:
6
- metadata.gz: d055eeb98d94ce58784bbf6686b38c6ccdf4465a8ec56381b6c81ab137e6b6b9d193b7eb224f9b45115cbaa7a26432ceae90b8af4e5b4b59d068d7098e773507
7
- data.tar.gz: 3d24de3051c7bebea572b3f5f749f22bc6774212de8c6267b264162dae5d7e38b45bdb5a10e6dd0aec44936ba93db14bcda37ac4cd1a9f3b66fad76650fdd717
6
+ metadata.gz: de8bf0cddb83e2fd86b7876461e0b44c46eced02dc85b6375e60c3669d31b4079a9e8142842abb9a5b09dbf806c1d7288f96fbc4000168659029b115e033c7a9
7
+ data.tar.gz: 759a9899a5aaa126c10d5894294c66af62d74585f4d2eb99e4ed9813554fa7a07aade664071c529d7ebb71d72c62b87636abd9d09e3e82e77c8fb1193ee7ad8b
@@ -13,18 +13,28 @@ on:
13
13
  jobs:
14
14
  test:
15
15
  runs-on: ubuntu-latest
16
- container: ${{ matrix.ruby }}
17
16
  strategy:
18
17
  fail-fast: false
19
18
  matrix:
20
19
  ruby:
21
- - ruby:2.5
22
- - ruby:2.6
23
- - ruby:2.7
24
- # TODO: add jruby and truffleruby
20
+ - '2.5'
21
+ - '2.6'
22
+ - '2.7'
23
+ - '3.0'
24
+ - jruby
25
+ - truffleruby-head
25
26
  steps:
26
27
  - uses: actions/checkout@v2
27
- - run: apt-get update && apt-get install -y nodejs # For execjs
28
+ - name: Set up Ruby
29
+ uses: ruby/setup-ruby@v1
30
+ with:
31
+ ruby-version: ${{ matrix.ruby }}
32
+ - uses: actions/cache@v2
33
+ with:
34
+ path: vendor/bundle
35
+ key: ${{ runner.os }}-${{ matrix.ruby }}-gems-${{ hashFiles('**/Gemfile.lock') }}
36
+ restore-keys: ${{ runner.os }}-gems-
37
+ - run: sudo apt-get update && sudo apt-get install -y nodejs libxslt-dev # nodejs for execjs, libxslt for TruffleRuby nokogiri
28
38
  - name: bundle install
29
- run: bundle install -j$(nproc) --retry 3
39
+ run: bundle config path vendor/bundle && bundle install -j$(nproc) --retry 3
30
40
  - run: bundle exec rake test
data/.gitignore CHANGED
@@ -13,6 +13,6 @@
13
13
  *.bundle
14
14
  *.so
15
15
  *.su
16
- *.o
17
16
  *.a
17
+ *.o
18
18
  *.swp
data/CHANGELOG.md CHANGED
@@ -4,6 +4,45 @@ 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.4](https://github.com/k0kubun/hamlit/compare/v2.14.3...v2.14.4) - 2021-02-01
8
+
9
+ ### Fixed
10
+
11
+ - Prevent another SEGV in a C extension after `GC.compact` [#177](https://github.com/k0kubun/hamlit/issues/177)
12
+ *Thanks to @stanhu*
13
+
14
+ ## [2.14.3](https://github.com/k0kubun/hamlit/compare/v2.14.2...v2.14.3) - 2021-01-24
15
+
16
+ ### Fixed
17
+
18
+ - Ensure the Rails initializer is called before `:load_config_initializers` [#176](https://github.com/k0kubun/hamlit/issues/176)
19
+ *Thanks to @sunny*
20
+
21
+ ## [2.14.2](https://github.com/k0kubun/hamlit/compare/v2.14.1...v2.14.2) - 2021-01-21
22
+
23
+ ### Fixed
24
+
25
+ - Prevent SEGV in a C extension after `GC.compact` [#171](https://github.com/k0kubun/hamlit/issues/171)
26
+ *Thanks to @stanhu*
27
+
28
+ ## [2.14.1](https://github.com/k0kubun/hamlit/compare/v2.14.0...v2.14.1) - 2021-01-07
29
+
30
+ ### Added
31
+
32
+ - Add `-c` option to `hamlit compile` that works like `haml -c` [#166](https://github.com/k0kubun/hamlit/issues/166)
33
+ *Thanks to @knightq*
34
+
35
+ ## [2.14.0](https://github.com/k0kubun/hamlit/compare/v2.13.2...v2.14.0) - 2021-01-07
36
+
37
+ ### Changed
38
+
39
+ - CLI changes
40
+ - Remove `-c` shorthand of `--color`.
41
+ - Make `--color` default. Please use `--no-color` to disable it.
42
+ - `--color` uses IRB instead of Pry for syntax highlight.
43
+ - Syntax highlight of `hamlit compile` is enabled only with IRB of Ruby 2.7+.
44
+ - Syntax highlight of `hamlit parse` / `hamlit temple` is enabled only with IRB of Ruby 3.1+.
45
+
7
46
  ## [2.13.2](https://github.com/k0kubun/hamlit/compare/v2.13.1...v2.13.2) - 2020-12-27
8
47
 
9
48
  ### Added
data/README.md CHANGED
@@ -1,7 +1,7 @@
1
1
  # Hamlit
2
2
 
3
3
  [![Gem Version](https://badge.fury.io/rb/hamlit.svg)](http://badge.fury.io/rb/hamlit)
4
- [![Build Status](https://travis-ci.org/k0kubun/hamlit.svg?branch=master)](https://travis-ci.org/k0kubun/hamlit)
4
+ [![test](https://github.com/k0kubun/hamlit/workflows/test/badge.svg)](https://github.com/k0kubun/hamlit/actions?query=workflow%3Atest)
5
5
 
6
6
  Hamlit is a high performance [Haml](https://github.com/haml/haml) implementation.
7
7
 
data/ext/hamlit/hamlit.c CHANGED
@@ -6,15 +6,9 @@
6
6
 
7
7
  VALUE mAttributeBuilder, mObjectRef;
8
8
  static ID id_flatten, id_keys, id_parse, id_prepend, id_tr, id_uniq_bang;
9
- static ID id_aria, id_data, id_equal, id_hyphen, id_space, id_underscore;
10
- static ID id_boolean_attributes, id_xhtml;
9
+ static ID id_xhtml;
11
10
 
12
- static VALUE str_aria() { return rb_const_get(mAttributeBuilder, id_aria); }
13
- static VALUE str_data() { return rb_const_get(mAttributeBuilder, id_data); }
14
- static VALUE str_equal() { return rb_const_get(mAttributeBuilder, id_equal); }
15
- static VALUE str_hyphen() { return rb_const_get(mAttributeBuilder, id_hyphen); }
16
- static VALUE str_space() { return rb_const_get(mAttributeBuilder, id_space); }
17
- static VALUE str_underscore() { return rb_const_get(mAttributeBuilder, id_underscore); }
11
+ static VALUE str_aria, str_data, str_equal, str_hyphen, str_space, str_underscore;
18
12
 
19
13
  static void
20
14
  delete_falsey_values(VALUE values)
@@ -51,7 +45,7 @@ hyphenate(VALUE str)
51
45
 
52
46
  for (i = 0; i < RSTRING_LEN(str); i++) {
53
47
  if (RSTRING_PTR(str)[i] == '_') {
54
- rb_str_update(str, i, 1, str_hyphen());
48
+ rb_str_update(str, i, 1, str_hyphen);
55
49
  }
56
50
  }
57
51
  return str;
@@ -97,7 +91,7 @@ hamlit_build_id(VALUE escape_attrs, VALUE values)
97
91
  values = rb_funcall(values, id_flatten, 0);
98
92
  delete_falsey_values(values);
99
93
 
100
- attr_value = rb_ary_join(values, str_underscore());
94
+ attr_value = rb_ary_join(values, str_underscore);
101
95
  return escape_attribute(escape_attrs, attr_value);
102
96
  }
103
97
 
@@ -110,7 +104,7 @@ hamlit_build_single_class(VALUE escape_attrs, VALUE value)
110
104
  case T_ARRAY:
111
105
  value = rb_funcall(value, id_flatten, 0);
112
106
  delete_falsey_values(value);
113
- value = rb_ary_join(value, str_space());
107
+ value = rb_ary_join(value, str_space);
114
108
  break;
115
109
  default:
116
110
  if (RTEST(value)) {
@@ -154,7 +148,7 @@ hamlit_build_multi_class(VALUE escape_attrs, VALUE values)
154
148
 
155
149
  rb_funcall(buf, id_uniq_bang, 0);
156
150
 
157
- return escape_attribute(escape_attrs, rb_ary_join(buf, str_space()));
151
+ return escape_attribute(escape_attrs, rb_ary_join(buf, str_space));
158
152
  }
159
153
 
160
154
  static VALUE
@@ -285,7 +279,7 @@ hamlit_build_data(VALUE escape_attrs, VALUE quote, VALUE values, VALUE key_str)
285
279
 
286
280
  switch (value) {
287
281
  case Qtrue:
288
- rb_str_concat(buf, str_space());
282
+ rb_str_concat(buf, str_space);
289
283
  rb_str_concat(buf, key);
290
284
  break;
291
285
  case Qnil:
@@ -293,9 +287,9 @@ hamlit_build_data(VALUE escape_attrs, VALUE quote, VALUE values, VALUE key_str)
293
287
  case Qfalse:
294
288
  break; // noop
295
289
  default:
296
- rb_str_concat(buf, str_space());
290
+ rb_str_concat(buf, str_space);
297
291
  rb_str_concat(buf, key);
298
- rb_str_concat(buf, str_equal());
292
+ rb_str_concat(buf, str_equal);
299
293
  rb_str_concat(buf, quote);
300
294
  rb_str_concat(buf, escape_attribute(escape_attrs, to_s(value)));
301
295
  rb_str_concat(buf, quote);
@@ -348,13 +342,10 @@ merge_all_attrs(VALUE hashes)
348
342
  }
349
343
 
350
344
  int
351
- is_boolean_attribute(VALUE key)
345
+ is_boolean_attribute(VALUE key, VALUE boolean_attributes)
352
346
  {
353
- VALUE boolean_attributes;
354
347
  if (str_eq(rb_str_substr(key, 0, 5), "data-", 5)) return 1;
355
348
  if (str_eq(rb_str_substr(key, 0, 5), "aria-", 5)) return 1;
356
-
357
- boolean_attributes = rb_const_get(mAttributeBuilder, id_boolean_attributes);
358
349
  return RTEST(rb_ary_includes(boolean_attributes, key));
359
350
  }
360
351
 
@@ -379,13 +370,13 @@ hamlit_build_for_class(VALUE escape_attrs, VALUE quote, VALUE buf, VALUE values)
379
370
  void
380
371
  hamlit_build_for_data(VALUE escape_attrs, VALUE quote, VALUE buf, VALUE values)
381
372
  {
382
- rb_str_concat(buf, hamlit_build_data(escape_attrs, quote, values, str_data()));
373
+ rb_str_concat(buf, hamlit_build_data(escape_attrs, quote, values, str_data));
383
374
  }
384
375
 
385
376
  void
386
377
  hamlit_build_for_aria(VALUE escape_attrs, VALUE quote, VALUE buf, VALUE values)
387
378
  {
388
- rb_str_concat(buf, hamlit_build_data(escape_attrs, quote, values, str_aria()));
379
+ rb_str_concat(buf, hamlit_build_data(escape_attrs, quote, values, str_aria));
389
380
  }
390
381
 
391
382
  void
@@ -424,7 +415,7 @@ hamlit_build_for_boolean(VALUE escape_attrs, VALUE quote, VALUE format, VALUE bu
424
415
  }
425
416
 
426
417
  static VALUE
427
- hamlit_build(VALUE escape_attrs, VALUE quote, VALUE format, VALUE object_ref, VALUE hashes)
418
+ hamlit_build(VALUE escape_attrs, VALUE quote, VALUE format, VALUE boolean_attributes, VALUE object_ref, VALUE hashes)
428
419
  {
429
420
  long i;
430
421
  VALUE attrs, buf, key, keys, value;
@@ -445,7 +436,7 @@ hamlit_build(VALUE escape_attrs, VALUE quote, VALUE format, VALUE object_ref, VA
445
436
  hamlit_build_for_data(escape_attrs, quote, buf, value);
446
437
  } else if (str_eq(key, "aria", 4)) {
447
438
  hamlit_build_for_aria(escape_attrs, quote, buf, value);
448
- } else if (is_boolean_attribute(key)) {
439
+ } else if (is_boolean_attribute(key, boolean_attributes)) {
449
440
  hamlit_build_for_boolean(escape_attrs, quote, format, buf, key, value);
450
441
  } else {
451
442
  hamlit_build_for_others(escape_attrs, quote, buf, key, value);
@@ -485,7 +476,7 @@ rb_hamlit_build_aria(int argc, VALUE *argv, RB_UNUSED_VAR(VALUE self))
485
476
  rb_check_arity(argc, 2, UNLIMITED_ARGUMENTS);
486
477
  rb_scan_args(argc - 2, argv + 2, "*", &array);
487
478
 
488
- return hamlit_build_data(argv[0], argv[1], array, str_aria());
479
+ return hamlit_build_data(argv[0], argv[1], array, str_aria);
489
480
  }
490
481
 
491
482
  static VALUE
@@ -496,7 +487,7 @@ rb_hamlit_build_data(int argc, VALUE *argv, RB_UNUSED_VAR(VALUE self))
496
487
  rb_check_arity(argc, 2, UNLIMITED_ARGUMENTS);
497
488
  rb_scan_args(argc - 2, argv + 2, "*", &array);
498
489
 
499
- return hamlit_build_data(argv[0], argv[1], array, str_data());
490
+ return hamlit_build_data(argv[0], argv[1], array, str_data);
500
491
  }
501
492
 
502
493
  static VALUE
@@ -504,10 +495,10 @@ rb_hamlit_build(int argc, VALUE *argv, RB_UNUSED_VAR(VALUE self))
504
495
  {
505
496
  VALUE array;
506
497
 
507
- rb_check_arity(argc, 4, UNLIMITED_ARGUMENTS);
508
- rb_scan_args(argc - 4, argv + 4, "*", &array);
498
+ rb_check_arity(argc, 5, UNLIMITED_ARGUMENTS);
499
+ rb_scan_args(argc - 5, argv + 5, "*", &array);
509
500
 
510
- return hamlit_build(argv[0], argv[1], argv[2], argv[3], array);
501
+ return hamlit_build(argv[0], argv[1], argv[2], argv[3], argv[4], array);
511
502
  }
512
503
 
513
504
  void
@@ -533,22 +524,14 @@ Init_hamlit(void)
533
524
  id_prepend = rb_intern("prepend");
534
525
  id_tr = rb_intern("tr");
535
526
  id_uniq_bang = rb_intern("uniq!");
536
-
537
- id_aria = rb_intern("ARIA");
538
- id_data = rb_intern("DATA");
539
- id_equal = rb_intern("EQUAL");
540
- id_hyphen = rb_intern("HYPHEN");
541
- id_space = rb_intern("SPACE");
542
- id_underscore = rb_intern("UNDERSCORE");
543
-
544
- id_boolean_attributes = rb_intern("BOOLEAN_ATTRIBUTES");
545
- id_xhtml = rb_intern("xhtml");
546
-
547
- rb_const_set(mAttributeBuilder, id_aria, rb_obj_freeze(rb_str_new_cstr("aria")));
548
- rb_const_set(mAttributeBuilder, id_data, rb_obj_freeze(rb_str_new_cstr("data")));
549
- rb_const_set(mAttributeBuilder, id_equal, rb_obj_freeze(rb_str_new_cstr("=")));
550
- rb_const_set(mAttributeBuilder, id_hyphen, rb_obj_freeze(rb_str_new_cstr("-")));
551
- rb_const_set(mAttributeBuilder, id_space, rb_obj_freeze(rb_str_new_cstr(" ")));
552
- rb_const_set(mAttributeBuilder, id_underscore, rb_obj_freeze(rb_str_new_cstr("_")));
527
+ id_xhtml = rb_intern("xhtml");
528
+
529
+ // Consider using rb_interned_str() once we stop supporting Ruby 2.7.
530
+ rb_gc_register_mark_object(str_aria = rb_obj_freeze(rb_str_new_cstr("aria")));
531
+ rb_gc_register_mark_object(str_data = rb_obj_freeze(rb_str_new_cstr("data")));
532
+ rb_gc_register_mark_object(str_equal = rb_obj_freeze(rb_str_new_cstr("=")));
533
+ rb_gc_register_mark_object(str_hyphen = rb_obj_freeze(rb_str_new_cstr("-")));
534
+ rb_gc_register_mark_object(str_space = rb_obj_freeze(rb_str_new_cstr(" ")));
535
+ rb_gc_register_mark_object(str_underscore = rb_obj_freeze(rb_str_new_cstr("_")));
553
536
  }
554
537
  #endif
@@ -13,7 +13,7 @@ module Hamlit::AttributeBuilder
13
13
  # TruffleRuby does not implement `rb_ary_sort_bang`, etc.
14
14
  if /java/ === RUBY_PLATFORM || RUBY_ENGINE == 'truffleruby'
15
15
  class << self
16
- def build(escape_attrs, quote, format, object_ref, *hashes)
16
+ def build(escape_attrs, quote, format, boolean_attributes, object_ref, *hashes)
17
17
  hashes << Hamlit::ObjectRef.parse(object_ref) if object_ref
18
18
  buf = []
19
19
  hash = merge_all_attrs(hashes)
@@ -27,7 +27,7 @@ module Hamlit::AttributeBuilder
27
27
  buf << " class=#{quote}#{build_class(escape_attrs, *hash[key])}#{quote}"
28
28
  when 'data'.freeze
29
29
  buf << build_data(escape_attrs, quote, *hash[key])
30
- when *BOOLEAN_ATTRIBUTES, /\Adata-/
30
+ when *boolean_attributes, /\Adata-/
31
31
  build_boolean!(escape_attrs, quote, format, buf, key, hash[key])
32
32
  else
33
33
  buf << " #{key}=#{quote}#{escape_html(escape_attrs, hash[key].to_s)}#{quote}"
@@ -31,7 +31,10 @@ module Hamlit
31
31
  attrs = []
32
32
  attrs.unshift(node.value[:attributes].inspect) if node.value[:attributes] != {}
33
33
 
34
- args = [@escape_attrs.inspect, "#{@quote.inspect}.freeze", @format.inspect].push(node.value[:object_ref]) + attrs
34
+ args = [
35
+ @escape_attrs.inspect, "#{@quote.inspect}.freeze", @format.inspect,
36
+ '::Hamlit::AttributeBuilder::BOOLEAN_ATTRIBUTES', node.value[:object_ref],
37
+ ] + attrs
35
38
  [:html, :attrs, [:dynamic, "::Hamlit::AttributeBuilder.build(#{args.join(', ')}, #{node.value[:dynamic_attributes].to_literal})"]]
36
39
  end
37
40
 
data/lib/hamlit/cli.rb CHANGED
@@ -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
@@ -3,7 +3,7 @@ require 'rails'
3
3
 
4
4
  module Hamlit
5
5
  class Railtie < ::Rails::Railtie
6
- initializer :hamlit do |app|
6
+ initializer :hamlit, before: :load_config_initializers do |app|
7
7
  require 'hamlit/rails_template'
8
8
  end
9
9
  end
@@ -1,4 +1,4 @@
1
1
  # frozen_string_literal: true
2
2
  module Hamlit
3
- VERSION = '2.13.2'
3
+ VERSION = '2.14.4'
4
4
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: hamlit
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.13.2
4
+ version: 2.14.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Takashi Kokubun
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-12-28 00:00:00.000000000 Z
11
+ date: 2021-02-01 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: temple
@@ -376,7 +376,7 @@ homepage: https://github.com/k0kubun/hamlit
376
376
  licenses:
377
377
  - MIT
378
378
  metadata: {}
379
- post_install_message:
379
+ post_install_message:
380
380
  rdoc_options: []
381
381
  require_paths:
382
382
  - lib
@@ -391,8 +391,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
391
391
  - !ruby/object:Gem::Version
392
392
  version: '0'
393
393
  requirements: []
394
- rubygems_version: 3.1.4
395
- signing_key:
394
+ rubygems_version: 3.1.2
395
+ signing_key:
396
396
  specification_version: 4
397
397
  summary: High Performance Haml Implementation
398
398
  test_files: []