diff --git a/Project.toml b/Project.toml index ee463d409..dc5e86e2e 100644 --- a/Project.toml +++ b/Project.toml @@ -1,7 +1,7 @@ name = "JuDoc" uuid = "4ca9428c-4c75-11e9-2efb-bf5cb6c1e8f8" authors = ["Thibaut Lienart "] -version = "0.4" +version = "0.4.1" [deps] Dates = "ade2ca70-3891-5945-98fb-dc099432e06a" diff --git a/src/converter/js_prerender.jl b/src/converter/js_prerender.jl index 98b78d223..ab5784edf 100644 --- a/src/converter/js_prerender.jl +++ b/src/converter/js_prerender.jl @@ -63,11 +63,16 @@ function js_prerender_highlight(hs::String)::String # core code cs = subs(hs, nextind(hs, matchrange(co).stop), prevind(hs, matchrange(cc).start)) cs = escape_string(cs) - + # lang lang = co.captures[2] if isnothing(lang) write(jsbuffer, """console.log("
$cs
");\n""") else + if lang == "html" && is_html_escaped(cs) + # corner case, see https://github.com/tlienart/JuDoc.jl/issues/326 + # highlight will re-escape the string further. + cs = html_unescape(cs) |> escape_string + end # add to content of jsbuffer write(jsbuffer, """console.log("
" + hljs.highlight("$lang", "$cs").value + "
");""") end @@ -113,3 +118,27 @@ function js2html(hs::String, jsbuffer::IOBuffer, matches::Vector{RegexMatch}, return String(take!(htmls)) end + + +# Copied from https://github.com/JuliaLang/julia/blob/acb7bd93fb2d5adbbabeaed9f39ab3c85495b02f/stdlib/Markdown/src/render/html.jl#L25-L31 +const _htmlescape_chars = LittleDict( + '<' => "<", + '>' => ">", + '"' => """, + '&' => "&" + ) +for ch in "'`!\$%()=+{}[]" + _htmlescape_chars[ch] = "&#$(Int(ch));" +end + +const _htmlesc_to = values(_htmlescape_chars) |> collect + +is_html_escaped(cs::String) = !isnothing(findfirst(ss -> occursin(ss, cs), _htmlesc_to)) + +function html_unescape(cs::String) + # this is a bit inefficient but whatever, `cs` shouldn't be very long. + for (ssfrom, ssto) in _htmlescape_chars + cs = replace(cs, ssto => ssfrom) + end + return cs +end diff --git a/test/global/html_esc.jl b/test/global/html_esc.jl new file mode 100644 index 000000000..4f2b188b9 --- /dev/null +++ b/test/global/html_esc.jl @@ -0,0 +1,8 @@ +# See https://github.com/tlienart/JuDoc.jl/issues/326 + +@testset "Issue 326" begin + h1 = "
Blah
" + h1e = Markdown.htmlesc(h1) + @test J.is_html_escaped(h1e) + @test J.html_unescape(h1e) == h1 +end diff --git a/test/runtests.jl b/test/runtests.jl index adc33b1d8..e689b806c 100644 --- a/test/runtests.jl +++ b/test/runtests.jl @@ -49,6 +49,7 @@ println("GLOBAL") include("global/cases1.jl") include("global/cases2.jl") include("global/ordering.jl") +include("global/html_esc.jl") begin # create temp dir to do complete integration testing (has to be here in order