3
var fs = require("fs");
4
var assert = require("chai").assert;
5
var PrismLoader = require("./prism-loader");
6
var TokenStreamTransformer = require("./token-stream-transformer");
9
* Handles parsing of a test case file.
12
* A test case file consists of at least two parts, separated by a line of dashes.
13
* This separation line must start at the beginning of the line and consist of at least three dashes.
15
* The test case file can either consist of two parts:
19
* {expected token stream}
26
* {expected token stream}
28
* {text comment explaining the test case}
30
* If the file contains more than three parts, the remaining parts are just ignored.
31
* If the file however does not contain at least two parts (so no expected token stream),
32
* the test case will later be marked as failed.
35
* @type {{runTestCase: Function, transformCompiledTokenStream: Function, parseTestCaseFile: Function}}
40
* Runs the given test case file and asserts the result
42
* The passed language identifier can either be a language like "css" or a composed language
43
* identifier like "css+markup". Composed identifiers can be used for testing language inclusion.
45
* When testing language inclusion, the first given language is the main language which will be passed
46
* to Prism for highlighting ("css+markup" will result in a call to Prism to highlight with the "css" grammar).
47
* But it will be ensured, that the additional passed languages will be loaded too.
49
* The languages will be loaded in the order they were provided.
51
* @param {string} languageIdentifier
52
* @param {string} filePath
54
runTestCase: function (languageIdentifier, filePath) {
55
var testCase = this.parseTestCaseFile(filePath);
56
var usedLanguages = this.parseLanguageNames(languageIdentifier);
58
if (null === testCase) {
59
throw new Error("Test case file has invalid format (or the provided token stream is invalid JSON), please read the docs.");
62
var Prism = PrismLoader.createInstance(usedLanguages.languages);
63
// the first language is the main language to highlight
64
var mainLanguageGrammar = Prism.languages[usedLanguages.mainLanguage];
65
var compiledTokenStream = Prism.tokenize(testCase.testSource, mainLanguageGrammar);
66
var simplifiedTokenStream = TokenStreamTransformer.simplify(compiledTokenStream);
68
assert.deepEqual(simplifiedTokenStream, testCase.expectedTokenStream, testCase.comment);
73
* Parses the language names and finds the main language.
75
* It is either the first language or the language followed by a exclamation mark “!”.
76
* There should only be one language with an exclamation mark.
78
* @param {string} languageIdentifier
80
* @returns {{languages: string[], mainLanguage: string}}
82
parseLanguageNames: function (languageIdentifier) {
83
var languages = languageIdentifier.split("+");
84
var mainLanguage = null;
86
languages = languages.map(
88
var pos = language.indexOf("!");
92
throw "There are multiple main languages defined.";
95
mainLanguage = language.replace("!", "");
104
mainLanguage = languages[languages.length-1];
108
languages: languages,
109
mainLanguage: mainLanguage
115
* Parses the test case from the given test case file
118
* @param {string} filePath
119
* @returns {{testSource: string, expectedTokenStream: Array.<Array.<string>>, comment:string?}|null}
121
parseTestCaseFile: function (filePath) {
122
var testCaseSource = fs.readFileSync(filePath, "utf8");
123
var testCaseParts = testCaseSource.split(/^-{10,}\w*$/m);
127
testSource: testCaseParts[0].trim(),
128
expectedTokenStream: JSON.parse(testCaseParts[1]),
132
// if there are three parts, the third one is the comment
133
// explaining the test case
134
if (testCaseParts[2]) {
135
testCase.comment = testCaseParts[2].trim();
141
// the JSON can't be parsed (e.g. it could be empty)