git.iko.soy/typeable/pandoc
on master help sign in
Removed HTML sanitization.

This is better done on the resulting HTML; use the xss-sanitize library for this. xss-sanitize is based on pandoc's sanitization, but improves it. - Removed stateSanitize from ParserState. - Removed --sanitize-html option.

commit5770ceca36a7ab15ad43b3d949c749f6425ecbcb authorJohn MacFarlane <jgm@berkeley.edu> dateFri 10 Dec 2010, 12:26 (16 years ago) parent17d48cf
5 files changed+10−118
README−6 src/Text/Pandoc/Parsing.hs−2 src/Text/Pandoc/Readers/HTML.hs+5−90 src/Text/Pandoc/Readers/Markdown.hs+5−11 src/pandoc.hs−9
README−6
@@ -269,12 +269,6 @@ Options
269269: Disable text wrapping in output. By default, text is wrapped
270270 appropriately for the output format.
271271
272−`--sanitize-html`
273−: Sanitizes HTML (in markdown or HTML input) using a whitelist.
274− Unsafe tags are replaced by HTML comments; unsafe attributes
275− are omitted. URIs in links and images are also checked against a
276− whitelist of URI schemes.
277−
278272`--email-obfuscation=`*none|javascript|references*
279273: Specify a method for obfuscating `mailto:` links in HTML documents.
280274 *none* leaves `mailto:` links as they are. *javascript* obfuscates
src/Text/Pandoc/Parsing.hs−2
@@ -586,7 +586,6 @@ data ParserState = ParserState
586586 { stateParseRaw :: Bool, -- ^ Parse raw HTML and LaTeX?
587587 stateParserContext :: ParserContext, -- ^ Inside list?
588588 stateQuoteContext :: QuoteContext, -- ^ Inside quoted environment?
589− stateSanitizeHTML :: Bool, -- ^ Sanitize HTML?
590589 stateKeys :: KeyTable, -- ^ List of reference keys
591590 stateCitations :: [String], -- ^ List of available citations
592591 stateNotes :: NoteTable, -- ^ List of notes
@@ -614,7 +613,6 @@ defaultParserState =
614613 ParserState { stateParseRaw = False,
615614 stateParserContext = NullState,
616615 stateQuoteContext = NoQuote,
617− stateSanitizeHTML = False,
618616 stateKeys = M.empty,
619617 stateCitations = [],
620618 stateNotes = [],
src/Text/Pandoc/Readers/HTML.hs+5−90
@@ -40,7 +40,6 @@ module Text.Pandoc.Readers.HTML (
4040 extractTagType,
4141 htmlBlockElement,
4242 htmlComment,
43− unsanitaryURI
4443 ) where
4544
4645import Text.ParserCombinators.Parsec
@@ -51,7 +50,6 @@ import Text.Pandoc.CharacterReferences ( decodeCharacterReferences )
5150import Data.Maybe ( fromMaybe )
5251import Data.List ( isPrefixOf, isSuffixOf, intercalate )
5352import Data.Char ( toLower, isAlphaNum )
54−import Network.URI ( parseURIReference, URI (..) )
5553import Control.Monad ( liftM, when )
5654
5755-- | Convert HTML-formatted string to 'Pandoc' document.
@@ -85,36 +83,6 @@ blockHtmlTags = ["address", "blockquote", "body", "center", "dir", "div",
8583 "dt", "frameset", "li", "tbody", "td", "tfoot",
8684 "th", "thead", "tr", "script", "style"]
8785
88−sanitaryTags :: [[Char]]
89−sanitaryTags = ["a", "abbr", "acronym", "address", "area", "b", "big",
90− "blockquote", "br", "button", "caption", "center",
91− "cite", "code", "col", "colgroup", "dd", "del", "dfn",
92− "dir", "div", "dl", "dt", "em", "fieldset", "font",
93− "form", "h1", "h2", "h3", "h4", "h5", "h6", "hr",
94− "i", "img", "input", "ins", "kbd", "label", "legend",
95− "li", "map", "menu", "ol", "optgroup", "option", "p",
96− "pre", "q", "s", "samp", "select", "small", "span",
97− "strike", "strong", "sub", "sup", "table", "tbody",
98− "td", "textarea", "tfoot", "th", "thead", "tr", "tt",
99− "u", "ul", "var"]
100−
101−sanitaryAttributes :: [[Char]]
102−sanitaryAttributes = ["abbr", "accept", "accept-charset",
103− "accesskey", "action", "align", "alt", "axis",
104− "border", "cellpadding", "cellspacing", "char",
105− "charoff", "charset", "checked", "cite", "class",
106− "clear", "cols", "colspan", "color", "compact",
107− "coords", "datetime", "dir", "disabled",
108− "enctype", "for", "frame", "headers", "height",
109− "href", "hreflang", "hspace", "id", "ismap",
110− "label", "lang", "longdesc", "maxlength", "media",
111− "method", "multiple", "name", "nohref", "noshade",
112− "nowrap", "prompt", "readonly", "rel", "rev",
113− "rows", "rowspan", "rules", "scope", "selected",
114− "shape", "size", "span", "src", "start",
115− "summary", "tabindex", "target", "title", "type",
116− "usemap", "valign", "value", "vspace", "width"]
117−
11886-- taken from HXT and extended
11987
12088closes :: String -> String -> Bool
@@ -153,41 +121,6 @@ _ `closes` _ = False
153121-- HTML utility functions
154122--
155123
156−-- | Returns @True@ if sanitization is specified and the specified tag is
157−-- not on the sanitized tag list.
158−unsanitaryTag :: [Char]
159− -> GenParser tok ParserState Bool
160−unsanitaryTag tag = do
161− st <- getState
162− return $ stateSanitizeHTML st && tag `notElem` sanitaryTags
163−
164−-- | returns @True@ if sanitization is specified and the specified attribute
165−-- is not on the sanitized attribute list.
166−unsanitaryAttribute :: ([Char], String, t)
167− -> GenParser tok ParserState Bool
168−unsanitaryAttribute (attr, val, _) = do
169− st <- getState
170− return $ stateSanitizeHTML st &&
171− (attr `notElem` sanitaryAttributes ||
172− (attr `elem` ["href","src"] && unsanitaryURI val))
173−
174−-- | Returns @True@ if the specified URI is potentially a security risk.
175−unsanitaryURI :: String -> Bool
176−unsanitaryURI u =
177− let safeURISchemes = [ "", "http:", "https:", "ftp:", "mailto:", "file:",
178− "telnet:", "gopher:", "aaa:", "aaas:", "acap:", "cap:", "cid:",
179− "crid:", "dav:", "dict:", "dns:", "fax:", "go:", "h323:", "im:",
180− "imap:", "ldap:", "mid:", "news:", "nfs:", "nntp:", "pop:",
181− "pres:", "sip:", "sips:", "snmp:", "tel:", "urn:", "wais:",
182− "xmpp:", "z39.50r:", "z39.50s:", "aim:", "callto:", "cvs:",
183− "ed2k:", "feed:", "fish:", "gg:", "irc:", "ircs:", "lastfm:",
184− "ldaps:", "magnet:", "mms:", "msnim:", "notes:", "rsync:",
185− "secondlife:", "skype:", "ssh:", "sftp:", "smb:", "sms:",
186− "snews:", "webcal:", "ymsgr:"]
187− in case parseURIReference (escapeURI u) of
188− Just p -> (map toLower $ uriScheme p) `notElem` safeURISchemes
189− Nothing -> True
190−
191124-- | Read blocks until end tag.
192125blocksTilEnd :: String -> GenParser Char ParserState [Block]
193126blocksTilEnd tag = do
@@ -240,10 +173,7 @@ anyHtmlTag = try $ do
240173 char '>'
241174 let result = "<" ++ tag ++
242175 concatMap (\(_, _, raw) -> (' ':raw)) attribs ++ ender' ++ ">"
243− unsanitary <- unsanitaryTag tag
244− if unsanitary
245− then return $ "<!-- unsafe HTML removed -->"
246− else return result
176+ return result
247177
248178anyHtmlEndTag :: GenParser Char ParserState [Char]
249179anyHtmlEndTag = try $ do
@@ -255,10 +185,7 @@ anyHtmlEndTag = try $ do
255185 spaces
256186 char '>'
257187 let result = "</" ++ tag ++ ">"
258− unsanitary <- unsanitaryTag tag
259− if unsanitary
260− then return $ "<!-- unsafe HTML removed -->"
261− else return result
188+ return result
262189
263190htmlTag :: Bool
264191 -> String
@@ -294,16 +221,10 @@ quoted quoteChar = do
294221 (many (noneOf [quoteChar]))
295222 return (result, [quoteChar])
296223
297−nullAttribute :: ([Char], [Char], [Char])
298−nullAttribute = ("", "", "")
299−
300224htmlAttribute :: GenParser Char ParserState ([Char], [Char], [Char])
301225htmlAttribute = do
302226 attr <- htmlRegularAttribute <|> htmlMinimizedAttribute
303− unsanitary <- unsanitaryAttribute attr
304− if unsanitary
305− then return nullAttribute
306− else return attr
227+ return attr
307228
308229-- minimized boolean attribute
309230htmlMinimizedAttribute :: GenParser Char st ([Char], [Char], [Char])
@@ -364,10 +285,7 @@ htmlScript = try $ do
364285 lookAhead $ htmlOpenTag "script"
365286 open <- anyHtmlTag
366287 rest <- liftM concat $ manyTill scriptChunk (htmlEndTag "script")
367− st <- getState
368− if stateSanitizeHTML st && not ("script" `elem` sanitaryTags)
369− then return "<!-- unsafe HTML removed -->"
370− else return $ open ++ rest ++ "</script>"
288+ return $ open ++ rest ++ "</script>"
371289
372290scriptChunk :: GenParser Char ParserState [Char]
373291scriptChunk = jsComment <|> jsString <|> jsChars
@@ -399,10 +317,7 @@ htmlStyle = try $ do
399317 lookAhead $ htmlOpenTag "style"
400318 open <- anyHtmlTag
401319 rest <- manyTill anyChar (htmlEndTag "style")
402− st <- getState
403− if stateSanitizeHTML st && not ("style" `elem` sanitaryTags)
404− then return "<!-- unsafe HTML removed -->"
405− else return $ open ++ rest ++ "</style>"
320+ return $ open ++ rest ++ "</style>"
406321
407322htmlBlockElement :: GenParser Char ParserState [Char]
408323htmlBlockElement = choice [ htmlScript, htmlStyle, htmlComment, xmlDec, definition ]
src/Text/Pandoc/Readers/Markdown.hs+5−11
@@ -41,7 +41,7 @@ import Text.Pandoc.Readers.LaTeX ( rawLaTeXInline, rawLaTeXEnvironment' )
4141import Text.Pandoc.Readers.HTML ( rawHtmlBlock, anyHtmlBlockTag,
4242 anyHtmlInlineTag, anyHtmlTag,
4343 anyHtmlEndTag, htmlEndTag, extractTagType,
44− htmlBlockElement, htmlComment, unsanitaryURI )
44+ htmlBlockElement, htmlComment )
4545import Text.Pandoc.CharacterReferences ( decodeCharacterReferences )
4646import Text.ParserCombinators.Parsec
4747import Control.Monad (when, liftM, guard)
@@ -1152,10 +1152,7 @@ link :: GenParser Char ParserState Inline
11521152link = try $ do
11531153 lab <- reference
11541154 (src, tit) <- source <|> referenceLink lab
1155− sanitize <- getState >>= return . stateSanitizeHTML
1156− if sanitize && unsanitaryURI src
1157− then fail "Unsanitary URI"
1158− else return $ Link lab (src, tit)
1155+ return $ Link lab (src, tit)
11591156
11601157-- a link like [this][ref] or [this][] or [this]
11611158referenceLink :: [Inline]
@@ -1175,12 +1172,9 @@ autoLink = try $ do
11751172 (orig, src) <- uri <|> emailAddress
11761173 char '>'
11771174 st <- getState
1178− let sanitize = stateSanitizeHTML st
1179− if sanitize && unsanitaryURI src
1180− then fail "Unsanitary URI"
1181− else return $ if stateStrict st
1182− then Link [Str orig] (src, "")
1183− else Link [Code orig] (src, "")
1175+ return $ if stateStrict st
1176+ then Link [Str orig] (src, "")
1177+ else Link [Code orig] (src, "")
11841178
11851179image :: GenParser Char ParserState Inline
11861180image = try $ do
src/pandoc.hs−9
@@ -155,7 +155,6 @@ data Opt = Opt
155155 , optStrict :: Bool -- ^ Use strict markdown syntax
156156 , optReferenceLinks :: Bool -- ^ Use reference links in writing markdown, rst
157157 , optWrapText :: Bool -- ^ Wrap text
158− , optSanitizeHTML :: Bool -- ^ Sanitize HTML
159158 , optPlugins :: [Pandoc -> IO Pandoc] -- ^ Plugins to apply
160159 , optEmailObfuscation :: ObfuscationMethod
161160 , optIdentifierPrefix :: String
@@ -194,7 +193,6 @@ defaultOpts = Opt
194193 , optStrict = False
195194 , optReferenceLinks = False
196195 , optWrapText = True
197− , optSanitizeHTML = False
198196 , optPlugins = []
199197 , optEmailObfuscation = JavascriptObfuscation
200198 , optIdentifierPrefix = ""
@@ -344,11 +342,6 @@ options =
344342 (\opt -> return opt { optWrapText = False }))
345343 "" -- "Do not wrap text in output"
346344
347− , Option "" ["sanitize-html"]
348− (NoArg
349− (\opt -> return opt { optSanitizeHTML = True }))
350− "" -- "Sanitize HTML"
351−
352345 , Option "" ["email-obfuscation"]
353346 (ReqArg
354347 (\arg opt -> do
@@ -673,7 +666,6 @@ main = do
673666 , optStrict = strict
674667 , optReferenceLinks = referenceLinks
675668 , optWrapText = wrap
676− , optSanitizeHTML = sanitize
677669 , optEmailObfuscation = obfuscationMethod
678670 , optIdentifierPrefix = idPrefix
679671 , optIndentedCodeClasses = codeBlockClasses
@@ -772,7 +764,6 @@ main = do
772764 let startParserState =
773765 defaultParserState { stateParseRaw = parseRaw,
774766 stateTabStop = tabStop,
775− stateSanitizeHTML = sanitize,
776767 stateLiterateHaskell = "+lhs" `isSuffixOf` readerName' ||
777768 lhsExtension sources,
778769 stateStandalone = standalone',