JavaScript Standard Style does not recognize Mocha - javascript

I have a Mocha test file that looks like this:
var expect = require('chai').expect
var muting = require('../muting')
describe('muting', function () {
describe('init()', function () {
it('should inject an object into twitter', function () {
var twitter = 'twitter'
muting.init(twitter)
expect(muting.twitter).to.equal(twitter)
})
})
})
When I run mocha from the CLI, it runs the test successfully.
When I run standard (the executable for JavaScript Standard Style) I get errors on Mocha's framework functions like so:
standard: Use JavaScript Standard Style (https://github.com/feross/standard)
c:\..\test\index.js:5:0: 'describe' is not defined.
c:\..\test\index.js:6:2: 'describe' is not defined.
c:\..\test\index.js:7:4: 'it' is not defined.
What's the cleanest way to make Standard not complain about these functions?

I prefer to edit my .eslintrc and add mocha to env section:
...
"env": {
"commonjs": true,
"node": true,
"mocha": true
},
...
this way my package.json file is kept clean, also vscode plugin for eslint understands it better

Actually, you don't need to list every single global variable in your package.json
You can specify environments instead like this:
"standard": {
"env": [ "mocha" ]
}
Source: Official ESLint configuration docs.

while eslint's comment configuration works great for a single file, I prefer to use standard's package.json globals configuration to do this for my projects. E.g.
{
"name": "my-package",
"version": "1.0.0",
"standard": {
"globals": [
"describe",
"context",
"before",
"beforeEach",
"after",
"afterEach",
"it",
"expect"
]
}
}

for eslint use this line on the beginning of test_file.js
/* eslint-env mocha */

You can use the same solution as for web workers
/* global describe it */
var expect = require('chai').expect
var muting = require('../muting')
describe('muting', function () {
describe('init()', function () {
it('should inject an object into twitter', function () {
var twitter = 'twitter'
muting.init(twitter)
expect(muting.twitter).to.equal(twitter)
})
})
})

As pointed out by Nick Tomlin you just need to declare globals.
I use to put it in the command line, since I have different globals for tests as for sources or different parts of the project.
For tests we should use
standard --global describe --global it test/
elsewhere in my project I want to lint code that uses jQuery so I use
standard --global $ src/client/
Bonus tip
If you are using vim with Syntastic you maybe want to add to your .vimrc
let b:syntastic_checkers = ['standard']
let g:syntastic_javascript_standard_args = "--global $ --global it --global describe"

Related

How to isolate specific ESLint errors? [duplicate]

I know you can define rules in an .eslintrc file, but what if I just want to run eslint and check for one specific rule?
E.g. $ eslint helpme.js --rule some-important-rule
I don't know if this is the best way, but I was able to get this working:
$ eslint helpme.js --no-eslintrc --env "es6" --env "node" --parser-options "{ecmaVersion: 2018}" --rule "{some-important-rule: error}"
Note: With this method (ignoring .eslintrc completeley) you still have to add some stuff from .eslintrc like your environment and parser options.
If you want to use your .eslintrc file to keep your configuration (parser, plugin settings, etc), you can use eslint-nibble with the --rule=some-important-rule flag. This will respect your normal configuration, but only show you errors from that rule. There are some other flags as well like --no-interactive if you want to run this in something like a CI environment.
Disclaimer: I'm the creator of eslint-nibble.
Expanding on #matrik answer, this doesn't require me to define all eslint config again and also shows the file name.
eslint helpme.js | egrep "react/jsx-no-literals" -B 1
Try ESLint custom formatter.
It can be used to filter part of rules, files you want to pay attention to.
And you don't need to :
Edit your ESLint config file.
Use complicate command.
DEMO for filter files contain error which rules id is prop-types:
// ./eslint-file-path-formatter.js
const fs = require('fs');
function containRules(result, targetRuleId) {
if (!result || !targetRuleId) {
return false;
}
return result.messages.some((cur) => {
// console.log(`cur?.ruleId = ${cur?.ruleId}`);
if (cur?.ruleId?.includes(targetRuleId)) {
return true;
}
});
}
module.exports = function (results, context) {
const summary = [];
results.forEach((cur) => {
if (containRules(cur, 'prop-types')) {
summary.push(`'${cur.filePath}',`);
}
});
// fs.writeFileSync('eslint-error-files.txt', summary.join('\n'));
// return 'Done Write';
return summary.join('\n');
};
Usage:
eslint . -f ./eslint-file-path-formatter.js
Then this formatter will print all files name to console.
You can also write result to local files, do whatever you want.
Simple way to see single rule output while still using .eslintrc is to use grep:
$ eslint helpme.js | egrep "(^/|some\-important\-rule$)"

Nodejs with JEST how to import using ES6 and relative path?

I want to avoid this:
const SomeMethod = require('../shared/SomeMethod')
And instead use something more modern like this:
import { SomeMethod } from '/shared'
(under the hood): the /shared directory includes an index file of course, returning the object with the SomeMethod property which is also includes to a file.
As I am using JEST, I need two things to get around: 1 is that the node installed supports ES6 imports and 2 is that JEST will be familiar with relative path - notice that I have used the **/**shared so it means - go to the src directory and start from there.
But how to achieve this?
You can achieve this using babel. According to the documentation of jest, you need to do the following
yarn add --dev babel-jest #babel/core #babel/preset-env
and then create babel.config.js at the root of your project with the following content
module.exports = {
presets: [
[
'#babel/preset-env',
{
targets: {
node: 'current',
},
},
],
],
};
You can look into the documentation for more
Here is a step by step process of the same which is addressing the same problem
In order to use absolute path for Jest add the following line in jest.config.js
module.exports = {
moduleDirectories: ['node_modules', 'src'],
...
};
here, src is considered as the root. You may need to change this one according to your folder name.
For more information you can follow this article

How do I correctly configure mocha tests with ts_transformer_keys?

I can't seem to set the custom transformer for ts-transform-keys with my mocha tests.
I’m using mocha 6.1.4
ts-node 8.3.0 https://www.npmjs.com/package/ts-node
ts-trasnformer-keys 0.3.5 https://github.com/kimamula/ts-transformer-keys
ttypescript 1.5.7 https://github.com/cevek/ttypescript
The ts-node documentation says that you cannot set a custom transformer on the CLI, only programatically. So I'm trying to use ttypescript to get around that restriction.
I've tried the following...
Note: test.ts contains the following
import { keys } from 'ts-transformer-keys';
describe("xyz"), () => {
it("123", (done) => {
keys<CustomInterface>();
});
});
Attempt 1) - Set the ts-node with an environment variable
TS_NODE_COMPILER="ttypescript" mocha test/test.ts --require ts-node/register
Then I have the following in test/tsconfig.json
{
"compilerOptions": {
"plugins": [
{ "transform": "ts-transformer-keys/transformer" }
]
}
}
This results in Uncaught TypeError: ts_transformer_keys_1.keys is not a function which indicates that the custom transformer wasn't used at compile time.
Attempt 2) Following the typescript API example from ts-transformer-keys
I added a mocha.opts file with the following
--file test/transformer-config.js
and a transformer-config.js file with the following
const ts = require('typescript');
const keysTransformer = require('ts-transformer-keys/transformer').default;
const program = ts.createProgram(['test/test.ts'], {
strict: true,
noEmitOnError: true,
target: ts.ScriptTarget.ES5
});
const transformers = {
before: [keysTransformer(program)],
after: []
};
const { emitSkipped, diagnostics } = program.emit(undefined, undefined, undefined, false, transformers);
if (emitSkipped) {
throw new Error(diagnostics.map(diagnostic => diagnostic.messageText).join('\n'));
}
Then I invoke it like this mocha test/test.ts --require ts-node/register
This results in the following error
/Users/jjohnson/Documents/OCS/hmp/git/hmp-server/server/test/ttypescript-register.js:17
throw new Error(diagnostics.map(diagnostic => diagnostic.messageText).join('\n'));
^
Error: [object Object]
[object Object]
[object Object]
at Object.<anonymous> (/Users/jjohnson/Documents/OCS/hmp/git/hmp-server/server/test/ttypescript-register.js:17:9)
at Module._compile (internal/modules/cjs/loader.js:777:30)
...
It feels like in Attempt 1 it wasn't ever calling the code that sets the custom transformer in tsconfig.json or if it was getting called the code was failing silently.
It feels like in Attempt 2 I'm creating a new instance of the typescript program and then that fails for some reason. And even if it succeeded I'm not sure that this is the right way to go about configuring things since the ts.createProgram wants a list of RootNames for the files it will transpile.
Maybe my entire approach is wrong.
All I really want is a way that in my mocha tests I can verify that the expected result type is what the method returned. And I'd like to be able to do this w/out touching too much of the source code.
you should be able to define your required module (see below) and run ts-node programmatically. In this way, you can safely use any customer transformer.
// tsnode.js
const transformer = require('ts-transformer-keys/transformer').default;
require("ts-node").register({
transformers: program => ({
before: [
transformer(program)
]
})
});
then you can run mocha with require
mocha --require './tsnode.js' --watch-extensions ts,tsx "test/**/*.{ts,tsx}
You can tell ts-node which compiler to use in tsconfig.json. This is covered in the ts-node docs. If your using transformers presumably your also using ttypescript compiler. You just need to add this:
"ts-node": {
"compiler": "ttypescript"
}

Testing internal functions in Mocha ESlint error

I'm currently developing an Nodejs application and carrying out some unit tests (I'm using Mocha, Chai and Sinon).
I ran into a little ESlint error when I exported and tested an internal function.
function _buildPayload(){
//....
}
module.exports = { _buildPayload };
Then in my test script
const {_buildPayload} = requires('./someModule')
describe('Test',function(){
it('Should work',function(){
let expected = _buildPayload();
})
})
When I write the let expected = _buildPayload(); ESlint returns the following error:
error Shouldn't be accessing private attribute '_buildPayLoad'
My question is should I change the name of my function to not represent and internal even though it is?
#philipisapain makes a good point that testing internal methods may not be necessary. If you do need to do it, you have a couple options:
Disable the rule by placing /* eslint-disable rule-name */ at the top of any test scripts that call private methods.
Disable the rule in all test scripts using a glob config in your .eslintrc, provided you're using at least ESLint v4.1.0:
"overrides": [{
"files": ["*.test.js"],
"rules": [{
"rule-name": "off"
}]
}]

why is jasmine-node not picking up my helper script?

This question is likely based in my lack of previous experience with node.js, but I was hoping jasmine-node would just let me run my jasmine specs from the command line.
TestHelper.js:
var helper_func = function() {
console.log("IN HELPER FUNC");
};
my_test.spec.js:
describe ('Example Test', function() {
it ('should use the helper function', function() {
helper_func();
expect(true).toBe(true);
});
});
Those are the only two files in the directory. Then, when I do:
jasmine-node .
I get
ReferenceError: helper_func is not defined
I'm sure the answer to this is easy, but I didn't find any super-simple intros, or anything obvious on github. Any advice or help would be greatly appreciated!
Thanks!
In node, everything is namespaced to it's js file. To make the function callable by other files, change TestHelper.js to look like this:
var helper_func = function() {
console.log("IN HELPER FUNC");
};
// exports is the "magic" variable that other files can read
exports.helper_func = helper_func;
And then change your my_test.spec.js to look like this:
// include the helpers and get a reference to it's exports variable
var helpers = require('./TestHelpers');
describe ('Example Test', function() {
it ('should use the helper function', function() {
helpers.helper_func(); // note the change here too
expect(true).toBe(true);
});
});
and, lastly, I believe jasmine-node . will run every file in the directory sequentially - but you don't need to run the helpers. Instead you could move them to a different directory (and change the ./ in the require() to the correct path), or you could just run jasmine-node *.spec.js.
you do not necessarily need to include your helper script in the spec (testing) file if you have the jasmine config as:
{
"spec_dir": "spec",
"spec_files": [
"**/*[sS]pec.js"
],
"helpers": [
"helpers/**/*.js"
],
"stopSpecOnExpectationFailure": false,
"random": false
}
Everything in the helpers/ folder will run before the Spec files. In the helpers files have something like this to include your function.
beforeAll(function(){
this.helper_func = function() {
console.log("IN HELPER FUNC");
};
});
you will then be able to make references to it in your spec files

Categories

Resources