mirror of
https://github.com/wu736139669/Monkey-Test.git
synced 2026-08-05 05:55:46 +00:00
174 lines
5.4 KiB
JavaScript
174 lines
5.4 KiB
JavaScript
'use strict';
|
|
|
|
var singleQuote = '\''.charCodeAt(0);
|
|
var doubleQuote = '"'.charCodeAt(0);
|
|
var backslash = '\\'.charCodeAt(0);
|
|
var slash = '/'.charCodeAt(0);
|
|
var newline = '\n'.charCodeAt(0);
|
|
var space = ' '.charCodeAt(0);
|
|
var feed = '\f'.charCodeAt(0);
|
|
var tab = '\t'.charCodeAt(0);
|
|
var cr = '\r'.charCodeAt(0);
|
|
var comma = ','.charCodeAt(0);
|
|
var colon = ':'.charCodeAt(0);
|
|
var openBracket = '('.charCodeAt(0);
|
|
var closeBracket = ')'.charCodeAt(0);
|
|
|
|
module.exports = function (input) {
|
|
var tokens = [];
|
|
var value = input;
|
|
|
|
var code, next, quote, escape, escapePos, last, nodes;
|
|
|
|
var length = value.length;
|
|
var pos = 0;
|
|
var stack = [tokens];
|
|
var balanced = 0;
|
|
|
|
while (pos < length) {
|
|
code = value.charCodeAt(pos);
|
|
last = tokens[tokens.length - 1];
|
|
|
|
switch (code) {
|
|
case newline:
|
|
case space:
|
|
case tab:
|
|
case cr:
|
|
case feed:
|
|
next = pos;
|
|
do {
|
|
next += 1;
|
|
if (next === length) {
|
|
break;
|
|
}
|
|
code = value.charCodeAt(next);
|
|
} while (code === space ||
|
|
code === newline ||
|
|
code === tab ||
|
|
code === cr ||
|
|
code === feed);
|
|
if (last && last.type === 'div') {
|
|
last.after = value.slice(pos, next);
|
|
} else {
|
|
tokens.push({
|
|
type: 'space',
|
|
value: value.slice(pos, next)
|
|
});
|
|
}
|
|
pos = next - 1;
|
|
break;
|
|
|
|
case comma:
|
|
case colon:
|
|
case slash:
|
|
last = last && last.type === 'space' ? tokens.pop() : null;
|
|
tokens.push({
|
|
type: 'div',
|
|
value: String.fromCharCode(code),
|
|
before: last && last.type === 'space' ? last.value : '',
|
|
after: ''
|
|
});
|
|
|
|
break;
|
|
|
|
case openBracket:
|
|
balanced += 1;
|
|
nodes = [];
|
|
tokens.push({
|
|
type: 'function',
|
|
value: last && last.type === 'word' ? tokens.pop().value : '',
|
|
nodes: nodes
|
|
});
|
|
stack.push(nodes);
|
|
tokens = nodes;
|
|
break;
|
|
|
|
case closeBracket:
|
|
balanced -= 1;
|
|
tokens = stack[balanced];
|
|
break;
|
|
|
|
case singleQuote:
|
|
case doubleQuote:
|
|
quote = String.fromCharCode(code);
|
|
next = pos;
|
|
do {
|
|
escape = false;
|
|
next = value.indexOf(quote, next + 1);
|
|
if (next === -1) {
|
|
value += quote;
|
|
next = value.length - 1;
|
|
}
|
|
escapePos = next;
|
|
while (value.charCodeAt(escapePos - 1) === backslash) {
|
|
escapePos -= 1;
|
|
escape = !escape;
|
|
}
|
|
} while (escape);
|
|
tokens.push({
|
|
type: 'string',
|
|
quote: quote,
|
|
value: value.slice(pos + 1, next)
|
|
});
|
|
pos = next;
|
|
break;
|
|
|
|
case backslash:
|
|
next = pos;
|
|
escape = true;
|
|
while (value.charCodeAt(next + 1) === backslash) {
|
|
next += 1;
|
|
escape = !escape;
|
|
}
|
|
code = value.charCodeAt(next + 1);
|
|
if (escape && code !== slash &&
|
|
code !== space &&
|
|
code !== newline &&
|
|
code !== tab &&
|
|
code !== cr &&
|
|
code !== feed) {
|
|
next += 1;
|
|
}
|
|
tokens.push({
|
|
type: 'word',
|
|
value: value.slice(pos, next + 1)
|
|
});
|
|
pos = next;
|
|
break;
|
|
|
|
default:
|
|
next = pos;
|
|
do {
|
|
next += 1;
|
|
if (next === length) {
|
|
break;
|
|
}
|
|
code = value.charCodeAt(next);
|
|
} while (code !== singleQuote &&
|
|
code !== doubleQuote &&
|
|
code !== backslash &&
|
|
code !== slash &&
|
|
code !== newline &&
|
|
code !== space &&
|
|
code !== feed &&
|
|
code !== tab &&
|
|
code !== cr &&
|
|
code !== comma &&
|
|
code !== colon &&
|
|
code !== openBracket &&
|
|
code !== closeBracket);
|
|
|
|
tokens.push({
|
|
type: 'word',
|
|
value: value.slice(pos, next)
|
|
});
|
|
pos = next - 1;
|
|
break;
|
|
}
|
|
|
|
pos += 1;
|
|
}
|
|
|
|
return stack[0];
|
|
};
|