Skip to content

Commit

Permalink
Merge pull request #893 from DanPurdy/feature/strip-bom
Browse files Browse the repository at this point in the history
Fix BOM markers causing parse issues
  • Loading branch information
bgriffith authored Oct 27, 2016
2 parents 663eeef + 16955ab commit d2c4ce4
Show file tree
Hide file tree
Showing 6 changed files with 102 additions and 3 deletions.
7 changes: 4 additions & 3 deletions lib/groot.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,14 +3,15 @@
//////////////////////////////
'use strict';

var gonzales = require('gonzales-pe'),
fm = require('front-matter');
var gonzales = require('gonzales-pe');
var fm = require('front-matter');
var helpers = require('./helpers');

module.exports = function (text, syntax, filename) {
var tree;

// Run `.toString()` to allow Buffers to be passed in
text = text.toString();
text = helpers.stripBom(text.toString());

// if we're skipping front matter do it here, fall back to just our text in case it fails
if (fm.test(text)) {
Expand Down
20 changes: 20 additions & 0 deletions lib/helpers.js
Original file line number Diff line number Diff line change
Expand Up @@ -394,4 +394,24 @@ helpers.isPartialStringMatch = function (needle, haystack) {
return false;
};

/**
* A copy of the the stripBom module from https://github.com/sindresorhus/strip-bom/blob/master/index.js
* The module requires node > 4 whereas we support earlier versions.
* This function strips the BOM marker from the beginning of a file
*
* @param {string} str - The string we wish to strip the BOM marker from
* @returns {string} The string without a BOM marker
*/
helpers.stripBom = function (str) {
if (typeof str !== 'string') {
throw new TypeError('Expected a string, got ' + typeof str);
}

if (str.charCodeAt(0) === 0xFEFF) {
return str.slice(1);
}

return str;
};

module.exports = helpers;
5 changes: 5 additions & 0 deletions tests/bom-utf8/starts-with-mixin-utf8-bom.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
@mixin foo(
$param: 'def'
) {
color: red;
}
5 changes: 5 additions & 0 deletions tests/bom-utf8/var-utf8-bom.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
$my-color: red;

body {
color: $my-color;
}
40 changes: 40 additions & 0 deletions tests/cli.js
Original file line number Diff line number Diff line change
Expand Up @@ -472,3 +472,43 @@ describe('cli', function () {
});
});
});

// ==============================================================================
// UTF-8 BOM
// ==============================================================================

describe('Reading files with UTF-8 BOM', function () {
before(function () {
var testText = fs.readFileSync('tests/bom-utf8/starts-with-mixin-utf8-bom.scss').toString();
if (testText.charCodeAt(0) !== 0xFEFF) {
throw new Error('BOM test files have no BOM markers');
}
});

it('should not throw a parse error from file containing a BOM', function (done) {
var command = 'node bin/sass-lint -v tests/bom-utf8/starts-with-mixin-utf8-bom.scss --format json';

exec(command, function (err, stdout) { // eslint-disable-line handle-callback-err
var result = JSON.parse(stdout)[0];

// Files with BOM markers that start with a mixin throw a fatal error
// https://github.com/sasstools/sass-lint/issues/880
assert.equal(result.errorCount, 0);
done();
});
});

it('should return the correct amount of warnings from a file containing BOM markers', function (done) {
var command = 'node bin/sass-lint -v tests/bom-utf8/var-utf8-bom.scss --format json';

exec(command, function (err, stdout) { // eslint-disable-line handle-callback-err
var result = JSON.parse(stdout)[0];

// Files starting with variables threw extra errors
// see https://github.com/sasstools/sass-lint/issues/880
assert.equal(result.errorCount, 0);
assert.equal(result.warningCount, 2);
done();
});
});
});
28 changes: 28 additions & 0 deletions tests/helpers/stripBom.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
'use strict';

var assert = require('assert'),
helpers = require('../../lib/helpers'),
fs = require('fs');

describe('helpers - stripBom', function () {

//////////////////////////////
// Strip BOM
//////////////////////////////

it('should remove the BOM marker', function (done) {
var file = fs.readFileSync('tests/bom-utf8/starts-with-mixin-utf8-bom.scss').toString();
assert.equal(file.charCodeAt(0), 0xFEFF);
assert.notEqual(helpers.stripBom(file).charCodeAt(0), 0xFEFF);
done();
});

it('should throw an error if not passed a string', function (done) {
assert.throws(
function () {
helpers.stripBom(8);
}, Error
);
done();
});
});

0 comments on commit d2c4ce4

Please sign in to comment.