Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use new messages without protobuf dependencies, and Markdown support. #1645

Merged
merged 22 commits into from
May 24, 2021
Merged
Show file tree
Hide file tree
Changes from 19 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 29 additions & 8 deletions compatibility/cck_spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,17 @@ import { config, expect, use } from 'chai'
import chaiExclude from 'chai-exclude'
import glob from 'glob'
import fs from 'fs'
import ndjsonParse from 'ndjson-parse'
import path from 'path'
import { PassThrough } from 'stream'
import { Cli } from '../lib'
import { PassThrough, pipeline, Writable } from 'stream'
import { Cli } from '../src'
import toString from 'stream-to-string'
import { doesHaveValue, doesNotHaveValue } from '../src/value_checker'
import { normalizeMessageOutput } from '../features/support/formatter_output_helpers'
import * as messages from '@cucumber/messages'
import * as messageStreams from '@cucumber/message-streams'
import util from 'util'

const asyncPipeline = util.promisify(pipeline)
const PROJECT_PATH = path.join(__dirname, '..')
const CCK_FEATURES_PATH = 'node_modules/@cucumber/compatibility-kit/features'
const CCK_IMPLEMENTATIONS_PATH = 'compatibility/features'
Expand All @@ -20,13 +23,15 @@ use(chaiExclude)

describe('Cucumber Compatibility Kit', () => {
glob.sync(`${CCK_FEATURES_PATH}/**/*.ndjson`).forEach((fixturePath) => {
const suiteName = /^.+\/(.+)\.ndjson$/.exec(fixturePath)[1]
const match = /^.+\/(.+)(\.md|\.feature)\.ndjson$/.exec(fixturePath)
const suiteName = match[1]
const extension = match[2]
it(`passes the cck suite for '${suiteName}'`, async () => {
const args = [
'node',
path.join(PROJECT_PATH, 'bin', 'cucumber-js'),
].concat([
`${CCK_FEATURES_PATH}/${suiteName}/${suiteName}.feature`,
`${CCK_FEATURES_PATH}/${suiteName}/${suiteName}${extension}`,
'--require',
`${CCK_IMPLEMENTATIONS_PATH}/${suiteName}/${suiteName}.ts`,
'--profile',
Expand All @@ -45,10 +50,26 @@ describe('Cucumber Compatibility Kit', () => {
stdout.end()

const rawOutput = await toString(stdout)
const actualMessages = normalize(ndjsonParse(rawOutput))
const expectedMessages = ndjsonParse(
fs.readFileSync(fixturePath, { encoding: 'utf-8' })
const actualMessages = normalize(
rawOutput
.split('\n')
.filter((line) => line.trim() !== '')
.map((line) => JSON.parse(line))
)

const expectedMessages: messages.Envelope[] = []
await asyncPipeline(
fs.createReadStream(fixturePath, { encoding: 'utf-8' }),
new messageStreams.NdjsonToMessageStream(),
new Writable({
objectMode: true,
write(envelope: messages.Envelope, _: BufferEncoding, callback) {
expectedMessages.push(envelope)
callback()
},
})
)

expect(actualMessages)
.excludingEvery([
'meta',
Expand Down
2 changes: 1 addition & 1 deletion compatibility/features/attachments/attachments.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Before, When, World } from '../../..'
import { Before, When, World } from '../../../src'
import { ReadableStreamBuffer } from 'stream-buffers'
import fs from 'fs'
import path from 'path'
Expand Down
2 changes: 1 addition & 1 deletion compatibility/features/data-tables/data-tables.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { When, Then, DataTable } from '../../..'
import { When, Then, DataTable } from '../../../src'
import { expect } from 'chai'

When(
Expand Down
2 changes: 1 addition & 1 deletion compatibility/features/examples-tables/examples-tables.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import assert from 'assert'
import { Given, When, Then } from '../../..'
import { Given, When, Then } from '../../../src'

Given('there are {int} cucumbers', function (this: any, initialCount: number) {
this.count = initialCount
Expand Down
21 changes: 20 additions & 1 deletion compatibility/features/hooks/hooks.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
import { When, Before, After } from '../../..'
import { When, Before, After, World } from '../../../src'
import fs from 'fs'
import path from 'path'

Before(function () {
// no-op
Expand All @@ -19,3 +21,20 @@ After(function () {
After('@some-tag or @some-other-tag', function () {
throw new Error('Exception in conditional hook')
})

After('@with-attachment', async function (this: World) {
await this.attach(
fs.createReadStream(
path.join(
process.cwd(),
'node_modules',
'@cucumber',
'compatibility-kit',
'features',
'hooks',
'cucumber.svg'
)
),
'image/svg+xml'
)
})
6 changes: 6 additions & 0 deletions compatibility/features/markdown/markdown.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import assert from 'assert'
import { Given } from '../../../src'

Given('I have {int} cukes in my belly', function (cukeCount: number) {
assert(cukeCount)
})
2 changes: 1 addition & 1 deletion compatibility/features/minimal/minimal.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import assert from 'assert'
import { Given } from '../../..'
import { Given } from '../../../src'

Given('I have {int} cukes in my belly', function (cukeCount: number) {
assert(cukeCount)
Expand Down
2 changes: 1 addition & 1 deletion compatibility/features/parameter-types/parameter-types.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Given, defineParameterType } from '../../..'
import { Given, defineParameterType } from '../../../src'
import { expect } from 'chai'

class Flight {
Expand Down
2 changes: 1 addition & 1 deletion compatibility/features/rules/rules.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import assert from 'assert'
import { Given, When, Then } from '../../..'
import { Given, When, Then } from '../../../src'

Given(
'there are {int} {float} coins inside',
Expand Down
2 changes: 1 addition & 1 deletion compatibility/features/stack-traces/stack-traces.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { When } from '../../..'
import { When } from '../../../src'

When('a step throws an exception', function () {
throw new Error('BOOM')
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Given } from '../../..'
import { Given } from '../../../src'

// eslint-disable-next-line @typescript-eslint/no-unused-vars
Given('{airport} is closed because of a strike', function (airport: any) {
Expand Down
44 changes: 0 additions & 44 deletions features/cli.feature

This file was deleted.

47 changes: 47 additions & 0 deletions features/cli.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
# Command line interface
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should the extension .feature.md be for MDG files?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure. What are the benefits of enforcing that extension?

Copy link
Contributor

@davidjgoss davidjgoss May 19, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

From the discussion the other day it was that:

  • We'd avoid collecting Markdown files that weren't intended as specs for Cucumber e.g. READMEs or whatever
  • Tools like IDEs could use this convention to look for steps in .feature.md files and offer completion and quick-run features like they do for feature files

Users could always specify the glob differently themselves, as many do.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For a human, from just reading the file name, we know that this should be an executable spec in addition of some documentation

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's a good point. IIRC, @mpkorstanje also suggested that using .feature.md could protect against accidentally picking up Markdown files without any Gherkin in it.

I'll change it.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed - it's looking for .feature.md by default now

In order to run cucumber in different contexts
As a person who wants to run features
I want to run Cucumber on the command line

## Scenario: run feature with non-default step definitions file location specified (-r option)

* Given a file named "features/a.feature" with:
```gherkin
Feature: some feature
Scenario:
When a step is passing
```
* And a file named "step_definitions/cucumber_steps.js" with:
```javascript
const {When} = require('@cucumber/cucumber')

When(/^a step is passing$/, function() {})
```
* When I run cucumber-js with `-r step_definitions/cucumber_steps.js`

## Scenario: run feature with step definitions in required directory (-r option)

* Given a file named "features/a.feature" with:
```gherkin
Feature: some feature
Scenario:
When a step is passing
```
* And a file named "step_definitions/cucumber_steps.js" with:
```javascript
const {When} = require('@cucumber/cucumber')

When(/^a step is passing$/, function() {});
```
* When I run cucumber-js with `-r step_definitions`

`@spawn`
# Scenario: display Cucumber version

* When I run cucumber-js with `--version`
* Then I see the version of Cucumber

`@spawn`
# Scenario: display help
* When I run cucumber-js with `--help`
* Then I see the help text for Cucumber
Loading