git.iko.soy/typeable/pandoc
on master help sign in
Merge pull request #1781 from bergey/rst

parse RST quoted literal blocks and class directives

commit704cfc1e3c2b6bc97cc315c92671dc47e9c76977 authorJohn MacFarlane <jgm@berkeley.edu> dateMon 1 Dec 2014, 13:21 (12 years ago) parent4d296f774c1b54
2 files changed+39−4
src/Text/Pandoc/Readers/RST.hs+17−3 tests/Tests/Readers/RST.hs+22−1
src/Text/Pandoc/Readers/RST.hs+17−3
@@ -47,7 +47,7 @@ import Text.Pandoc.Builder (Inlines, Blocks, trimInlines, (<>))
4747import qualified Text.Pandoc.Builder as B
4848import Data.Monoid (mconcat, mempty)
4949import Data.Sequence (viewr, ViewR(..))
50−import Data.Char (toLower, isHexDigit)
50+import Data.Char (toLower, isHexDigit, isSpace)
5151
5252-- | Parse reStructuredText string and return Pandoc document.
5353readRST :: ReaderOptions -- ^ Reader options
@@ -335,6 +335,13 @@ indentedBlock = try $ do
335335 optional blanklines
336336 return $ unlines lns
337337
338+quotedBlock :: Parser [Char] st [Char]
339+quotedBlock = try $ do
340+ quote <- lookAhead $ oneOf "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~"
341+ lns <- many1 $ lookAhead (char quote) >> anyLine
342+ optional blanklines
343+ return $ unlines lns
344+
338345codeBlockStart :: Parser [Char] st Char
339346codeBlockStart = string "::" >> blankline >> blankline
340347
@@ -342,7 +349,8 @@ codeBlock :: Parser [Char] st Blocks
342349codeBlock = try $ codeBlockStart >> codeBlockBody
343350
344351codeBlockBody :: Parser [Char] st Blocks
345−codeBlockBody = try $ B.codeBlock . stripTrailingNewlines <$> indentedBlock
352+codeBlockBody = try $ B.codeBlock . stripTrailingNewlines <$>
353+ (indentedBlock <|> quotedBlock)
346354
347355lhsCodeBlock :: RSTParser Blocks
348356lhsCodeBlock = try $ do
@@ -513,7 +521,6 @@ directive = try $ do
513521-- TODO: line-block, parsed-literal, table, csv-table, list-table
514522-- date
515523-- include
516−-- class
517524-- title
518525directive' :: RSTParser Blocks
519526directive' = do
@@ -594,6 +601,13 @@ directive' = do
594601 Just t -> B.link (escapeURI $ trim t) ""
595602 $ B.image src "" alt
596603 Nothing -> B.image src "" alt
604+ "class" -> do
605+ let attrs = ("", (splitBy isSpace $ trim top), map (\(k,v) -> (k, trimr v)) fields)
606+ -- directive content or the first immediately following element
607+ children <- case body of
608+ "" -> block
609+ _ -> parseFromString parseBlocks body'
610+ return $ B.divWith attrs children
597611 _ -> return mempty
598612
599613-- TODO:
tests/Tests/Readers/RST.hs+22−1
@@ -67,5 +67,26 @@ tests = [ "line block with blank line" =:
6767 link "http://foo.bar.baz" "" "http://foo.bar.baz" <> ". " <>
6868 link "http://foo.bar/baz_(bam)" "" "http://foo.bar/baz_(bam)"
6969 <> " (" <> link "http://foo.bar" "" "http://foo.bar" <> ")")
70+ , "indented literal block" =: unlines
71+ [ "::"
72+ , ""
73+ , " block quotes"
74+ , ""
75+ , " can go on for many lines"
76+ , "but must stop here"]
77+ =?> (doc $
78+ codeBlock "block quotes\n\ncan go on for many lines" <>
79+ para "but must stop here")
80+ , "line block with 3 lines" =: "| a\n| b\n| c"
81+ =?> para ("a" <> linebreak <> "b" <> linebreak <> "c")
82+ , "quoted literal block using >" =: "::\n\n> quoted\n> block\n\nOrdinary paragraph"
83+ =?> codeBlock "> quoted\n> block" <> para "Ordinary paragraph"
84+ , "quoted literal block using | (not a line block)" =: "::\n\n| quoted\n| block\n\nOrdinary paragraph"
85+ =?> codeBlock "| quoted\n| block" <> para "Ordinary paragraph"
86+ , "class directive with single paragraph" =: ".. class:: special\n\nThis is a \"special\" paragraph."
87+ =?> divWith ("", ["special"], []) (para "This is a \"special\" paragraph.")
88+ , "class directive with two paragraphs" =: ".. class:: exceptional remarkable\n\n First paragraph.\n\n Second paragraph."
89+ =?> divWith ("", ["exceptional", "remarkable"], []) (para "First paragraph." <> para "Second paragraph.")
90+ , "class directive around literal block" =: ".. class:: classy\n\n::\n\n a\n b"
91+ =?> divWith ("", ["classy"], []) (codeBlock "a\nb")
7092 ]
71−