enkessler / cuke_linter

A linting tool for Cucumber
MIT License
32 stars 8 forks source link

Something goes wrong when running cuke_linter with overcommit #21

Closed pr4bh4sh closed 3 years ago

pr4bh4sh commented 3 years ago

I'm trying to run cuke_linter as part of overcommit's pre-commit hook. I'm partially successful in that. If I trigger overcommit manually everything goes as expected. However, when there are file change and overcommit is triggered by the commit action something goes wrong with parsing the feature file.

I'm not sure where does this issue belong here. However, from the stack trace, the error seems to be originating from cuke_linter's actions.

I've created https://github.com/pr4bh4sh/cuke-issue which reproduces the issue.

The steps to reproduce the issue are

  1. clone the repo, install gem with bundler and create the overcommit sign. git clone git@github.com:pr4bh4sh/cuke-issue.git && bundle install && overcommit -sign && overcommit --sign pre-commit

  2. Run the overcommit with overcommit -r, the output would be something like

    
    > overcommit -r
    Running pre-commit hooks
    Run GherkinLint.........................................[GherkinLint] FAILED
    Errors on lines you didn't modify:
    /Users/prabhash/personal/cuke-issue/features/test.feature:7 Step 'Then Some other things happen' should use 'And' instead of 'Then'

✗ One or more pre-commit hooks failed


3. Introduce a change in the feature file with `echo '' >> features/test.feature`

4. Make a commit **(Issue happens here)**
```bash
> git commit -m 'a commit'
Running pre-commit hooks
Run GherkinLint.........................................[GherkinLint] FAILED
Hook raised unexpected error
invalid field name="cuke_modeler_parsing_data"
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/protobuf-cucumber-3.10.8/lib/protobuf/message.rb:205:in `rescue in []'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/protobuf-cucumber-3.10.8/lib/protobuf/message.rb:200:in `[]'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_modeler-1.5.1/lib/cuke_modeler/adapters/gherkin_4_adapter.rb:35:in `adapt_feature!'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_modeler-1.5.1/lib/cuke_modeler/adapters/gherkin_4_adapter.rb:23:in `adapt'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_modeler-1.5.1/lib/cuke_modeler/parsing.rb:138:in `parse_text'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_modeler-1.5.1/lib/cuke_modeler/models/feature_file.rb:60:in `process_feature_file'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_modeler-1.5.1/lib/cuke_modeler/models/feature_file.rb:31:in `initialize'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_linter-1.1.0/lib/cuke_linter.rb:76:in `new'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_linter-1.1.0/lib/cuke_linter.rb:76:in `block in collect_file_path_models'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_linter-1.1.0/lib/cuke_linter.rb:71:in `collect'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_linter-1.1.0/lib/cuke_linter.rb:71:in `collect_file_path_models'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/cuke_linter-1.1.0/lib/cuke_linter.rb:57:in `lint'
/Users/prabhash/personal/cuke-issue/util/ruby_gherkin_lint.rb:8:in `run'
/Users/prabhash/personal/cuke-issue/.git-hooks/pre_commit/gherkin_lint.rb:7:in `run'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/overcommit-0.57.0/lib/overcommit/hook/base.rb:47:in `block in run_and_transform'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/overcommit-0.57.0/lib/overcommit/utils.rb:260:in `with_environment'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/overcommit-0.57.0/lib/overcommit/hook/base.rb:47:in `run_and_transform'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/overcommit-0.57.0/lib/overcommit/hook_runner.rb:161:in `run_hook'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/overcommit-0.57.0/lib/overcommit/hook_runner.rb:97:in `block in consume'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/overcommit-0.57.0/lib/overcommit/hook_runner.rb:94:in `loop'
/Users/prabhash/.rvm/gems/ruby-2.6.3/gems/overcommit-0.57.0/lib/overcommit/hook_runner.rb:94:in `consume'

✗ One or more pre-commit hooks failed
enkessler commented 3 years ago

The immediately suspicious thing is that the stack trace goes from cuke_modeler to protobuf-cucumber. Given that the versions of CukeModeler and Cucumber that you are using are from several years ago, that gem didn't even exist back then. I also don't see it in the lockfile of your sample project, so I'm curious what it is even doing in the runtime environment in the first place. Perhaps something will become more apparent when I try to recreate this locally.

enkessler commented 3 years ago

I can run your recreation just fine on my machine and no issue is present.

After looking through the code, I can with reasonable confidence say that the problem is that your environment is mixing incompatible versions of various gems in the Cucumber tech stack. That is, you are running into https://github.com/cucumber/cucumber/issues/1063. The end result is that the wrong type of object is being given back to the cuke_modeler gem when it uses Gherkin to parse the feature file. I say Gherkin instead of gherkin or cucumber-gherkin because I can't tell which gem (and any further transitive dependencies) is actually being invoked at runtime due to the linked issue.

To avoid this problem, your best bet is to either remove newer versions of Cucumber related gems from your runtime environment or to use use newer versions of cucumber-gherkin and cuke_modeler that are actually designed to handle the newer objects.

pr4bh4sh commented 3 years ago

Thanks, it worked. I initially did uninstall cucumber but not all the deps.

For someone facing the same issue(or my future self) gem uninstall $(gem list --no-versions | grep 'cucumber') than bundle install fixed the problem.

enkessler commented 3 years ago

That makes sense. No newer version of cucumber means no cucumber-gherkin which, in turn, means no namespace conflicts with the gherkin gem that cuke_modeler thought it was actually using.

Glad to hear that it worked out.