diff --git a/CHANGELOG.md b/CHANGELOG.md index 8c54f24c..085a694f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,9 @@ The format is based on [Keep a Changelog](http://keepachangelog.com/) and this project adheres to [Semantic Versioning](http://semver.org/). ## [Unreleased] +### Added +- (Javascript) Support for compiled cjs style step definitions ([#222](https://github.com/cucumber/language-service/pull/222)) + ### Fixed - Parameter highlighting for scenario outline steps with leading spaces ([#219](https://github.com/cucumber/language-service/pull/219)) - (Ruby) Support `And` and `But` step definition annotations ([#211](https://github.com/cucumber/language-service/pull/211)) diff --git a/src/language/javascriptLanguage.ts b/src/language/javascriptLanguage.ts index 62a575d9..da2a23d7 100644 --- a/src/language/javascriptLanguage.ts +++ b/src/language/javascriptLanguage.ts @@ -3,6 +3,45 @@ import { Language } from './types.js' export const javascriptLanguage: Language = { ...tsxLanguage, + defineStepDefinitionQueries: [ + ...tsxLanguage.defineStepDefinitionQueries, + // Compiled cjs step definitions of the format: + // (0, some_cucumber_import.Given)("step pattern here", function...) + `(call_expression + function: (parenthesized_expression + (sequence_expression + (member_expression + property: (property_identifier) @function-name + ) + ) + ) + arguments: (arguments + [ + (string) @expression + (regex) @expression + (template_string) @expression + ] + ) + (#match? @function-name "Given|When|Then") + ) @root`, + // Compiled cjs step definitions of the format: + // (0, Given)("step pattern here", function...) + `(call_expression + function: (parenthesized_expression + (sequence_expression + (identifier) @function-name + ) + ) + arguments: (arguments + [ + (string) @expression + (regex) @expression + (template_string) @expression + ] + ) + (#match? @function-name "Given|When|Then") + ) @root`, + ], defaultSnippetTemplate: ` {{ keyword }}('{{ expression }}', ({{ #parameters }}{{ #seenParameter }}, {{ /seenParameter }}{{ name }}{{ /parameters }}) => { // {{ blurb }} diff --git a/test/language/ExpressionBuilder.test.ts b/test/language/ExpressionBuilder.test.ts index 73766f6f..a61f3cd8 100644 --- a/test/language/ExpressionBuilder.test.ts +++ b/test/language/ExpressionBuilder.test.ts @@ -87,6 +87,7 @@ function defineContract(makeParserAdapter: () => ParserAdapter) { 'a {planet}', /^a regexp$/, "the bee's knees", + ...(languageName === 'javascript' ? ['a compiled format'] : []), ]) assert.deepStrictEqual(errors, [ 'There is already a parameter type with name int', diff --git a/test/language/testdata/javascript/StepDefinitions.js b/test/language/testdata/javascript/StepDefinitions.js index 34dc08bc..d70f816a 100644 --- a/test/language/testdata/javascript/StepDefinitions.js +++ b/test/language/testdata/javascript/StepDefinitions.js @@ -1,4 +1,4 @@ -import { Given } from '@cucumber/cucumber' +import cucumber, { Given } from '@cucumber/cucumber' import assert from 'assert' import React from 'react' @@ -24,6 +24,10 @@ Given('an {undefined-parameter}', async function (date) { assert(date) }) -Given("the bee's knees", async function () { +;(0, Given)("the bee's knees", async function () { + assert(true) +}) + +;(0, cucumber.Given)('a compiled format', async function () { assert(true) })