r7kamura / slimi

Yet another implementation for Slim template language.
MIT License
13 stars 2 forks source link

MalformedIndentationError is raised when a blank line containing spaces is present #14

Open zoras opened 1 year ago

zoras commented 1 year ago
$ bundle exec rubocop --parallel
undefined method `[]' for nil:NilClass
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:66:in `dispatcher'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:49:in `compile'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:7:in `block in on_multi'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:7:in `each'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:7:in `on_multi'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:114:in `dispatcher'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:49:in `compile'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/slimi-0.7.4/lib/slimi/filters/base.rb:45:in `on_slimi_text'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:80:in `dispatcher'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:49:in `compile'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/html/dispatcher.rb:27:in `on_html_tag'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:97:in `dispatcher'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:49:in `compile'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:7:in `block in on_multi'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:7:in `each'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:7:in `on_multi'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:114:in `dispatcher'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:49:in `compile'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/temple-0.8.0/lib/temple/mixins/dispatcher.rb:45:in `call'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-slim-0.2.2/lib/rubocop/slim/ruby_extractor.rb:46:in `ast'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-slim-0.2.2/lib/rubocop/slim/ruby_extractor.rb:73:in `ruby_ranges'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-slim-0.2.2/lib/rubocop/slim/ruby_extractor.rb:58:in `ruby_clips'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-slim-0.2.2/lib/rubocop/slim/ruby_extractor.rb:27:in `call'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-slim-0.2.2/lib/rubocop/slim/ruby_extractor.rb:14:in `call'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:359:in `block in extract_ruby_sources'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:358:in `each'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:358:in `find'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:358:in `extract_ruby_sources'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:343:in `inspect_file'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:287:in `block in do_inspection_loop'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:321:in `block in iterate_until_no_changes'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:314:in `loop'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:314:in `iterate_until_no_changes'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:283:in `do_inspection_loop'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:164:in `block in file_offenses'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:189:in `file_offense_cache'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:163:in `file_offenses'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:99:in `block in warm_cache'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:587:in `call_with_index'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:557:in `process_incoming_jobs'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:537:in `block in worker'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:528:in `fork'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:528:in `worker'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:519:in `block in create_workers'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:518:in `each'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:518:in `each_with_index'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:518:in `create_workers'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:457:in `work_in_processes'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:294:in `map'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/parallel-1.22.1/lib/parallel.rb:238:in `each'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:99:in `warm_cache'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/runner.rb:72:in `run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli/command/execute_runner.rb:26:in `block in execute_runner'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli/command/execute_runner.rb:52:in `with_redirect'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli/command/execute_runner.rb:25:in `execute_runner'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli/command/execute_runner.rb:17:in `run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli/command.rb:11:in `run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli/environment.rb:18:in `run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli.rb:118:in `run_command'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli.rb:125:in `execute_runners'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli.rb:51:in `block in run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli.rb:77:in `profile_if_needed'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/lib/rubocop/cli.rb:43:in `run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/exe/rubocop:19:in `block in <top (required)>'
~/.asdf/installs/ruby/2.7.5/lib/ruby/2.7.0/benchmark.rb:308:in `realtime'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/rubocop-1.57.1/exe/rubocop:19:in `<top (required)>'
~/.asdf/installs/ruby/2.7.5/bin/rubocop:25:in `load'
~/.asdf/installs/ruby/2.7.5/bin/rubocop:25:in `<top (required)>'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/cli/exec.rb:58:in `load'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/cli/exec.rb:58:in `kernel_load'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/cli/exec.rb:23:in `run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/cli.rb:486:in `exec'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/vendor/thor/lib/thor/command.rb:27:in `run'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/vendor/thor/lib/thor/invocation.rb:127:in `invoke_command'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/vendor/thor/lib/thor.rb:392:in `dispatch'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/cli.rb:31:in `dispatch'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/vendor/thor/lib/thor/base.rb:485:in `start'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/cli.rb:25:in `start'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/exe/bundle:48:in `block in <top (required)>'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/lib/bundler/friendly_errors.rb:120:in `with_friendly_errors'
~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/bundler-2.3.22/exe/bundle:36:in `<top (required)>'
~/.asdf/installs/ruby/2.7.5/bin/bundle:25:in `load'
~/.asdf/installs/ruby/2.7.5/bin/bundle:25:in `<main>'
r7kamura commented 1 year ago

Thanks @zoras for reporting.

Is it correct that you succeed in non-parallel mode, but fail in parallel mode? There seems to be a problem parsing a particular Slim template, so could you please tell me the contents of that template so I can find the cause?

I think this is probably the same issue as the one you posted just before:

zoras commented 1 year ago

Is it correct that you succeed in non-parallel mode, but fail in parallel mode? No, when I run in non-parallel mode I get errors but it fails without error in parallel mode.

This is slim file with error

~/.asdf/installs/ruby/2.7.5/lib/ruby/gems/2.7.0/gems/slimi-0.7.4/lib/slimi/parser.rb:571:in `syntax_error!': MalformedIndentationError at _file.slim:23:9 (Slimi::Errors::MalformedIndentationError)
        i.fa-circle
r7kamura commented 1 year ago

Okay, so it seems there are two problems.

One is that when an exception occurs in the parser inside RuboCop, the exception is not reported properly when running in parallel mode. This is a problem that should be improved on the RuboCop side.

The other is either a problem with the slimi parser or with the way the slim template is written. I see that the exception is that there is a problem with indentation.

For example, if you have written a Slim template with wrong indentation like the following, you will get an exception.

a
    b
  i.fa-circle
$ cat example.slim | slimi parse
/home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:571:in `syntax_error!': MalformedIndentationError at (__TEMPLATE__):3:3 (Slimi::Errors::MalformedIndentationError)
  i.fa-circle
  ^
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:105:in `parse_indent'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:62:in `parse_block'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:53:in `call'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/cli.rb:25:in `parse'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor/command.rb:27:in `run'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor/invocation.rb:127:in `invoke_command'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor.rb:392:in `dispatch'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor/base.rb:485:in `start'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/exe/slimi:7:in `<top (required)>'
        from /home/r7kamura/.rbenv/versions/3.1.3/bin/slimi:25:in `load'
        from /home/r7kamura/.rbenv/versions/3.1.3/bin/slimi:25:in `<main>

What is the code before and after the line where the exception is reported?

zoras commented 1 year ago

What is the code before and after the line where the exception is reported?

      = link_to url_for([:a, :b, file]), class: 'class', method: :post, 
                title: 'Awesome Title' do
        i.fa-circle
r7kamura commented 1 year ago

Hmmm...thanks, I'm pretty close to identifying the cause 👍

I thought this whitespace in the last line was incorrect for Slim syntax, but I see that it is successfully parsed in slimrb and fails in slimi:

$ cat example.slim | slimrb --compile
_buf = ''.dup; _slim_controls1 = link_to url_for([:a, :b, file]), class: 'class', method: :post,
title: 'Awesome Title' do; _slim_controls2 = ''.dup; 
; _slim_controls2 << ("<i class=\"fa-circle\"></i>".freeze); 
; 
; _slim_controls2; end; _buf << ((::Temple::Utils.escape_html((_slim_controls1))).to_s); _buf
$ cat example.slim | slimi compile
/home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:571:in `syntax_error!': MalformedIndentationError at (__TEMPLATE__):3:9 (Slimi::Errors::MalformedIndentationError)
        i.fa-circle
        ^
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:105:in `parse_indent'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:62:in `parse_block'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/parser.rb:53:in `call'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/temple-0.10.3/lib/temple/engine.rb:51:in `block in call'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/temple-0.10.3/lib/temple/engine.rb:51:in `each'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/temple-0.10.3/lib/temple/engine.rb:51:in `inject'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/temple-0.10.3/lib/temple/engine.rb:51:in `call'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/lib/slimi/cli.rb:11:in `compile'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor/command.rb:27:in `run'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor/invocation.rb:127:in `invoke_command'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor.rb:392:in `dispatch'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/thor-1.2.2/lib/thor/base.rb:485:in `start'
        from /home/r7kamura/.rbenv/versions/3.1.3/lib/ruby/gems/3.1.0/gems/slimi-0.7.4/exe/slimi:7:in `<top (required)>'
        from /home/r7kamura/.rbenv/versions/3.1.3/bin/slimi:25:in `load'
        from /home/r7kamura/.rbenv/versions/3.1.3/bin/slimi:25:in `<main>'

It seems to me that this is an Issue that should be taken up by slimi, the template parser, so I will transfer this Issue to that repository.

r7kamura commented 1 year ago

Adding a conditional branch here that does not raise an exception if it is a blank line (i.e., the next character is a newline) might resolve this issue:

https://github.com/r7kamura/slimi/blob/a910faa96b673cf0b41361fc21bd99b9df1198ba/lib/slimi/parser.rb#L105