test: unit tests for basic configurations

Extracted common config code to utils.js
Added travis config
Added mocha as devDep

Added yarn.lock. Travis CI installs yarn if the file is present.

Marked yarn.lock as binary to prevent conflict hell
Moved web pack back from peerDep to dep
Destructuring is not supported in Node v4.3, so replaced it

Node v4 requires "use strict" to allow block scoped let & const
Node v4: replaced "spread" operator with "apply"
master
Eugene Kulabuhov 2017-02-27 00:22:28 +00:00 committed by Joshua Wiens
parent 38a7be7f5b
commit 43910f3356
6 changed files with 2329 additions and 1 deletions

2
.gitattributes vendored Normal file
View File

@ -0,0 +1,2 @@
# Treats the lock file as binary & prevents conflict hell
yarn.lock -diff

33
.travis.yml Normal file
View File

@ -0,0 +1,33 @@
sudo: false
language: node_js
branches:
only:
- master
matrix:
fast_finish: true
include:
# - os: linux
# node_js: '7'
# env: WEBPACK_VERSION="2.2.0" BITHOUND_CHECK=true JOB_PART=lint
- os: linux
node_js: '7'
env: WEBPACK_VERSION="2.2.0" JOB_PART=test
- os: linux
node_js: '4.3'
env: WEBPACK_VERSION="2.2.0" JOB_PART=test
- os: linux
node_js: '6'
env: WEBPACK_VERSION="2.2.0" JOB_PART=test
# - os: linux
# node_js: '7'
# env: WEBPACK_VERSION="2.2.0" JOB_PART=coverage
before_install:
- nvm --version
- node --version
before_script:
- if [ "$WEBPACK_VERSION" ]; then yarn add webpack@^$WEBPACK_VERSION; fi
# - if [ "$BITHOUND_CHECK" ]; then npm install -g bithound; bithound check git@github.com:$TRAVIS_REPO_SLUG.git; fi
script:
- yarn run travis:$JOB_PART
after_success:
- bash <(curl -s https://codecov.io/bash)

View File

@ -4,7 +4,12 @@
"author": "Tobias Koppers @sokra",
"description": "style loader module for webpack",
"devDependencies": {
"css-loader": "~0.8.0"
"css-loader": "~0.8.0",
"file-loader": "^0.10.1",
"jsdom": "^9.11.0",
"memory-fs": "^0.4.1",
"mocha": "^3.2.0",
"webpack": "^2.2.1"
},
"repository": {
"type": "git",
@ -13,5 +18,9 @@
"license": "MIT",
"dependencies": {
"loader-utils": "^1.0.2"
},
"scripts": {
"test": "mocha",
"travis:test": "yarn run test"
}
}

151
test/basicTest.js Normal file
View File

@ -0,0 +1,151 @@
// Node v4 requires "use strict" to allow block scoped let & const
"use strict";
describe("basic tests", function() {
var path = require("path");
var utils = require("./utils"),
runCompilerTest = utils.runCompilerTest;
var fs;
var requiredCss = ".required { color: blue }",
requiredCssTwo = ".requiredTwo { color: cyan }",
requiredStyle = `<style type="text/css">${requiredCss}</style>`,
existingStyle = "<style>.existing { color: yellow }</style>",
rootDir = path.resolve(__dirname + "/../") + "/",
jsdomHtml = [
"<html>",
"<head>",
existingStyle,
"</head>",
"<body>",
"</body>",
"</html>"
].join("\n");
var styleLoaderOptions = {};
var cssRule = {};
var defaultCssRule = {
test: /\.css?$/,
use: [
{
loader: "style-loader",
options: styleLoaderOptions
},
"css-loader"
]
};
var webpackConfig = {
entry: "./main.js",
output: {
filename: "bundle.js"
},
module: {
rules: [cssRule]
}
};
beforeEach(function() {
// Reset all style-loader options
for (var member in styleLoaderOptions) {
delete styleLoaderOptions[member];
}
for (var member in defaultCssRule) {
cssRule[member] = defaultCssRule[member];
}
fs = utils.setup(webpackConfig, jsdomHtml);
// Create a tiny file system. rootDir is used because loaders are refering to absolute paths.
fs.mkdirpSync(rootDir);
fs.writeFileSync(rootDir + "main.js", "var css = require('./style.css');");
fs.writeFileSync(rootDir + "style.css", requiredCss);
fs.writeFileSync(rootDir + "styleTwo.css", requiredCssTwo);
}); // before each
it("insert at bottom", function(done) {
let expected = [existingStyle, requiredStyle].join("\n");
runCompilerTest(expected, done);
}); // it insert at bottom
it("insert at top", function(done) {
styleLoaderOptions.insertAt = "top";
let expected = [requiredStyle, existingStyle].join("\n");
runCompilerTest(expected, done);
}); // it insert at top
it("singleton", function(done) {
// Setup
styleLoaderOptions.singleton = true;
fs.writeFileSync(
rootDir + "main.js",
[
"var a = require('./style.css');",
"var b = require('./styleTwo.css');"
].join("\n")
);
// Run
let expected = [
existingStyle,
`<style type="text/css">${requiredCss}${requiredCssTwo}</style>`
].join("\n");
runCompilerTest(expected, done);
}); // it singleton
it("url", function(done) {
cssRule.use = [
{
loader: "style-loader/url",
options: {}
},
"file-loader"
];
// Run
let expected = [
existingStyle,
'<link rel="stylesheet" type="text/css" href="ec9d4f4f24028c3d51bf1e7728e632ff.css">'
].join("\n");
runCompilerTest(expected, done);
}); // it url
it("useable", function(done) {
cssRule.use = [
{
loader: "style-loader/useable",
options: {}
},
"css-loader"
];
fs.writeFileSync(
rootDir + "main.js",
[
"var css = require('./style.css');",
"var cssTwo = require('./styleTwo.css');",
"css.use();",
"cssTwo.use();",
"css.unuse();"
].join("\n")
);
// Run
let expected = [
existingStyle,
`<style type="text/css">${requiredCssTwo}</style>`
].join("\n");
runCompilerTest(expected, done);
}); // it useable
}); // describe

75
test/utils.js Normal file
View File

@ -0,0 +1,75 @@
// Node v4 requires "use strict" to allow block scoped let & const
"use strict";
var MemoryFS = require("memory-fs");
var realFs = require("fs");
var webpack = require("webpack");
var path = require("path");
var jsdom = require("jsdom");
var assert = require("assert");
var compiler;
var jsdomHtml;
module.exports = {
setup: function(webpackConfig, _jsdomHtml) {
let fs = new MemoryFS();
jsdomHtml = _jsdomHtml;
// Makes webpack resolve style-loader to local folder instead of node_modules
Object.assign(webpackConfig, {
resolveLoader: {
alias: {
"style-loader": path.resolve(__dirname, "../")
}
}
});
compiler = webpack(webpackConfig);
// Tell webpack to use our in-memory FS
compiler.inputFileSystem = fs;
compiler.outputFileSystem = fs;
compiler.resolvers.normal.fileSystem = fs;
compiler.resolvers.context.fileSystem = fs;
["readFileSync", "statSync"].forEach(fn => {
// Preserve the reference to original function
fs["mem" + fn] = fs[fn];
compiler.inputFileSystem[fn] = function(_path) {
// Fallback to real FS if file is not in the memoryFS
if (fs.existsSync(_path)) {
return fs["mem" + fn].apply(fs, arguments);
} else {
return realFs[fn].apply(realFs, arguments);
}
};
});
return fs;
},
runCompilerTest: function(expected, done) {
compiler.run(function(err, stats) {
if (stats.compilation.errors.length) {
throw new Error(stats.compilation.errors);
}
const bundleJs = stats.compilation.assets["bundle.js"].source();
jsdom.env({
html: jsdomHtml,
src: [bundleJs],
done: function(err, window) {
assert.equal(window.document.head.innerHTML.trim(), expected);
// free memory associated with the window
window.close();
done();
}
});
});
}
};

2058
yarn.lock Normal file

File diff suppressed because it is too large Load Diff