mirror of
https://github.com/showdownjs/showdown.git
synced 2024-03-22 13:30:55 +08:00
fix(encodeAmpsAndAngles): fix > and < encoding
In some circumstances, > and < were not being encoded properly. Closes #236
This commit is contained in:
parent
3172e06851
commit
7f43b79b33
72
dist/showdown.js
vendored
72
dist/showdown.js
vendored
@ -1,4 +1,4 @@
|
||||
;/*! showdown 05-02-2017 */
|
||||
;/*! showdown 06-02-2017 */
|
||||
(function(){
|
||||
/**
|
||||
* Created by Tivie on 13-07-2015.
|
||||
@ -1148,7 +1148,7 @@ showdown.Converter = function (converterOptions) {
|
||||
text = showdown.subParser('hashPreCodeTags')(text, options, globals);
|
||||
text = showdown.subParser('githubCodeBlocks')(text, options, globals);
|
||||
text = showdown.subParser('hashHTMLBlocks')(text, options, globals);
|
||||
text = showdown.subParser('hashHTMLSpans')(text, options, globals);
|
||||
text = showdown.subParser('hashCodeTags')(text, options, globals);
|
||||
text = showdown.subParser('stripLinkDefinitions')(text, options, globals);
|
||||
text = showdown.subParser('blockGamut')(text, options, globals);
|
||||
text = showdown.subParser('unhashHTMLSpans')(text, options, globals);
|
||||
@ -1621,6 +1621,12 @@ showdown.subParser('encodeAmpsAndAngles', function (text, options, globals) {
|
||||
// Encode naked <'s
|
||||
text = text.replace(/<(?![a-z\/?$!])/gi, '<');
|
||||
|
||||
// Encode <
|
||||
text = text.replace(/</g, '<');
|
||||
|
||||
// Encode >
|
||||
text = text.replace(/>/g, '>');
|
||||
|
||||
text = globals.converter._dispatch('encodeAmpsAndAngles.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
@ -1847,12 +1853,32 @@ showdown.subParser('hashHTMLSpans', function (text, options, globals) {
|
||||
'use strict';
|
||||
text = globals.converter._dispatch('hashHTMLSpans.before', text, options, globals);
|
||||
|
||||
var matches = showdown.helper.matchRecursiveRegExp(text, '<code\\b[^>]*>', '</code>', 'gi');
|
||||
|
||||
for (var i = 0; i < matches.length; ++i) {
|
||||
text = text.replace(matches[i][0], '¨C' + (globals.gHtmlSpans.push(matches[i][0]) - 1) + 'C');
|
||||
function hashHTMLSpan (html) {
|
||||
return '¨C' + (globals.gHtmlSpans.push(html) - 1) + 'C';
|
||||
}
|
||||
|
||||
// Hash Self Closing tags
|
||||
text = text.replace(/<[^>]+?\/>/gi, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
// Hash tags without properties
|
||||
text = text.replace(/<([^>]+?)>[\s\S]*?<\/\1>/g, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
// Hash tags with properties
|
||||
text = text.replace(/<([^>]+?)\s[^>]+?>[\s\S]*?<\/\1>/g, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
// Hash self closing tags without />
|
||||
text = text.replace(/<[^>]+?>/gi, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
/*showdown.helper.matchRecursiveRegExp(text, '<code\\b[^>]*>', '</code>', 'gi');*/
|
||||
|
||||
text = globals.converter._dispatch('hashHTMLSpans.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
@ -1865,7 +1891,19 @@ showdown.subParser('unhashHTMLSpans', function (text, options, globals) {
|
||||
text = globals.converter._dispatch('unhashHTMLSpans.before', text, options, globals);
|
||||
|
||||
for (var i = 0; i < globals.gHtmlSpans.length; ++i) {
|
||||
text = text.replace('¨C' + i + 'C', globals.gHtmlSpans[i]);
|
||||
var repText = globals.gHtmlSpans[i],
|
||||
// limiter to prevent infinite loop (assume 10 as limit for recurse)
|
||||
limit = 0;
|
||||
|
||||
while (/¨C(\d+)C/.test(repText)) {
|
||||
var num = RegExp.$1;
|
||||
repText = repText.replace('¨C' + num + 'C', globals.gHtmlSpans[num]);
|
||||
if (limit === 10) {
|
||||
break;
|
||||
}
|
||||
++limit;
|
||||
}
|
||||
text = text.replace('¨C' + i + 'C', repText);
|
||||
}
|
||||
|
||||
text = globals.converter._dispatch('unhashHTMLSpans.after', text, options, globals);
|
||||
@ -1885,11 +1923,24 @@ showdown.subParser('hashPreCodeTags', function (text, options, globals) {
|
||||
return '\n\n¨G' + (globals.ghCodeBlocks.push({text: wholeMatch, codeblock: codeblock}) - 1) + 'G\n\n';
|
||||
};
|
||||
|
||||
// Hash <pre><code>
|
||||
text = showdown.helper.replaceRecursiveRegExp(text, repFunc, '^ {0,3}<pre\\b[^>]*>\\s*<code\\b[^>]*>', '^ {0,3}</code>\\s*</pre>', 'gim');
|
||||
|
||||
text = globals.converter._dispatch('hashPreCodeTags.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
|
||||
showdown.subParser('hashCodeTags', function (text, options, globals) {
|
||||
'use strict';
|
||||
text = globals.converter._dispatch('hashCodeTags.before', text, options, globals);
|
||||
// Hash naked <code>
|
||||
var matches = showdown.helper.matchRecursiveRegExp(text, '<code\\b[^>]*>', '</code>', 'gi');
|
||||
for (var i = 0; i < matches.length; ++i) {
|
||||
text = text.replace(matches[i][0], '¨C' + (globals.gHtmlSpans.push(matches[i][0]) - 1) + 'C');
|
||||
}
|
||||
text = globals.converter._dispatch('hashCodeTags.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
|
||||
showdown.subParser('headers', function (text, options, globals) {
|
||||
'use strict';
|
||||
@ -2450,10 +2501,15 @@ showdown.subParser('spanGamut', function (text, options, globals) {
|
||||
// Must come after _DoAnchors(), because you can use < and >
|
||||
// delimiters in inline links like [this](<url>).
|
||||
text = showdown.subParser('autoLinks')(text, options, globals);
|
||||
text = showdown.subParser('encodeAmpsAndAngles')(text, options, globals);
|
||||
text = showdown.subParser('italicsAndBold')(text, options, globals);
|
||||
text = showdown.subParser('strikethrough')(text, options, globals);
|
||||
|
||||
// we need to hash HTML tags inside spans
|
||||
text = showdown.subParser('hashHTMLSpans')(text, options, globals);
|
||||
|
||||
// now we encode amps and angles
|
||||
text = showdown.subParser('encodeAmpsAndAngles')(text, options, globals);
|
||||
|
||||
// Do hard breaks
|
||||
if (options.simpleLineBreaks) {
|
||||
// GFM style hard breaks
|
||||
|
2
dist/showdown.js.map
vendored
2
dist/showdown.js.map
vendored
File diff suppressed because one or more lines are too long
6
dist/showdown.min.js
vendored
6
dist/showdown.min.js
vendored
File diff suppressed because one or more lines are too long
2
dist/showdown.min.js.map
vendored
2
dist/showdown.min.js.map
vendored
File diff suppressed because one or more lines are too long
@ -302,7 +302,7 @@ showdown.Converter = function (converterOptions) {
|
||||
text = showdown.subParser('hashPreCodeTags')(text, options, globals);
|
||||
text = showdown.subParser('githubCodeBlocks')(text, options, globals);
|
||||
text = showdown.subParser('hashHTMLBlocks')(text, options, globals);
|
||||
text = showdown.subParser('hashHTMLSpans')(text, options, globals);
|
||||
text = showdown.subParser('hashCodeTags')(text, options, globals);
|
||||
text = showdown.subParser('stripLinkDefinitions')(text, options, globals);
|
||||
text = showdown.subParser('blockGamut')(text, options, globals);
|
||||
text = showdown.subParser('unhashHTMLSpans')(text, options, globals);
|
||||
|
@ -12,6 +12,12 @@ showdown.subParser('encodeAmpsAndAngles', function (text, options, globals) {
|
||||
// Encode naked <'s
|
||||
text = text.replace(/<(?![a-z\/?$!])/gi, '<');
|
||||
|
||||
// Encode <
|
||||
text = text.replace(/</g, '<');
|
||||
|
||||
// Encode >
|
||||
text = text.replace(/>/g, '>');
|
||||
|
||||
text = globals.converter._dispatch('encodeAmpsAndAngles.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
|
@ -5,12 +5,32 @@ showdown.subParser('hashHTMLSpans', function (text, options, globals) {
|
||||
'use strict';
|
||||
text = globals.converter._dispatch('hashHTMLSpans.before', text, options, globals);
|
||||
|
||||
var matches = showdown.helper.matchRecursiveRegExp(text, '<code\\b[^>]*>', '</code>', 'gi');
|
||||
|
||||
for (var i = 0; i < matches.length; ++i) {
|
||||
text = text.replace(matches[i][0], '¨C' + (globals.gHtmlSpans.push(matches[i][0]) - 1) + 'C');
|
||||
function hashHTMLSpan (html) {
|
||||
return '¨C' + (globals.gHtmlSpans.push(html) - 1) + 'C';
|
||||
}
|
||||
|
||||
// Hash Self Closing tags
|
||||
text = text.replace(/<[^>]+?\/>/gi, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
// Hash tags without properties
|
||||
text = text.replace(/<([^>]+?)>[\s\S]*?<\/\1>/g, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
// Hash tags with properties
|
||||
text = text.replace(/<([^>]+?)\s[^>]+?>[\s\S]*?<\/\1>/g, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
// Hash self closing tags without />
|
||||
text = text.replace(/<[^>]+?>/gi, function (wm) {
|
||||
return hashHTMLSpan(wm);
|
||||
});
|
||||
|
||||
/*showdown.helper.matchRecursiveRegExp(text, '<code\\b[^>]*>', '</code>', 'gi');*/
|
||||
|
||||
text = globals.converter._dispatch('hashHTMLSpans.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
@ -23,7 +43,19 @@ showdown.subParser('unhashHTMLSpans', function (text, options, globals) {
|
||||
text = globals.converter._dispatch('unhashHTMLSpans.before', text, options, globals);
|
||||
|
||||
for (var i = 0; i < globals.gHtmlSpans.length; ++i) {
|
||||
text = text.replace('¨C' + i + 'C', globals.gHtmlSpans[i]);
|
||||
var repText = globals.gHtmlSpans[i],
|
||||
// limiter to prevent infinite loop (assume 10 as limit for recurse)
|
||||
limit = 0;
|
||||
|
||||
while (/¨C(\d+)C/.test(repText)) {
|
||||
var num = RegExp.$1;
|
||||
repText = repText.replace('¨C' + num + 'C', globals.gHtmlSpans[num]);
|
||||
if (limit === 10) {
|
||||
break;
|
||||
}
|
||||
++limit;
|
||||
}
|
||||
text = text.replace('¨C' + i + 'C', repText);
|
||||
}
|
||||
|
||||
text = globals.converter._dispatch('unhashHTMLSpans.after', text, options, globals);
|
||||
|
@ -11,8 +11,21 @@ showdown.subParser('hashPreCodeTags', function (text, options, globals) {
|
||||
return '\n\n¨G' + (globals.ghCodeBlocks.push({text: wholeMatch, codeblock: codeblock}) - 1) + 'G\n\n';
|
||||
};
|
||||
|
||||
// Hash <pre><code>
|
||||
text = showdown.helper.replaceRecursiveRegExp(text, repFunc, '^ {0,3}<pre\\b[^>]*>\\s*<code\\b[^>]*>', '^ {0,3}</code>\\s*</pre>', 'gim');
|
||||
|
||||
text = globals.converter._dispatch('hashPreCodeTags.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
|
||||
showdown.subParser('hashCodeTags', function (text, options, globals) {
|
||||
'use strict';
|
||||
text = globals.converter._dispatch('hashCodeTags.before', text, options, globals);
|
||||
// Hash naked <code>
|
||||
var matches = showdown.helper.matchRecursiveRegExp(text, '<code\\b[^>]*>', '</code>', 'gi');
|
||||
for (var i = 0; i < matches.length; ++i) {
|
||||
text = text.replace(matches[i][0], '¨C' + (globals.gHtmlSpans.push(matches[i][0]) - 1) + 'C');
|
||||
}
|
||||
text = globals.converter._dispatch('hashCodeTags.after', text, options, globals);
|
||||
return text;
|
||||
});
|
||||
|
@ -19,10 +19,15 @@ showdown.subParser('spanGamut', function (text, options, globals) {
|
||||
// Must come after _DoAnchors(), because you can use < and >
|
||||
// delimiters in inline links like [this](<url>).
|
||||
text = showdown.subParser('autoLinks')(text, options, globals);
|
||||
text = showdown.subParser('encodeAmpsAndAngles')(text, options, globals);
|
||||
text = showdown.subParser('italicsAndBold')(text, options, globals);
|
||||
text = showdown.subParser('strikethrough')(text, options, globals);
|
||||
|
||||
// we need to hash HTML tags inside spans
|
||||
text = showdown.subParser('hashHTMLSpans')(text, options, globals);
|
||||
|
||||
// now we encode amps and angles
|
||||
text = showdown.subParser('encodeAmpsAndAngles')(text, options, globals);
|
||||
|
||||
// Do hard breaks
|
||||
if (options.simpleLineBreaks) {
|
||||
// GFM style hard breaks
|
||||
|
@ -1,3 +1,3 @@
|
||||
<h1 id="some-header">some header</h1>
|
||||
<h1 id="some-header-with--chars">some header with &+$,/:;=?@\"#{}|^~[]`\*()%.!' chars</h1>
|
||||
<h1 id="another-header--with--chars">another header > with < chars</h1>
|
||||
<h1 id="another-header--with--chars">another header > with < chars</h1>
|
||||
|
@ -0,0 +1,5 @@
|
||||
<p>this should be <parsed></parsed></p>
|
||||
<p>this should be <parsed></p>
|
||||
<p>this should be <parsed/></p>
|
||||
<p>this should> appear</p>
|
||||
<p>this text <should appear</p>
|
@ -0,0 +1,9 @@
|
||||
this should be <parsed></parsed>
|
||||
|
||||
this should be <parsed>
|
||||
|
||||
this should be <parsed/>
|
||||
|
||||
this should> appear
|
||||
|
||||
this text <should appear
|
@ -1 +1 @@
|
||||
<p>There is an <a href="http://validator.w3.org/check?uri=http://www.w3.org/&verbose=1">ampersand</a> in the URI.</p>
|
||||
<p>There is an <a href="http://validator.w3.org/check?uri=http://www.w3.org/&verbose=1">ampersand</a> in the URI.</p>
|
Loading…
x
Reference in New Issue
Block a user