Skip to content

Commit 3b10553

Browse files
authored
fix: toString should stringify node (#74)
* fix: toString should stringify node * refactor: rename, rework inherited nodes for toString * chore: remove commented code
1 parent bc08be3 commit 3b10553

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

46 files changed

+513
-87
lines changed

lib/ValuesParser.js

+1
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ module.exports = class ValuesParser extends Parser {
5252
const inline = Comment.testInline(token);
5353
const node = this.lastNode;
5454
node.inline = inline;
55+
Object.setPrototypeOf(node, Comment.prototype);
5556
}
5657

5758
fromFirst(tokens, Constructor) {

lib/ValuesStringifier.js

+6-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,11 @@
11
const Stringifier = require('postcss/lib/stringifier');
22

3-
module.exports = class LessStringifier extends Stringifier {
3+
module.exports = class ValuesStringifier extends Stringifier {
4+
static stringify(node, builder) {
5+
const stringifier = new ValuesStringifier(builder);
6+
stringifier.stringify(node);
7+
}
8+
49
basic(node, value) {
510
const print = value || node.value;
611
const after = node.raws.after ? this.raw(node, 'after') || '' : '';

lib/index.js

+11-5
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
const Input = require('postcss/lib/input');
1212

1313
const Parser = require('./ValuesParser');
14-
const Stringifier = require('./ValuesStringifier');
14+
const { stringify } = require('./ValuesStringifier');
1515

1616
module.exports = {
1717
parse(css, options) {
@@ -20,13 +20,19 @@ module.exports = {
2020

2121
parser.parse();
2222

23+
const { root } = parser;
24+
const ogToString = root.toString;
25+
26+
function toString(stringifier) {
27+
return ogToString.bind(root)(stringifier || module.exports.stringify);
28+
}
29+
30+
root.toString = toString.bind(root);
31+
2332
return parser.root;
2433
},
2534

26-
stringify(node, builder) {
27-
const stringifier = new Stringifier(builder);
28-
stringifier.stringify(node);
29-
},
35+
stringify,
3036

3137
nodeToString(node) {
3238
let result = '';

lib/nodes/AtWord.js

+4-3
Original file line numberDiff line numberDiff line change
@@ -12,10 +12,11 @@ const AtRule = require('postcss/lib/node');
1212

1313
const { registerWalker } = require('../walker');
1414

15+
const { stringify } = require('../ValuesStringifier');
16+
1517
class AtWord extends AtRule {
16-
constructor(options) {
17-
super(options);
18-
this.type = 'atword';
18+
toString(stringifier = stringify) {
19+
return super.toString(stringifier);
1920
}
2021
}
2122

lib/nodes/Comment.js

+50-40
Original file line numberDiff line numberDiff line change
@@ -8,61 +8,71 @@
88
The above copyright notice and this permission notice shall be
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
11-
const Comment = require('postcss/lib/comment');
11+
const PostCssComment = require('postcss/lib/comment');
12+
13+
const { stringify } = require('../ValuesStringifier');
1214

1315
const inlineRegex = /(\/\/)/;
1416

15-
Comment.testInline = (token) => inlineRegex.test(token[1]);
17+
class Comment extends PostCssComment {
18+
static testInline(token) {
19+
return inlineRegex.test(token[1]);
20+
}
1621

17-
Comment.tokenizeNext = (tokens, parser) => {
18-
const [first] = tokens;
19-
const newlineIndex = tokens.findIndex((t) => /\n/.test(t[1]));
20-
let bits = tokens;
21-
let rest = [];
22+
static tokenizeNext(tokens, parser) {
23+
const [first] = tokens;
24+
const newlineIndex = tokens.findIndex((t) => /\n/.test(t[1]));
25+
let bits = tokens;
26+
let rest = [];
2227

23-
if (newlineIndex >= 0) {
24-
bits = tokens.slice(0, newlineIndex);
25-
rest = tokens.slice(newlineIndex);
26-
}
28+
if (newlineIndex >= 0) {
29+
bits = tokens.slice(0, newlineIndex);
30+
rest = tokens.slice(newlineIndex);
31+
}
32+
33+
bits = bits.map((t) => t[1]);
2734

28-
bits = bits.map((t) => t[1]);
35+
// see tilde comment in tokenizeInline
36+
const text = bits.concat('~~').join('');
37+
const last = bits[bits.length - 1];
38+
const newToken = ['comment', text, first[2], first[3], last[2], last[3]];
2939

30-
// see tilde comment in tokenizeInline
31-
const text = bits.concat('~~').join('');
32-
const last = bits[bits.length - 1];
33-
const newToken = ['comment', text, first[2], first[3], last[2], last[3]];
40+
parser.back([newToken, ...rest]);
41+
}
3442

35-
parser.back([newToken, ...rest]);
36-
};
43+
static tokenizeInline(tokens, parser) {
44+
const [first, ...rest] = tokens;
45+
const bits = first[1].split(/(\/\/.+)/).filter((t) => !!t);
46+
const newTokens = [];
47+
const [, , startLine, , endLine] = first;
48+
let [, , , startChar, , endChar] = first;
3749

38-
Comment.tokenizeInline = (tokens, parser) => {
39-
const [first, ...rest] = tokens;
40-
const bits = first[1].split(/(\/\/.+)/).filter((t) => !!t);
41-
const newTokens = [];
42-
const [, , startLine, , endLine] = first;
43-
let [, , , startChar, , endChar] = first;
50+
for (let bit of bits) {
51+
const comment = bit.slice(0, 2) === '//';
52+
const type = comment ? 'comment' : 'word';
4453

45-
for (let bit of bits) {
46-
const comment = bit.slice(0, 2) === '//';
47-
const type = comment ? 'comment' : 'word';
54+
if (comment) {
55+
// the Parser base comment() method trims the last two characters when creating the node
56+
// these tildes are added to counter that. it's hacky, but it works, and we don't have to
57+
// re-implement the method
58+
bit += '~~';
59+
}
4860

49-
if (comment) {
50-
// the Parser base comment() method trims the last two characters when creating the node
51-
// these tildes are added to counter that. it's hacky, but it works, and we don't have to
52-
// re-implement the method
53-
bit += '~~';
54-
}
61+
if (bit !== bits[0]) {
62+
startChar = endChar + 1;
63+
}
5564

56-
if (bit !== bits[0]) {
57-
startChar = endChar + 1;
58-
}
65+
endChar = startChar + bit.length - 1;
5966

60-
endChar = startChar + bit.length - 1;
67+
newTokens.push([type, bit, startLine, startChar, endLine, endChar]);
68+
}
6169

62-
newTokens.push([type, bit, startLine, startChar, endLine, endChar]);
70+
parser.back(newTokens.concat(rest));
6371
}
6472

65-
parser.back(newTokens.concat(rest));
66-
};
73+
toString(stringifier = stringify) {
74+
return super.toString(stringifier);
75+
}
76+
}
6777

6878
module.exports = Comment;

lib/nodes/Container.js

+21
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
/*
2+
Copyright © 2018 Andrew Powell
3+
4+
This Source Code Form is subject to the terms of the Mozilla Public
5+
License, v. 2.0. If a copy of the MPL was not distributed with this
6+
file, You can obtain one at http://mozilla.org/MPL/2.0/.
7+
8+
The above copyright notice and this permission notice shall be
9+
included in all copies or substantial portions of this Source Code Form.
10+
*/
11+
const PostCssContainer = require('postcss/lib/container');
12+
13+
const { stringify } = require('../ValuesStringifier');
14+
15+
class Container extends PostCssContainer {
16+
toString(stringifier = stringify) {
17+
return super.toString(stringifier);
18+
}
19+
}
20+
21+
module.exports = Container;

lib/nodes/Func.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@
88
The above copyright notice and this permission notice shall be
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
11-
const Container = require('postcss/lib/container');
12-
1311
const { registerWalker } = require('../walker');
1412

13+
const Container = require('./Container');
14+
1515
const colorFunctions = ['hsl', 'hsla', 'rgb', 'rgba'];
1616

1717
class Func extends Container {

lib/nodes/Interpolation.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@
88
The above copyright notice and this permission notice shall be
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
11-
const Container = require('postcss/lib/container');
12-
1311
const { registerWalker } = require('../walker');
1412

13+
const Container = require('./Container');
14+
1515
class Interpolation extends Container {
1616
constructor(options = {}) {
1717
super(options);

lib/nodes/Node.js

+21
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
/*
2+
Copyright © 2018 Andrew Powell
3+
4+
This Source Code Form is subject to the terms of the Mozilla Public
5+
License, v. 2.0. If a copy of the MPL was not distributed with this
6+
file, You can obtain one at http://mozilla.org/MPL/2.0/.
7+
8+
The above copyright notice and this permission notice shall be
9+
included in all copies or substantial portions of this Source Code Form.
10+
*/
11+
const PostCssNode = require('postcss/lib/node');
12+
13+
const { stringify } = require('../ValuesStringifier');
14+
15+
class Node extends PostCssNode {
16+
toString(stringifier = stringify) {
17+
return super.toString(stringifier || {});
18+
}
19+
}
20+
21+
module.exports = Node;

lib/nodes/Numeric.js

+2-1
Original file line numberDiff line numberDiff line change
@@ -9,10 +9,11 @@
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
1111
const isNumber = require('is-number');
12-
const Node = require('postcss/lib/node');
1312

1413
const { registerWalker } = require('../walker');
1514

15+
const Node = require('./Node');
16+
1617
const unitRegex = /%|ch|cm|em|ex|in|mm|pc|pt|px|rem|vh|vmax|vmin|vw$/i;
1718

1819
class Numeric extends Node {

lib/nodes/Operator.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@
88
The above copyright notice and this permission notice shall be
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
11-
const Node = require('postcss/lib/node');
12-
1311
const { registerWalker } = require('../walker');
1412

13+
const Node = require('./Node');
14+
1515
const operators = ['+', '-', '/', '*', '%'];
1616
const operRegex = new RegExp(`([/|*}])`);
1717

lib/nodes/Punctuation.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -8,11 +8,11 @@
88
The above copyright notice and this permission notice shall be
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
11-
const Node = require('postcss/lib/node');
12-
1311
const { getTokens } = require('../tokenize');
1412
const { registerWalker } = require('../walker');
1513

14+
const Node = require('./Node');
15+
1616
/**
1717
* @desc Punctuation nodes can contain:
1818
* , : ( ) { } [ ]

lib/nodes/Quoted.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@
88
The above copyright notice and this permission notice shall be
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
11-
const Node = require('postcss/lib/node');
12-
1311
const { registerWalker } = require('../walker');
1412

13+
const Node = require('./Node');
14+
1515
class Quoted extends Node {
1616
constructor(options) {
1717
super(options);

lib/nodes/UnicodeRange.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@
88
The above copyright notice and this permission notice shall be
99
included in all copies or substantial portions of this Source Code Form.
1010
*/
11-
const Node = require('postcss/lib/node');
12-
1311
const { registerWalker } = require('../walker');
1412

13+
const Node = require('./Node');
14+
1515
class UnicodeRange extends Node {
1616
constructor(options) {
1717
super(options);

lib/nodes/Word.js

+2-1
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,11 @@
1010
*/
1111
const colors = require('color-name');
1212
const isUrl = require('is-url-superb');
13-
const Node = require('postcss/lib/node');
1413

1514
const { registerWalker } = require('../walker');
1615

16+
const Node = require('./Node');
17+
1718
const escapeRegex = /^\\(.+)/;
1819
const hexRegex = /^#(.+)/;
1920
const colorRegex = /^#([0-9a-f]{3}|[0-9a-f]{4}|[0-9a-f]{6}|[0-9a-f]{8})$/i;

test/atword.test.js

+2
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,8 @@ for (const fixture of snapshot) {
2424
const string = nodeToString(root);
2525

2626
t.is(string, fixture);
27+
t.is(fixture, root.toString());
28+
t.snapshot(root.first.toString());
2729
t.snapshot(string);
2830
t.snapshot(nodes);
2931
});

test/comment.test.js

+2
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,8 @@ for (const fixture of snapshot) {
2424
const string = nodeToString(root);
2525

2626
t.is(string, fixture);
27+
t.is(fixture, root.toString());
28+
t.snapshot(root.first.toString());
2729
t.snapshot(string);
2830
t.snapshot(nodes);
2931
});

test/fixtures/interpolation.js

+2-1
Original file line numberDiff line numberDiff line change
@@ -12,5 +12,6 @@ module.exports = {
1212
options: {
1313
interpolation: { prefix: '#' }
1414
},
15-
snapshot: ['#{batman}', '#{2px}', '#{2 * 2px}']
15+
snapshot: ['#{batman}', '#{2px}', '#{2 * 2px}'],
16+
throws: ['#{batman']
1617
};

test/func.test.js

+2
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,8 @@ for (const fixture of snapshot) {
2424
const string = nodeToString(root);
2525

2626
t.is(string, fixture);
27+
t.is(fixture, root.toString());
28+
t.snapshot(root.first.toString());
2729
t.snapshot(string);
2830
t.snapshot(nodes);
2931
});

test/interpolation.test.js

+9-1
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ const test = require('ava');
1212

1313
const { nodeToString, parse } = require('../lib');
1414

15-
const { options, snapshot } = require('./fixtures/interpolation');
15+
const { options, snapshot, throws } = require('./fixtures/interpolation');
1616

1717
for (const fixture of snapshot) {
1818
test(fixture, (t) => {
@@ -24,7 +24,15 @@ for (const fixture of snapshot) {
2424
const string = nodeToString(root);
2525

2626
t.is(string, fixture);
27+
t.is(fixture, root.toString());
28+
t.snapshot(root.first.toString());
2729
t.snapshot(string);
2830
t.snapshot(nodes);
2931
});
3032
}
33+
34+
for (const fixture of throws) {
35+
test(fixture, (t) => {
36+
t.throws(() => parse(fixture));
37+
});
38+
}

test/numeric.test.js

+2
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,8 @@ for (const fixture of snapshot) {
2424
const string = nodeToString(root);
2525

2626
t.is(string, fixture);
27+
t.is(fixture, root.toString());
28+
t.snapshot(root.first.toString());
2729
t.snapshot(string);
2830
t.snapshot(nodes);
2931
});

0 commit comments

Comments
 (0)