Last active
May 25, 2021 10:17
-
-
Save jbpros/8414fc60f4fd072c12f3 to your computer and use it in GitHub Desktop.
Cucumber.js step definition transforms
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# features/my.feature | |
Feature: | |
Scenario: cukes | |
Given I have 10 cucumbers in my BaG | |
Given I don't have 20 cucumbers in my bAg | |
Given I have 98775655 cucumbers in my bag |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// features/step_definitions/stepdefs.js | |
var transform = require('./support/transform.js'); | |
module.exports = function () { | |
this.Transform(/^(\d+)$/, function (matches) { return parseInt(matches[0]); }); | |
this.Transform(/^(have|don't have)$/, function (matches) { return matches[0] == 'have'; }); | |
this.Transform(/^([bB][aA][gG])$/, function () { return 'bag'; }); | |
this.Given(/^I (have|don't have) (\d+) cucumbers in my (.*)$/, function (has, count, where) { | |
console.log('Given...', has, typeof count, where) | |
}); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// features/support/transform.js | |
var transforms = []; | |
function cast(value) { | |
for (var i = 0; i < transforms.length; i++) { | |
var transform = transforms[i]; | |
var matches = transform.pattern.exec(value); | |
if (matches) { | |
return transform.fn(matches); | |
} | |
} | |
return value; | |
} | |
function t(fn) { | |
var args = []; | |
var body = 'var args = [];'; | |
for (var i = 0; i < fn.length; i++) { | |
args.push('arg' + i); | |
body += 'args.push(this.cast(arg' + i + '));\n'; | |
} | |
body += 'return this.fn.apply(this, args);'; | |
var transformedFn = Function.apply(null, args.concat([body])).bind({fn: fn, cast: cast}); | |
return transformedFn; | |
} | |
module.exports = function () { | |
var _defineStep = this.defineStep; | |
this.defineStep = function (pattern, fn) { | |
_defineStep(pattern, t(fn)); | |
}; | |
this.Given = this.When = this.Then = this.defineStep; | |
this.Transform = function (pattern, fn) { | |
transforms.push({ pattern: pattern, fn: fn }); | |
}; | |
} |
@robsquires - your solution was quite close, but you should do something like that:
Function.apply(null, args.concat([body])).bind(Object.assign({}, new this.World(), {fn: fn, cast: cast})
And just make sure that t
function is called with the same scope from exported function. For example using ES6 you can do something like that:
this.defineStep = (pattern, fn) => {
_defineStep(pattern, t.call(this, fn));
};
@pittgoose I also had same issue as you and to fix it I required transforms inside module.exports
function, i.e.:
module.exports = function () {
require('./support/transform').call(this);
this.Transform(/^(\d+)$/, function (matches) {
return parseInt(matches[0], 10);
});
}
I know maybe it's late for you guys, but I got exactly same problem, so I would like to help others that will fall into same issues here.
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I'm trying to implement this, but I keep getting an error which states: Error: TypeError: this.Transform is not a function.
Feature file:
Step file:
transform.js