[email protected] works smoothly on a clean project, but fails to run on mine (tests broke when i've upgraded to from [email protected]):
(function (exports, require, module, __filename, __dirname) { import {
^^^^^^
SyntaxError: Unexpected reserved word
I'm sure it's caused by some weird babel dependency, so it might be unrelated to ava. Last working state is 7d31571, if i try to upgrade to [email protected], tests are broken.
I will investigate it tomorrow...
Did you try rm -rf node_modules and npm i?
What version of Node are you using? Something tells me Babel was removed from compiling tests.
yup, still the same, btw it might be the same as #108 ?
Yep, that's my guess.
So right now there is no way to test modules directly? I mean, i have to transpile them first, and test the transpiled files?
Implicitly transpiling dependencies in 0.2.0 was a bug that was later fixed 0.3.0. Transpiling dependencies by default is both surprising and slow. I'm open to considering an option for enabling this, but it will not be by default.
what about allowing something like $ babel-node node_modules/.bin/ava ? i'm not really familiar with ava internals, so that's just an idea.
That won't work as we spawn the test files. Just use AVA 0.2.0 until we've figured out how to deal with this. Alternatively use a fork where you've removed this line.
I'm open to considering an option for enabling this, but it will not be by default.
I agree. I want to run both tests and target codes for tests with Babel. I think that is proper and as it should be.
What should the option be named?
@floatdrop Any thoughts as to how we should solve this now that #103 has landed?
@madbence you can require file with following code in tests as workaround:
// app.es5.js
require('babel/register');
require('./app');
@sindresorhus besides this workaround, not really.
We could set the execPath, when we fork a test file, to the babel-node executable instead of vanilla node.
Hm, any progress on that? Still can't use external files.
@theaqua This issue is still open, so no. @floatdrop has already provided a workaround if you can't wait.
To move this issue forward, come up with a good name for a CLI flag to enable it.
pm2 uses execInterpreter option. I think it's ok because most users will install custom interpreter (coffeescript or babel) as dependency and ava can search in local node_modules automagically.
@theaqua If I understand correctly, that is what Mocha does too.
@sindresorhus
--transpile-all|-a--compile-all|-a--compilers js:babel/register (like in mocha, istanbul, etc)@madbence I like --transpile-all.
I think --transpile-transitive is more descriptive/accurate, though.
Then again, _"transpile"_ a general term. As AVA _specifically_ transpiles using Babel, maybe _"babelify"_ would be a better word.
--transpile-transitive would be the longest command line flag I've seen in a while.
@Qix- -tt for short
Per GNU specs on arguments, -tt would be supplying the short-form argument -t twice. Doesn't make sense. --transpile-all would make the most sense whilst still being correct. --compile-all isn't _technically_ correct but would still probably be easier for people to type.
btw what's the rationale behind this behavior (ava transpiles tests only)? it's just slow?
It is more than just "ava transpiles tests only".
It is that ava allows you to write tests in ES2015 with zero impact on your production environment.
By zero impact, I mean no transpilation an no polyfills. (IMO polyfills are the sneakier harder to detect bug).
For example, we make sure Promise is available inside your tests, without impacting it's availability in production code.
// Always works in tests. Only works in production in Node >= 0.12
new Promise(...)
Trickier still is a prototype polyfill. Something like String.prototype.includes(). If Babel actually modifies the prototype, your test suite no longer protects you against mistakenly using str.includes() in production. Users will report errors in Node 0.12 that you can't write a failing test case for (because it has been polyfilled even in your production environment).
AVA uses the runtime plugin to provide polyfill aliasing. An example of how that works is here. This means that:
".... some string ....".includes()
Will work in your tests on any platform. But will throw in production code on platforms that do not support str.includes()
@jamestalmage very good points. However, one of the things to consider is the viability of backwards compatibility in Node. NPM thrives under the idea of progressive code reform. Node proper is no exception. I think one of the motivations behind AVA is that it is, indeed, very progressive and puts into low-priority the considerations it makes towards older versions of Node.
hmm, i still don't get the point... why should i write my tests in es2015 if i can't write my lib in es2015? if i want to support some older node versions, i know that i _have_ to publish a transpiled version of my lib (so i should test the transpiled code, which is not the default behavior right now). but maybe i'm just missing something about how one should develop modules in es2015...
Good points, @jamestalmage.
My situation is this: I am writing an Express application and using a Babel require hook in an entry-point to transpile my entire app (example.)
I have seen @floatdrop's solution but it would be tedious for me to use, as I require many test files.
@Whoaa512 has the same problem as me. Fair play to him, he actually sent a pr. It got turned down but now it _sounds_ like @sindresorhus is considering it...?
@madbence you don't have to write your lib in ES2015. The fact AVA allows you to write your tests in ES2015 is just a functional gain.
Because your tests are not used in the wild. Your production code might be. The idea is to let you use ES2015 for test code, even if you are not allowed to use it for production (because you want to support old Node without transpilation).
Another big issue with providing transpiled dependencies is, again, polyfills. For your code to run standalone, babel needs to include the polyfills in the output. This is not good if you want a small reusable library (you don't want Node loading up 10 copies of a string.includes() polyfill)
By the way, I really like how Mocha allows you to plugin transpilers like Babel:
mocha ./test --recursive --compilers js:babel-core/register
If Mocha can make Babel work in source files (despite all the valid concerns you raise, @jamestalmage), I am sure it can work for AVA, as well. Whether or not this is something the maintainers/community at large want implementing is another matter!
I don't think a cli-hook has been ruled out.
In the mean-time, require('babel-core/register') at the top of every test file should work.
It doesn't seem to work for me. I added require('babel-core/register') to the top of a test file, then ran ava ./example/test-file.js, and it spat out:
(function (exports, require, module, __filename, __dirname) { import fetch from 'isomorphic-fetch';
^^^^^^
SyntaxError: Unexpected reserved word
Am I missing something? For reference I'm writing my entire browser-based app in ES2015, and I just want a testing solution that'll efficiently transpile _everything_. Mocha handles this really smoothly as @alexbooker noted. I wouldn't _mind_ adding the babel registration to the top of my tests if it would work, although it wouldn't be optimal.
It's nice that ava lets you write ES2015 tests on non-ES2015 projects, but if it won't work on ES2015 projects it seems like it's going to be pretty marginalised. :)
@codyhatch, adding require('babel-core/register') at the top of the file will enabled it for further requires but not for the file in which it was required.
So let's assume I have a project like:
src/
app.js
modules/
module1.js
module2.js
...
test/
app.spec.js
module1.spec.js
module2.spec.js
...
So the workaround is to create a new module2.wrapper.js for every single test, which does nothing but register babel and then import the actual test? That...seems to work. But wow, that's a really ugly solution for a large project. :(
Thanks though.
Should we expect different behavior for those writing tests for a library (used in many unknown environments) and those writing tests for an application (used in a single known environment e.g. electron)?
I'm just thinking of my scenario where I want to write tests for an application that is run in electron. I'm using electron-compile and I have full control over the environment my es6 application is running in. Or is AVA not intended for this scenario?
A repo is worth a thousand comments:
https://github.com/jamestalmage/__ava_with_babel_for_production
// @codyhatch @BarryThePenguin @alexbooker @madbence @theaqua
@jamestalmage welp! I'm sold
Reading back through, it wasn't clear to me that you can
import test from 'ava';
import 'babel/register';
// now import ES6
import app from '../src/app';
test('test app', t => {
t.ok(app);
t.end();
});
I'm happy with this as a solution
+1 for a --compilers (or perhaps --preprocessors) flag that lets you use custom register hooks, like mocha does (as @alexbooker alluded to) with a pretty clean syntax. Other test runners (Karma, babel-tape-runner) do similar things.
Including import babel-core/register at the top of every test file is clunky enough, and gets much worse if you want to write a custom compiler (e.g. like this, which is necessary to test JS that uses CSS modules). You should be able to specify this when invoking AVA.
import babel-core/register is a really good, simple workaround until this feature lands. @sindresorhus what do you think about putting this in the README until it's officially addressed? (I wouldn't mind submitting a PR for it)
@sparty02 Sure, PR welcome.
Hi!
import 'babel-core/register' and import 'babel-register' are not working for me.
You need to install as dependencies of your own project to use outside of tests
Already done that @jamestalmage
It was purely a problem with babel presets/plugins/config settings, nvm, thanks a lot
EDIT: Whoops... Not the issue I thought it was. Sorry!
:)
for anybody trying to make import 'babel-core/register'; work in AVA, try installing babel-core 5.x.x, that did the trick for me, 6 doesn't work for some reason (you probably need have properly configured .babelrc in your directory or something)
@Hurtak: Yes. Babel 6 doesn't do anything by default.
This issue is solved for me by adding --require 'babel-register' (Babel 6) with a .babelrc file:
{
"presets": ["es2015", "stage-2"]
}
If you're interested, here's a migration from Mocha to AVA in a small library: https://github.com/kentcdodds/starwars-names/pull/12/files?w=1
edit the reason I bring it up is because it supports ES6 with Babel 6 in my source without having to import babel-register. Thought you'd all be interested.
Cool!
Your use of the --require flag is spot on for what we intended. #407 should make the experience even better.
We would value any feedback on pain points you encountered during the transition.
Cool, I added a comment about that. I prefer to use config to avoid polluting the package.json keyspace :-) (It's also technically the recommended way to do what is being done).
Not really any pain points. The only thing that I would say is the assertions are pretty limiting. I prefer the declarative syntax of something like Chai. But I expect that the small surface area of the API is intentional. I ended up bringing in another utility library to make testing a little more declarative though.
This is what I use in my package.json file:
"scripts": {
"test": "ava --require babel-register --require babel-polyfill '**/*.test.js'"
},
"dependencies": {
"babel-core": "^6.4.0",
"babel-polyfill": "^6.3.14",
"babel-preset-es2015": "^6.3.13",
"babel-preset-stage-0": "^6.3.13",
"babel-register": "^6.3.13"
},
"devDependencies": {
"ava": "^0.9.2"
},
"babel": {
"presets": [
"es2015",
"stage-0"
],
},
Had to dig around this issue this morning to get it working with [email protected] in order to run on travis with [email protected] and [email protected]
I had to use the ignore babel config property that somehow went unmentioned in this whole thread, here is the actual snippet of code that I dropped at the top of my test file:
require('babel-core/register')({
ignore: false
});
_TIP: ignore can also be a function that receives a filename and returns false, this way you can filter only the files that need the transpiling, I ended up using it and test times were a lot better_
@sindresorhus @vdemedes @jamestalmage is there anything we want to improve here beyond the existing --require support? If not I'll close and remove the link to this issue from the README.
Not that I'm aware of.
Sure, we can close it for now.
@Whoaa512 dude you rule
Most helpful comment
Had to dig around this issue this morning to get it working with [email protected] in order to run on travis with [email protected] and [email protected]
I had to use the
ignorebabel config property that somehow went unmentioned in this whole thread, here is the actual snippet of code that I dropped at the top of my test file:_TIP:
ignorecan also be a function that receives a filename and returnsfalse, this way you can filter only the files that need the transpiling, I ended up using it and test times were a lot better_