Integrating javascripts unit tests code coverage in MSBuild - javascript

I am using Jasmine and Karma for writing unit tests and code coverage. I have created the tasks using Gulp and running them through task runner explorer in VS 2015 update 3.
var gulp = require("gulp");
var Server = require('karma').Server;
var remapIstanbul = require('remap-istanbul/lib/gulpRemapIstanbul');
gulp.task('unit-tests', function (done) {
new Server({
configFile: __dirname + '/karma.conf.js'
}, done).start();
});
gulp.task('code-coverage', function () {
return gulp.src('_reports/coverage-javascript.json')
.pipe(remapIstanbul({
reports: {
'json': '_reports/coverage-typescript.json',
'html': '_reports/html-report'
}
}));
});
I want to read the generated html results file, i.e. from _reports/html-report/index.html file during Gated Builds or Nightly builds. I want to use this code coverage to perform certain actions like stopping the build if code coverage is below 80% or when a test failed.
How can I do that?

I have implemented one solution which fails MSBuild whenever any Unit Test failed. Basically I wrote a Custom Target in my project.csproj file which runs after 'CompileTypeScript' target.
<PropertyGroup>
<CompileDependsOn>
$(CompileDependsOn);
GulpBuild;
</CompileDependsOn>
</PropertyGroup>
<Target Name="GulpBuild" DependsOnTargets="CompileTypeScript">
<Exec Command="./node_modules/.bin/gulp task-name" />
</Target>
This task will run after Visual studio compiles TS to JS. In build server 'Path' variable is not set for 'gulp', that's why passing the command through node_modules .bin folder.

Related

Generate a local HTML file with PUG (npm / gulp)

How to create a HTML file with the same name as my pug file each time I save using gulp?
All the docs on https://pugjs.org/ explain how to return pug in console...
You need task runner or module bundler for that. So choose one -grunt/gulp/webpack. Consider webpack as newest one and width best functionality.
Here an example width gulp as moust easy to understand from my point of view.
First install npm packages for compiling pug and watch for changes - npm install --save gulp-pug gulp-watch.
Then create and config your gulpfile.js.
First import an npm modules
var pug = require('gulp-pug');
var watch = require('gulp-watch');
Then create compiling task
gulp.task('pug',function() {
return gulp.src('PATH_TO_TEMPLATES/*.jade')
.pipe(pug({
doctype: 'html',
pretty: false
}))
.pipe(gulp.dest('./src/main/webapp/'));
});
And then create watcher
gulp.task('watch', function () {
return watch('PATH_TO_TEMPLATES/*.jade', { ignoreInitial: false })
.pipe(gulp.dest('pug'));
});
And run gulp-watch from you console.
Here an example width gulp 4.0
install npm packages for compiling pug/jade by following command
npm install --save gulp-pug .
create script with name gulpfile.js
//gulpfile.js
var gulp = require("gulp"), pug = require('gulp-pug');
function pugToHtml(){
return gulp.src('src')
.pipe(pug({
pretty: true
}))
.pipe(gulp.dest('dest'));
}
exports.pugToHtml = pugToHtml;
We can run the above code using the following command in your file directory:
gulp pugToHtml
You can now do the same without requiring gulp-watch as well.
Require module:
var pug = require('gulp-pug');
Task example:
//create task
gulp.task('pug', function buildHTML(){
gulp.src('src/pre/*.pug')
.pipe(pug())
.pipe(gulp.dest('src/post'));
});
Watch:
//pug serve
gulp.task('watch', ['pug'], function() {
gulp.watch(['src/pug-pre/*.pug'], ['pug']);
});
You can then run gulp watch. You can also set watch to the default task so you only have to write gulp in Terminal, if you are not automating anything else:
// default task
gulp.task('default', ['watch']);

UNKOWN error thrown when compiling typescript using Gulp in VS2015

I have installed Visual Studio 2015 (with no other previous versions) on a new laptop and have pulled down the source for our MVC web app. We have a gulp file with tasks to compile our less and typescript.
When running this task ...
cmd.exe /c gulp -b "C:\Code\Trunk\MyProj\MyProj.Web" --color --gulpfile "C:\Code\Trunk\MyProj\MyProj.Web\Gulpfile.js" typescript
... I get the following error:
[09:43:16] Using gulpfile C:\Code\Trunk\MyProj\MyProj.Web\Gulpfile.js
[09:43:16] Starting 'typescript'...
[09:43:34] Plumber found unhandled error:
Error: UNKNOWN, open 'C:\Code\Trunk\MyProj\MyProj.Web\app\allergy\main.js'
Process terminated with code 0.
Here is the task in the gulp file (with other parts removed for brevity):
var gulp = require("gulp");
var plumber = require("gulp-plumber");
var sourcemaps = require("gulp-sourcemaps");
var typescript = require("gulp-typescript");
var merge = require("merge2");
var paths = {
typescript: {
globpatterns: {
all: "./Scripts/**/*.ts",
excludedefinitions: "!./Scripts/**/*.d.ts"
}
}
};
gulp.task("typescript", function () {
var result = gulp.src([
paths.typescript.globpatterns.all,
paths.typescript.globpatterns.excludedefinitions
])
.pipe(plumber())
.pipe(sourcemaps.init())
.pipe(typescript({
removeComments: true,
declarationFiles: false,
noImplicitAny: false,
noEmitOnError: true,
module: "amd",
target: "ES5"
}));
return merge([
result.js.pipe(gulp.dest("./")),
result.pipe(sourcemaps.write()).pipe(gulp.dest("./"))
]);
});
My colleague has the same set-up as me and gets no error.
Typescript is set to version 1.0 in the project file (<TypeScriptToolsVersion>1.0</TypeScriptToolsVersion>) and I can't change this just now. I wondered if the reason was beacuse I don't have this version installed on my machine but my colleague doesn't either. C:\Program Files (x86)\Microsoft SDKs\TypeScript only has a folder for 1.7
I noticed that the task completes successfully if I remove either of the 2 lines with in the merge block.
It's a different .js file in the error message each time
I searched the web to see what the UNKNOWN error even means but couldn't find anything obvious / helpful. Anyone know how to fix this error? Or how I go about finding out why it's being thrown?
EDIT 20-Jan-2016
So, I was getting this error consistently for about a week ... and now it has stopped happening. I haven't made any changes to my development environment either. I'd like to leave this question open since I'm curious as to why this happened.

Issue a unit test on a Gulp file using Karma & Jasmine

I wrote a unit test for a Gulp file. The test runs through karma using Jasmine Framework (safari/chrome).
Knowing that Karma runs the test file, specified in the json config file, in the browser, it should have a way to run Node's modules in the browser.
After researching, I found that by using Browserify I'll be able to require modules in the browser.
When I write this command
browserify ./Test/GulpTest.js -o ./Test/TEST.js -d
The new TEST.js seems to be big
and I run the following command to start the test on the new TEST.js
karma start karma.conf.js
I get this error:
gulp input stream
✗ should compile from ts to js TypeError: Cannot read property 'isTTY' of undefined
at Object. (/Users/Snap/Desktop/Demo App/Test/TEST.js:75226:20)
at Object.252._process (/Users/Snap/Desktop/Demo App/Test/TEST.js:75284:4)
at s (/Users/Snap/Desktop/Demo App/Test/TEST.js:1:254)
at /Users/Snap/Desktop/Demo App/Test/TEST.js:1:305
at Object.31../lib/PluginError (/Users/Snap/Desktop/Demo App/Test/TEST.js:3530:9)
at Object.239../lib/PluginError (/Users/Snap/Desktop/Demo App/Test/TEST.js:75113:21)
at s (/Users/Snap/Desktop/Demo App/Test/TEST.js:1:254)
at /Users/Snap/Desktop/Demo App/Test/TEST.js:1:305
at Object.229.deprecated (/Users/Snap/Desktop/Demo App/Test/TEST.js:74824:13)
at s (/Users/Snap/Desktop/Demo App/Test/TEST.js:1:254)
Chrome 44.0.2403 (Mac OS X 10.10.4): Executed 1 of 1 (1 FAILED) ERROR
(0.037 secs / 0.03 secs)
it("should compile from ts to js", function () {
var gulp = require("gulp");
var ts = require("gulp-typescript");
var lazy = require("gulp-load-plugins");
var fs = require('graceful-fs');
var should = require('should');
var join = require('path').join;
/*
* * * Compile Typescript to JavaScript
*/
gulp.task("ts-compiler", function () {
return gulp.src("./Test/lib/file.ts")
.pipe(lazy.typescript({
// Generates corresponding .map file.
sourceMap : false,
// Generates corresponding .d.ts file.
declaration : true,
// Do not emit comments to output.
removeComments : false,
// Warn on expressions and declarations with an implied 'any' type.
noImplicitAny : false,
// Skip resolution and preprocessing.
noResolve : false,
// Specify module code generation: 'commonjs' or 'amd'
module : "amd",
// Specify ECMAScript target version: 'ES3' (default), or 'ES5'
target : "ES5"
}))
.pipe(gulp.dest("./Test/lib/dest"));
});
gulp.start("ts-compiler", function () {
console.log("compiling...");
should.exist("./Test/lib/dest/file.js");
});
});
You can't run Gulp inside karma and jasmine—you're running it as if it is a front-end library, and it is not.
You need to use a back-end testing library. You can still use jasmine, you just have to use it through nodejs, which is how gulp runs: https://www.npmjs.com/package/jasmine
You might be interested to see how I wrote unit tests for my gulp tasks where I work: https://github.com/Lostmyname/lmn-gulp-tasks/tree/master/test

Configure a separate Grunt instance in a test

I have been writing a small grunt plugin, and now I am stuck trying to test the plugin end-to-end. What I would like to accomplish is this
Write a test case that configures a grunt instance with a minimal grunt config for my plugin and runs that task
Test that the file produced equals the intended output
Run that test automatically when running grunt nodeunit
So far, I seem stuck on configuring an individual Grunt instance, as the new instance seems to share configuration with that of the already loaded Grunt instance.
I got something like this in my plugin_test.js
var testGrunt = require('grunt');
exports.codekit = {
setUp: function(done) {
testGrunt.initConfig({
myPlugin : {
// the config
}
});
testGrunt.task.run(['myPlugin']);
done();
},
basic_parsing_works: function(test) {
test.expect(1); // no idea what this does
test.equal(1,1,'basic test');
//var actual = testGrunt.file.read('tmp/test01_result.html');
//var expected = testGrunt.file.read('expected/test01_expected.html');
//test.equal(actual, expected, 'should parse file.');
test.done();
}
};
The problem is that when I run the task for myPlugin it uses the configuration loaded in the "outer" (already running) Grunt instance. Even though I have specifically created a new Grunt instance under a different name (testGrunt).
Is there a way to avoid this?

grunt and qunit - running a single test

I already have grunt-contrib-qunit set up. My Gruntfile.js includes something like this
qunit: { files: ['test/*.html'] }
Now I can run grunt qunit and all my tests run.
Question: how can I run just one single test without running all of them? Is there a way I can overload the value of files from the command line?
You definitely need to look into grunt-contrib-qunit and grunt-contrib-connect (https://github.com/gruntjs/grunt-contrib-qunit and https://github.com/gruntjs/grunt-contrib-connect) as the tandem will provide you with a headless phantom and a local webserver.
UPDATE - as for running just one specific test, you could write something like this, listing your tests as separate targets for your qunit task:
grunt.initConfig({
qunit: {
justSomething: ['test/justsomething.html'],
justSomethingElse: ['test/justsomethingelse.html'],
all: ['test/*.html']
}
});
Then you can call grunt qunit:justSomething, or grunt qunit:all - this is not specific to qunit, though - see http://gruntjs.com/configuring-tasks
Now, if you would really like to use the target to specify a test name, you would go with something like:
module.exports = function(grunt) {
grunt.loadNpmTasks('grunt-contrib-qunit');
grunt.initConfig({
qunit: {
all: ['test/**/*.html']
}
});
grunt.task.registerTask('foo', 'A sample task that run one test.', function(testname) {
if(!!testname)
grunt.config('qunit.all', ['test/' + testname + '.html']);
grunt.task.run('qunit:all');
});
}
Then call grunt foo:testname.
Yet again, this is not specific to qunit - but rather grunt task writing.
Hope that (finally) helps.

Categories

Resources