'use strict'; function getTrace(node) { function shouldPutToTrace(syntax) { if (syntax === null) { return false; } return ( syntax.type === 'Type' || syntax.type === 'Property' || syntax.type === 'Keyword' ); } function hasMatch(matchNode) { if (Array.isArray(matchNode.match)) { // use for-loop for better perfomance for (let i = 0; i < matchNode.match.length; i++) { if (hasMatch(matchNode.match[i])) { if (shouldPutToTrace(matchNode.syntax)) { result.unshift(matchNode.syntax); } return true; } } } else if (matchNode.node === node) { result = shouldPutToTrace(matchNode.syntax) ? [matchNode.syntax] : []; return true; } return false; } let result = null; if (this.matched !== null) { hasMatch(this.matched); } return result; } function isType(node, type) { return testNode(this, node, match => match.type === 'Type' && match.name === type); } function isProperty(node, property) { return testNode(this, node, match => match.type === 'Property' && match.name === property); } function isKeyword(node) { return testNode(this, node, match => match.type === 'Keyword'); } function testNode(match, node, fn) { const trace = getTrace.call(match, node); if (trace === null) { return false; } return trace.some(fn); } exports.getTrace = getTrace; exports.isKeyword = isKeyword; exports.isProperty = isProperty; exports.isType = isType;