From 13280a811264690c42ac7d795efa0c702fad0b7b Mon Sep 17 00:00:00 2001
From: Albert Krewinkel <albert@zeitkraut.de>
Date: Mon, 8 Aug 2016 09:40:50 +0200
Subject: [PATCH] Org reader: preserve indentation of verse lines

Leading spaces in verse lines are converted to non-breaking spaces, so
indentation is preserved.

This fixes #3064.
---
 src/Text/Pandoc/Readers/Org/Blocks.hs | 11 ++++++++++-
 tests/Tests/Readers/Org.hs            |  8 ++++++++
 2 files changed, 18 insertions(+), 1 deletion(-)

diff --git a/src/Text/Pandoc/Readers/Org/Blocks.hs b/src/Text/Pandoc/Readers/Org/Blocks.hs
index 0bd82ce2f..66db207d9 100644
--- a/src/Text/Pandoc/Readers/Org/Blocks.hs
+++ b/src/Text/Pandoc/Readers/Org/Blocks.hs
@@ -422,7 +422,16 @@ verseBlock blockType = try $ do
   ignHeaders
   content <- rawBlockContent blockType
   fmap B.para . mconcat . intersperse (pure B.linebreak)
-    <$> mapM (parseFromString inlines) (map (++ "\n") . lines $ content)
+    <$> mapM parseVerseLine (lines content)
+ where
+   -- replace initial spaces with nonbreaking spaces to preserve
+   -- indentation, parse the rest as normal inline
+   parseVerseLine :: String -> OrgParser (F Inlines)
+   parseVerseLine cs = do
+     let (initialSpaces, indentedLine) = span isSpace cs
+     let nbspIndent = B.str $ map (const '\160') initialSpaces
+     line <- parseFromString inlines (indentedLine ++ "\n")
+     return (pure nbspIndent <> line)
 
 -- | Read a code block and the associated results block if present.  Which of
 -- boths blocks is included in the output is determined using the "exports"
diff --git a/tests/Tests/Readers/Org.hs b/tests/Tests/Readers/Org.hs
index 1f8a8a01e..a879b0912 100644
--- a/tests/Tests/Readers/Org.hs
+++ b/tests/Tests/Readers/Org.hs
@@ -1440,6 +1440,14 @@ tests =
                   ] =?>
           para ("foo" <> linebreak <> linebreak <> "bar")
 
+      , "Verse block with varying indentation" =:
+          unlines [ "#+BEGIN_VERSE"
+                  , "  hello darkness"
+                  , "my old friend"
+                  , "#+END_VERSE"
+                  ] =?>
+          para ("\160\160hello darkness" <> linebreak <> "my old friend")
+
       , "Raw block LaTeX" =:
           unlines [ "#+BEGIN_LaTeX"
                   , "The category $\\cat{Set}$ is adhesive."