Check for possible pre-existing marker strings in Handlebars
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58
diff --git a/components/prism-handlebars.js b/components/prism-handlebars.js
index 72b6d14..aabff07 100644
--- a/components/prism-handlebars.js
+++ b/components/prism-handlebars.js
@@ -51,9 +51,15 @@
env.backupCode = env.code;
env.code = env.code.replace(handlebars_pattern, function(match) {
- env.tokenStack.push(match);
+ var i = env.tokenStack.length;
+ // Check for existing strings
+ while (env.backupCode.indexOf('___HANDLEBARS' + i + '___') !== -1)
+ ++i;
- return '___HANDLEBARS' + env.tokenStack.length + '___';
+ // Create a sparse array
+ env.tokenStack[i] = match;
+
+ return '___HANDLEBARS' + i + '___';
});
});
@@ -72,9 +78,12 @@
return;
}
- for (var i = 0, t; t = env.tokenStack[i]; i++) {
+ for (var i = 0, keys = Object.keys(env.tokenStack); i < keys.length; ++i) {
+ var k = keys[i];
+ var t = env.tokenStack[k];
+
// The replace prevents $$, $&, $`, $', $n, $nn from being interpreted as special patterns
- env.highlightedCode = env.highlightedCode.replace('___HANDLEBARS' + (i + 1) + '___', Prism.highlight(t, env.grammar, 'handlebars').replace(/\$/g, '$$$$'));
+ env.highlightedCode = env.highlightedCode.replace('___HANDLEBARS' + k + '___', Prism.highlight(t, env.grammar, 'handlebars').replace(/\$/g, '$$$$'));
}
env.element.innerHTML = env.highlightedCode;
diff --git a/components/prism-handlebars.min.js b/components/prism-handlebars.min.js
index c029cca..d542c27 100644
--- a/components/prism-handlebars.min.js
+++ b/components/prism-handlebars.min.js
@@ -1 +1 @@
-!function(e){var a=/\{\{\{[\s\S]+?\}\}\}|\{\{[\s\S]+?\}\}/g;e.languages.handlebars=e.languages.extend("markup",{handlebars:{pattern:a,inside:{delimiter:{pattern:/^\{\{\{?|\}\}\}?$/i,alias:"punctuation"},string:/(["'])(\\?.)*?\1/,number:/\b-?(0x[\dA-Fa-f]+|\d*\.?\d+([Ee][+-]?\d+)?)\b/,"boolean":/\b(true|false)\b/,block:{pattern:/^(\s*~?\s*)[#\/]\S+?(?=\s*~?\s*$|\s)/i,lookbehind:!0,alias:"keyword"},brackets:{pattern:/\[[^\]]+\]/,inside:{punctuation:/\[|\]/,variable:/[\s\S]+/}},punctuation:/[!"#%&'()*+,.\/;<=>@\[\\\]^`{|}~]/,variable:/[^!"#%&'()*+,.\/;<=>@\[\\\]^`{|}~\s]+/}}}),e.languages.insertBefore("handlebars","tag",{"handlebars-comment":{pattern:/\{\{![\s\S]*?\}\}/,alias:["handlebars","comment"]}}),e.hooks.add("before-highlight",function(e){"handlebars"===e.language&&(e.tokenStack=[],e.backupCode=e.code,e.code=e.code.replace(a,function(a){return e.tokenStack.push(a),"___HANDLEBARS"+e.tokenStack.length+"___"}))}),e.hooks.add("before-insert",function(e){"handlebars"===e.language&&(e.code=e.backupCode,delete e.backupCode)}),e.hooks.add("after-highlight",function(a){if("handlebars"===a.language){for(var n,t=0;n=a.tokenStack[t];t++)a.highlightedCode=a.highlightedCode.replace("___HANDLEBARS"+(t+1)+"___",e.highlight(n,a.grammar,"handlebars").replace(/\$/g,"$$$$"));a.element.innerHTML=a.highlightedCode}})}(Prism);
\ No newline at end of file
+!function(e){var a=/\{\{\{[\s\S]+?\}\}\}|\{\{[\s\S]+?\}\}/g;e.languages.handlebars=e.languages.extend("markup",{handlebars:{pattern:a,inside:{delimiter:{pattern:/^\{\{\{?|\}\}\}?$/i,alias:"punctuation"},string:/(["'])(\\?.)*?\1/,number:/\b-?(0x[\dA-Fa-f]+|\d*\.?\d+([Ee][+-]?\d+)?)\b/,"boolean":/\b(true|false)\b/,block:{pattern:/^(\s*~?\s*)[#\/]\S+?(?=\s*~?\s*$|\s)/i,lookbehind:!0,alias:"keyword"},brackets:{pattern:/\[[^\]]+\]/,inside:{punctuation:/\[|\]/,variable:/[\s\S]+/}},punctuation:/[!"#%&'()*+,.\/;<=>@\[\\\]^`{|}~]/,variable:/[^!"#%&'()*+,.\/;<=>@\[\\\]^`{|}~\s]+/}}}),e.languages.insertBefore("handlebars","tag",{"handlebars-comment":{pattern:/\{\{![\s\S]*?\}\}/,alias:["handlebars","comment"]}}),e.hooks.add("before-highlight",function(e){"handlebars"===e.language&&(e.tokenStack=[],e.backupCode=e.code,e.code=e.code.replace(a,function(a){for(var n=e.tokenStack.length;-1!==e.backupCode.indexOf("___HANDLEBARS"+n+"___");)++n;return e.tokenStack[n]=a,"___HANDLEBARS"+n+"___"}))}),e.hooks.add("before-insert",function(e){"handlebars"===e.language&&(e.code=e.backupCode,delete e.backupCode)}),e.hooks.add("after-highlight",function(a){if("handlebars"===a.language){for(var n=0,t=Object.keys(a.tokenStack);n<t.length;++n){var r=t[n],o=a.tokenStack[r];a.highlightedCode=a.highlightedCode.replace("___HANDLEBARS"+r+"___",e.highlight(o,a.grammar,"handlebars").replace(/\$/g,"$$$$"))}a.element.innerHTML=a.highlightedCode}})}(Prism);
\ No newline at end of file
diff --git a/tests/languages/handlebars/handlebars_in_markup_feature.js b/tests/languages/handlebars/handlebars_in_markup_feature.js
index 13f51db..dc53d29 100644
--- a/tests/languages/handlebars/handlebars_in_markup_feature.js
+++ b/tests/languages/handlebars/handlebars_in_markup_feature.js
@@ -1,4 +1,5 @@
module.exports = {
'<div>{{{intro}}}</div>': '<span class="token tag"><span class="token tag"><span class="token punctuation"><</span>div</span><span class="token punctuation">></span></span><span class="token handlebars"><span class="token delimiter punctuation">{{{</span><span class="token variable">intro</span><span class="token delimiter punctuation">}}}</span></span><span class="token tag"><span class="token tag"><span class="token punctuation"></</span>div</span><span class="token punctuation">></span></span>',
- '<div class="{{foo}}">': '<span class="token tag"><span class="token tag"><span class="token punctuation"><</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation">=</span><span class="token punctuation">"</span><span class="token handlebars"><span class="token delimiter punctuation">{{</span><span class="token variable">foo</span><span class="token delimiter punctuation">}}</span></span><span class="token punctuation">"</span></span><span class="token punctuation">></span></span>'
+ '<div class="{{foo}}">': '<span class="token tag"><span class="token tag"><span class="token punctuation"><</span>div</span> <span class="token attr-name">class</span><span class="token attr-value"><span class="token punctuation">=</span><span class="token punctuation">"</span><span class="token handlebars"><span class="token delimiter punctuation">{{</span><span class="token variable">foo</span><span class="token delimiter punctuation">}}</span></span><span class="token punctuation">"</span></span><span class="token punctuation">></span></span>',
+ '___HANDLEBARS1___{{{intro}}}': '___HANDLEBARS1___<span class="token handlebars"><span class="token delimiter punctuation">{{{</span><span class="token variable">intro</span><span class="token delimiter punctuation">}}}</span></span>'
};
\ No newline at end of file