Commit 7776b5b6 authored by Jean-Philippe Lang's avatar Jean-Philippe Lang

Escape textile titles and styles (#2377).

git-svn-id: svn+ssh://rubyforge.org/var/svn/redmine/trunk@2170 e93f8b46-1217-0410-a6f0-8f06a7374b81
parent e48f0f04
...@@ -408,7 +408,7 @@ class RedCloth3 < String ...@@ -408,7 +408,7 @@ class RedCloth3 < String
# [ /"(?=[#{PUNCT_Q}]*[\s#{PUNCT_NOQ}])/, '&#8221;' ], # double closing # [ /"(?=[#{PUNCT_Q}]*[\s#{PUNCT_NOQ}])/, '&#8221;' ], # double closing
# [ /"/, '&#8220;' ], # double opening # [ /"/, '&#8220;' ], # double opening
# [ /\b( )?\.{3}/, '\1&#8230;' ], # ellipsis # [ /\b( )?\.{3}/, '\1&#8230;' ], # ellipsis
[ /\b([A-Z][A-Z0-9]{2,})\b(?:[(]([^)]*)[)])/, '<acronym title="\2">\1</acronym>' ], # 3+ uppercase acronym # [ /\b([A-Z][A-Z0-9]{2,})\b(?:[(]([^)]*)[)])/, '<acronym title="\2">\1</acronym>' ], # 3+ uppercase acronym
# [ /(^|[^"][>\s])([A-Z][A-Z0-9 ]+[A-Z0-9])([^<A-Za-z0-9]|$)/, '\1<span class="caps">\2</span>\3', :no_span_caps ], # 3+ uppercase caps # [ /(^|[^"][>\s])([A-Z][A-Z0-9 ]+[A-Z0-9])([^<A-Za-z0-9]|$)/, '\1<span class="caps">\2</span>\3', :no_span_caps ], # 3+ uppercase caps
# [ /(\.\s)?\s?--\s?/, '\1&#8212;' ], # em dash # [ /(\.\s)?\s?--\s?/, '\1&#8212;' ], # em dash
# [ /\s->\s/, ' &rarr; ' ], # right arrow # [ /\s->\s/, ' &rarr; ' ], # right arrow
...@@ -448,9 +448,12 @@ class RedCloth3 < String ...@@ -448,9 +448,12 @@ class RedCloth3 < String
# Search and replace for Textile glyphs (quotes, dashes, other symbols) # Search and replace for Textile glyphs (quotes, dashes, other symbols)
def pgl( text ) def pgl( text )
GLYPHS.each do |re, resub, tog| #GLYPHS.each do |re, resub, tog|
next if tog and method( tog ).call # next if tog and method( tog ).call
text.gsub! re, resub # text.gsub! re, resub
#end
text.gsub!(/\b([A-Z][A-Z0-9]{2,})\b(?:[(]([^)]*)[)])/) do |m|
"<acronym title=\"#{htmlesc $2}\">#{$1}</acronym>"
end end
end end
...@@ -467,7 +470,7 @@ class RedCloth3 < String ...@@ -467,7 +470,7 @@ class RedCloth3 < String
style << "vertical-align:#{ v_align( $& ) };" if text =~ A_VLGN style << "vertical-align:#{ v_align( $& ) };" if text =~ A_VLGN
end end
style << "#{ $1 };" if not filter_styles and style << "#{ htmlesc $1 };" if not filter_styles and
text.sub!( /\{([^}]*)\}/, '' ) text.sub!( /\{([^}]*)\}/, '' )
lang = $1 if lang = $1 if
...@@ -810,7 +813,7 @@ class RedCloth3 < String ...@@ -810,7 +813,7 @@ class RedCloth3 < String
end end
atts = pba( atts ) atts = pba( atts )
atts = " href=\"#{ url }#{ slash }\"#{ atts }" atts = " href=\"#{ url }#{ slash }\"#{ atts }"
atts << " title=\"#{ title }\"" if title atts << " title=\"#{ htmlesc title }\"" if title
atts = shelve( atts ) if atts atts = shelve( atts ) if atts
external = (url =~ /^https?:\/\//) ? ' class="external"' : '' external = (url =~ /^https?:\/\//) ? ' class="external"' : ''
......
...@@ -76,6 +76,15 @@ class ApplicationHelperTest < HelperTestCase ...@@ -76,6 +76,15 @@ class ApplicationHelperTest < HelperTestCase
to_test.each { |text, result| assert_equal "<p>#{result}</p>", textilizable(text) } to_test.each { |text, result| assert_equal "<p>#{result}</p>", textilizable(text) }
end end
def test_acronyms
to_test = {
'this is an acronym: GPL(General Public License)' => 'this is an acronym: <acronym title="General Public License">GPL</acronym>',
'GPL(This is a double-quoted "title")' => '<acronym title="This is a double-quoted &quot;title&quot;">GPL</acronym>',
}
to_test.each { |text, result| assert_equal "<p>#{result}</p>", textilizable(text) }
end
def test_attached_images def test_attached_images
to_test = { to_test = {
'Inline image: !logo.gif!' => 'Inline image: <img src="/attachments/download/3" title="This is a logo" alt="This is a logo" />', 'Inline image: !logo.gif!' => 'Inline image: <img src="/attachments/download/3" title="This is a logo" alt="This is a logo" />',
...@@ -90,6 +99,7 @@ class ApplicationHelperTest < HelperTestCase ...@@ -90,6 +99,7 @@ class ApplicationHelperTest < HelperTestCase
'This is a "link":http://foo.bar' => 'This is a <a href="http://foo.bar" class="external">link</a>', 'This is a "link":http://foo.bar' => 'This is a <a href="http://foo.bar" class="external">link</a>',
'This is an intern "link":/foo/bar' => 'This is an intern <a href="/foo/bar">link</a>', 'This is an intern "link":/foo/bar' => 'This is an intern <a href="/foo/bar">link</a>',
'"link (Link title)":http://foo.bar' => '<a href="http://foo.bar" title="Link title" class="external">link</a>', '"link (Link title)":http://foo.bar' => '<a href="http://foo.bar" title="Link title" class="external">link</a>',
'"link (Link title with "double-quotes")":http://foo.bar' => '<a href="http://foo.bar" title="Link title with &quot;double-quotes&quot;" class="external">link</a>',
"This is not a \"Link\":\n\nAnother paragraph" => "This is not a \"Link\":</p>\n\n\n\t<p>Another paragraph", "This is not a \"Link\":\n\nAnother paragraph" => "This is not a \"Link\":</p>\n\n\n\t<p>Another paragraph",
# no multiline link text # no multiline link text
"This is a double quote \"on the first line\nand another on a second line\":test" => "This is a double quote \"on the first line<br />\nand another on a second line\":test" "This is a double quote \"on the first line\nand another on a second line\":test" => "This is a double quote \"on the first line<br />\nand another on a second line\":test"
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment