From 5de88824fb0c04b6227b215b4cff23b6581895fc Mon Sep 17 00:00:00 2001 From: Ivan Posti Date: Sat, 20 Mar 2021 03:54:47 +0300 Subject: [PATCH] [IDEA-261987][Markdown] Encode element attributes, so the javascript won't choke special characters (cherry picked from commit 9b5709c45c0b073a2c1b0886c0df66b865adac8c) GitOrigin-RevId: 233640aa3d9733daa10d32f9ddad66c80623fd57 --- .../plugins/markdown/ui/preview/jcef/IncrementalDOM.kt | 10 ++-------- .../markdown/test/data/preview/id/htmlAttributes.js | 2 +- .../test/data/preview/id/javascriptCodeFence.js | 2 +- .../test/data/preview/id/javascriptCodeFenceSimple.js | 2 +- .../test/data/preview/id/specialCharactersEscape.js | 2 +- 5 files changed, 6 insertions(+), 12 deletions(-) diff --git a/plugins/markdown/src/org/intellij/plugins/markdown/ui/preview/jcef/IncrementalDOM.kt b/plugins/markdown/src/org/intellij/plugins/markdown/ui/preview/jcef/IncrementalDOM.kt index 8a86e87ae78a..b6503005541b 100644 --- a/plugins/markdown/src/org/intellij/plugins/markdown/ui/preview/jcef/IncrementalDOM.kt +++ b/plugins/markdown/src/org/intellij/plugins/markdown/ui/preview/jcef/IncrementalDOM.kt @@ -1,7 +1,6 @@ // Copyright 2000-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. package org.intellij.plugins.markdown.ui.preview.jcef -import com.intellij.openapi.util.text.StringUtil import org.jsoup.Jsoup import org.jsoup.nodes.Comment import org.jsoup.nodes.Node @@ -29,7 +28,7 @@ internal object IncrementalDOM { append(",'") append(attribute.key) append("','") - append(escapeAttributeContent(attribute.value)) + append(encodeArgument(attribute.value)) append("'") } append(");") @@ -76,7 +75,7 @@ internal object IncrementalDOM { // language=JavaScript return """ () => { - const o = (tag, ...attrs) => IncrementalDOM.elementOpen(tag, null, null, ...attrs); + const o = (tag, ...attrs) => IncrementalDOM.elementOpen(tag, null, null, ...attrs.map(decodeURIComponent)); const t = content => IncrementalDOM.text(decodeURIComponent(content)); const c = IncrementalDOM.elementClose; ${generateDomBuildCalls(html)} @@ -88,9 +87,4 @@ internal object IncrementalDOM { val document = Jsoup.parse(html) return traverse(document.body()).toString() } - - private fun escapeTagContent(string: String): String = - StringUtil.escapeChars(string, '\\', '`', '$') - - private fun escapeAttributeContent(string: String): String = StringUtil.escapeChar(string, '\'') } diff --git a/plugins/markdown/test/data/preview/id/htmlAttributes.js b/plugins/markdown/test/data/preview/id/htmlAttributes.js index a83a1fcdcf7f..4dd12d532b35 100644 --- a/plugins/markdown/test/data/preview/id/htmlAttributes.js +++ b/plugins/markdown/test/data/preview/id/htmlAttributes.js @@ -1 +1 @@ -o('div','md-src-pos','0..488');o('p','md-src-pos','0..54');o('span','md-src-pos','0..14');t(`Some%20text%20with`);c('span');t(`%20`);o('strong','attribute','value');o('span','md-src-pos','41..45');t(`some`);c('span');c('strong');c('p');o('p','md-src-pos','56..120');o('span','md-src-pos','56..75');t(`Some%20more%20text%20with`);c('span');t(`%20`);o('strong','attribute','value="df"');o('span','md-src-pos','107..111');t(`some`);c('span');c('strong');c('p');o('p','md-src-pos','122..176');o('span','md-src-pos','122..136');t(`Some%20text%20with`);c('span');t(`%20`);o('strong','attribute','value');o('span','md-src-pos','163..167');t(`some`);c('span');c('strong');c('p');o('p','md-src-pos','178..240');o('span','md-src-pos','178..192');t(`Some%20text%20with`);c('span');t(`%20`);o('strong','attribute','value=\'value\'');o('span','md-src-pos','227..231');t(`some`);c('span');c('strong');c('p');o('pre','md-src-pos','242..487');o('code','md-src-pos','242..487');o('span','md-src-pos','242..246');c('span');o('span','md-src-pos','246..312');t(`Some%20text%20with%20%3Cstrong%20attribute%3D%27value%27%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','313..399');t(`Some%20more%20text%20with%20%3Cstrong%20attribute%3D%27value%3D%22df%22%27%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','400..476');t(`Some%20text%20with%20%3Cstrong%20attribute%3D%22value%22%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','477..561');t(`Some%20text%20with%20%3Cstrong%20attribute%3D%22value%3D%27value%27%22%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','562..562');c('span');o('span','md-src-pos','484..487');c('span');c('code');c('pre');c('div'); +o('div','md-src-pos','0..488');o('p','md-src-pos','0..54');o('span','md-src-pos','0..14');t(`Some%20text%20with`);c('span');t(`%20`);o('strong','attribute','value');o('span','md-src-pos','41..45');t(`some`);c('span');c('strong');c('p');o('p','md-src-pos','56..120');o('span','md-src-pos','56..75');t(`Some%20more%20text%20with`);c('span');t(`%20`);o('strong','attribute','value%3D%22df%22');o('span','md-src-pos','107..111');t(`some`);c('span');c('strong');c('p');o('p','md-src-pos','122..176');o('span','md-src-pos','122..136');t(`Some%20text%20with`);c('span');t(`%20`);o('strong','attribute','value');o('span','md-src-pos','163..167');t(`some`);c('span');c('strong');c('p');o('p','md-src-pos','178..240');o('span','md-src-pos','178..192');t(`Some%20text%20with`);c('span');t(`%20`);o('strong','attribute','value%3D%27value%27');o('span','md-src-pos','227..231');t(`some`);c('span');c('strong');c('p');o('pre','md-src-pos','242..487');o('code','md-src-pos','242..487');o('span','md-src-pos','242..246');c('span');o('span','md-src-pos','246..312');t(`Some%20text%20with%20%3Cstrong%20attribute%3D%27value%27%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','313..399');t(`Some%20more%20text%20with%20%3Cstrong%20attribute%3D%27value%3D%22df%22%27%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','400..476');t(`Some%20text%20with%20%3Cstrong%20attribute%3D%22value%22%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','477..561');t(`Some%20text%20with%20%3Cstrong%20attribute%3D%22value%3D%27value%27%22%3Esome%3C%2Fstrong%3E`);c('span');t(`%0A`);o('span','md-src-pos','562..562');c('span');o('span','md-src-pos','484..487');c('span');c('code');c('pre');c('div'); \ No newline at end of file diff --git a/plugins/markdown/test/data/preview/id/javascriptCodeFence.js b/plugins/markdown/test/data/preview/id/javascriptCodeFence.js index 868086537431..bfc01dd413e4 100644 --- a/plugins/markdown/test/data/preview/id/javascriptCodeFence.js +++ b/plugins/markdown/test/data/preview/id/javascriptCodeFence.js @@ -1 +1 @@ -o('div','md-src-pos','0..225');o('pre','md-src-pos','0..225');o('code','class','language-javascript','md-src-pos','0..225');o('span','md-src-pos','0..14');c('span');o('span','md-src-pos','14..71');o('span','style','color:#cc7832');t(`const`);c('span');t(`%20value%20%3D%20`);o('span','style','color:#6a8759');t(`%22Some%20string`);c('span');o('span','style','color:#cc7832');t(`%5Cn`);c('span');o('span','style','color:#6a8759');t(`with`);c('span');o('span','style','color:#cc7832');t(`%5Ct`);c('span');o('span','style','color:#cc7832');t(`%5Cs`);c('span');o('span','style','color:#6a8759');t(`pecial`);c('span');o('span','style','color:#cc7832');t(`%5Cr`);c('span');o('span','style','color:#6a8759');t(`characters%22`);c('span');o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','71..137');o('span','style','color:#cc7832');t(`const`);c('span');t(`%20windowsPath%20%3D%20`);o('span','style','color:#6a8759');t(`%22C%3A`);c('span');o('span','style','color:#cc7832');t(`%5C`);c('span');o('span','style','color:#6a8759');t(`Documents`);c('span');o('span','style','color:#cc7832');t(`%5C`);c('span');o('span','style','color:#6a8759');t(`Newsletters`);c('span');o('span','style','color:#cc7832');t(`%5C`);c('span');o('span','style','color:#6a8759');t(`Summer2018.pdf%22`);c('span');o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','137..177');t(`console.log%28`);o('span','style','color:#6a8759');t(`%60`);c('span');o('span','style','color:#6a8759');t(`This%20is%20value%3A%20`);c('span');t(`%24%7Bvalue%7D`);o('span','style','color:#6a8759');t(`%60`);c('span');t(`%29`);o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','177..222');t(`console.log%28`);o('span','style','color:#6a8759');t(`%60`);c('span');o('span','style','color:#6a8759');t(`Windows%20path%3A%20`);c('span');t(`%24%7BwindowsPath%7D`);o('span','style','color:#6a8759');t(`%60`);c('span');t(`%29`);o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','222..223');c('span');o('span','md-src-pos','222..225');c('span');c('code');c('pre');c('div'); +o('div','md-src-pos','0..225');o('pre','md-src-pos','0..225');o('code','class','language-javascript','md-src-pos','0..225');o('span','md-src-pos','0..14');c('span');o('span','md-src-pos','14..71');o('span','style','color%3A%23cc7832');t(`const`);c('span');t(`%20value%20%3D%20`);o('span','style','color%3A%236a8759');t(`%22Some%20string`);c('span');o('span','style','color%3A%23cc7832');t(`%5Cn`);c('span');o('span','style','color%3A%236a8759');t(`with`);c('span');o('span','style','color%3A%23cc7832');t(`%5Ct`);c('span');o('span','style','color%3A%23cc7832');t(`%5Cs`);c('span');o('span','style','color%3A%236a8759');t(`pecial`);c('span');o('span','style','color%3A%23cc7832');t(`%5Cr`);c('span');o('span','style','color%3A%236a8759');t(`characters%22`);c('span');o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','71..137');o('span','style','color%3A%23cc7832');t(`const`);c('span');t(`%20windowsPath%20%3D%20`);o('span','style','color%3A%236a8759');t(`%22C%3A`);c('span');o('span','style','color%3A%23cc7832');t(`%5C`);c('span');o('span','style','color%3A%236a8759');t(`Documents`);c('span');o('span','style','color%3A%23cc7832');t(`%5C`);c('span');o('span','style','color%3A%236a8759');t(`Newsletters`);c('span');o('span','style','color%3A%23cc7832');t(`%5C`);c('span');o('span','style','color%3A%236a8759');t(`Summer2018.pdf%22`);c('span');o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','137..177');t(`console.log%28`);o('span','style','color%3A%236a8759');t(`%60`);c('span');o('span','style','color%3A%236a8759');t(`This%20is%20value%3A%20`);c('span');t(`%24%7Bvalue%7D`);o('span','style','color%3A%236a8759');t(`%60`);c('span');t(`%29`);o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','177..222');t(`console.log%28`);o('span','style','color%3A%236a8759');t(`%60`);c('span');o('span','style','color%3A%236a8759');t(`Windows%20path%3A%20`);c('span');t(`%24%7BwindowsPath%7D`);o('span','style','color%3A%236a8759');t(`%60`);c('span');t(`%29`);o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','222..223');c('span');o('span','md-src-pos','222..225');c('span');c('code');c('pre');c('div'); \ No newline at end of file diff --git a/plugins/markdown/test/data/preview/id/javascriptCodeFenceSimple.js b/plugins/markdown/test/data/preview/id/javascriptCodeFenceSimple.js index 9ea6dc408b9d..3d5559a3c36e 100644 --- a/plugins/markdown/test/data/preview/id/javascriptCodeFenceSimple.js +++ b/plugins/markdown/test/data/preview/id/javascriptCodeFenceSimple.js @@ -1 +1 @@ -o('div');o('div','md-src-pos','0..64');o('pre','md-src-pos','0..64');o('code','class','language-javascript','md-src-pos','0..64');o('span','md-src-pos','0..14');c('span');o('span','md-src-pos','14..29');t(`let%20b%20%3D%20`);o('span','style','color: rgb(6, 125, 23);');t(`%60`);c('span');o('span','style','color: rgb(6, 125, 23);');t(`Dear`);c('span');o('span','style','color: rgb(6, 125, 23);');t(`%60`);c('span');c('span');t(`%0A`);o('span','md-src-pos','29..61');t(`let%20a%20%3D%20`);o('span','style','color: rgb(6, 125, 23);');t(`%60`);c('span');o('span','style','color: rgb(6, 125, 23);');t(`%24%7Bb%7D%20mister%20Anderson.`);c('span');o('span','style','color: rgb(6, 125, 23);');t(`%60`);c('span');c('span');t(`%0A`);o('span','md-src-pos','60..61');c('span');o('span','md-src-pos','60..63');c('span');c('code');c('pre');c('div');c('div'); +o('div');o('div','md-src-pos','0..64');o('pre','md-src-pos','0..64');o('code','class','language-javascript','md-src-pos','0..64');o('span','md-src-pos','0..14');c('span');o('span','md-src-pos','14..29');t(`let%20b%20%3D%20`);o('span','style','color%3A%20rgb%286%2C%20125%2C%2023%29%3B');t(`%60`);c('span');o('span','style','color%3A%20rgb%286%2C%20125%2C%2023%29%3B');t(`Dear`);c('span');o('span','style','color%3A%20rgb%286%2C%20125%2C%2023%29%3B');t(`%60`);c('span');c('span');t(`%0A`);o('span','md-src-pos','29..61');t(`let%20a%20%3D%20`);o('span','style','color%3A%20rgb%286%2C%20125%2C%2023%29%3B');t(`%60`);c('span');o('span','style','color%3A%20rgb%286%2C%20125%2C%2023%29%3B');t(`%24%7Bb%7D%20mister%20Anderson.`);c('span');o('span','style','color%3A%20rgb%286%2C%20125%2C%2023%29%3B');t(`%60`);c('span');c('span');t(`%0A`);o('span','md-src-pos','60..61');c('span');o('span','md-src-pos','60..63');c('span');c('code');c('pre');c('div');c('div'); \ No newline at end of file diff --git a/plugins/markdown/test/data/preview/id/specialCharactersEscape.js b/plugins/markdown/test/data/preview/id/specialCharactersEscape.js index bad37d813d8d..a6f694f493e8 100644 --- a/plugins/markdown/test/data/preview/id/specialCharactersEscape.js +++ b/plugins/markdown/test/data/preview/id/specialCharactersEscape.js @@ -1 +1 @@ -o('div','md-src-pos','0..164');o('pre','md-src-pos','0..65');o('code','md-src-pos','0..65');o('span','md-src-pos','0..4');c('span');o('span','md-src-pos','4..22');t(`%5C0%5Ca%5Cb%5Ct%5Cn%5Cv%5Cf%5Cr%5Ce`);c('span');t(`%0A`);o('span','md-src-pos','23..42');t(`%27%22%60%5C%27%5C%22%5C%60`);c('span');t(`%0A`);o('span','md-src-pos','43..46');t(`%5C%5Cn`);c('span');t(`%0A`);o('span','md-src-pos','47..49');t(`%5Cn`);c('span');t(`%0A`);o('span','md-src-pos','50..75');t(`%24%25%5E%26*%7B%7D%5B%5D%28%29%2C.%2F%3F%2F%7E%5C%2F%5C%5C`);c('span');t(`%0A`);o('span','md-src-pos','76..76');c('span');o('span','md-src-pos','62..65');c('span');c('code');c('pre');o('pre','md-src-pos','67..163');o('code','class','language-javascript','md-src-pos','67..163');o('span','md-src-pos','45..59');c('span');o('span','md-src-pos','59..78');t(`console.log%28`);o('span','style','color:#6a8759');t(`%22`);c('span');o('span','style','color:#cc7832');t(`%5C%22`);c('span');o('span','style','color:#6a8759');t(`%22`);c('span');t(`%29`);o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','78..97');t(`console.log%28`);o('span','style','color:#6a8759');t(`%22`);c('span');o('span','style','color:#cc7832');t(`%5C%27`);c('span');o('span','style','color:#6a8759');t(`%22`);c('span');t(`%29`);o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','97..116');t(`console.log%28`);o('span','style','color:#6a8759');t(`%22`);c('span');o('span','style','color:#cc7832');t(`%5C%60`);c('span');o('span','style','color:#6a8759');t(`%22`);c('span');t(`%29`);o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','116..138');t(`console.log%28`);o('span','style','color:#6a8759');t(`%22`);c('span');o('span','style','color:#cc7832');t(`%5Cn`);c('span');o('span','style','color:#cc7832');t(`%5C%5C`);c('span');o('span','style','color:#6a8759');t(`n%22`);c('span');t(`%29`);o('span','style','color:#cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','138..139');c('span');o('span','md-src-pos','138..141');c('span');c('code');c('pre');c('div'); +o('div','md-src-pos','0..164');o('pre','md-src-pos','0..65');o('code','md-src-pos','0..65');o('span','md-src-pos','0..4');c('span');o('span','md-src-pos','4..22');t(`%5C0%5Ca%5Cb%5Ct%5Cn%5Cv%5Cf%5Cr%5Ce`);c('span');t(`%0A`);o('span','md-src-pos','23..42');t(`%27%22%60%5C%27%5C%22%5C%60`);c('span');t(`%0A`);o('span','md-src-pos','43..46');t(`%5C%5Cn`);c('span');t(`%0A`);o('span','md-src-pos','47..49');t(`%5Cn`);c('span');t(`%0A`);o('span','md-src-pos','50..75');t(`%24%25%5E%26*%7B%7D%5B%5D%28%29%2C.%2F%3F%2F%7E%5C%2F%5C%5C`);c('span');t(`%0A`);o('span','md-src-pos','76..76');c('span');o('span','md-src-pos','62..65');c('span');c('code');c('pre');o('pre','md-src-pos','67..163');o('code','class','language-javascript','md-src-pos','67..163');o('span','md-src-pos','45..59');c('span');o('span','md-src-pos','59..78');t(`console.log%28`);o('span','style','color%3A%236a8759');t(`%22`);c('span');o('span','style','color%3A%23cc7832');t(`%5C%22`);c('span');o('span','style','color%3A%236a8759');t(`%22`);c('span');t(`%29`);o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','78..97');t(`console.log%28`);o('span','style','color%3A%236a8759');t(`%22`);c('span');o('span','style','color%3A%23cc7832');t(`%5C%27`);c('span');o('span','style','color%3A%236a8759');t(`%22`);c('span');t(`%29`);o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','97..116');t(`console.log%28`);o('span','style','color%3A%236a8759');t(`%22`);c('span');o('span','style','color%3A%23cc7832');t(`%5C%60`);c('span');o('span','style','color%3A%236a8759');t(`%22`);c('span');t(`%29`);o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','116..138');t(`console.log%28`);o('span','style','color%3A%236a8759');t(`%22`);c('span');o('span','style','color%3A%23cc7832');t(`%5Cn`);c('span');o('span','style','color%3A%23cc7832');t(`%5C%5C`);c('span');o('span','style','color%3A%236a8759');t(`n%22`);c('span');t(`%29`);o('span','style','color%3A%23cc7832');t(`%3B`);c('span');c('span');t(`%0A`);o('span','md-src-pos','138..139');c('span');o('span','md-src-pos','138..141');c('span');c('code');c('pre');c('div'); \ No newline at end of file