git.iko.soy/typeable/pandoc
on master help sign in
consolidate simple-table detection (#5524)

add `onlySimpleTableCells` to `Text.Pandoc.Shared` [API change] This fixes an inconsistency in the HTML reader, which did not treat tables with `<p>` inside cells as simple.

commitd07ed83d705df491bba7b295bd5e80629d971685 authorMauro Bieg <mb21@users.noreply.github.com> dateMon 27 May 2019, 19:53 (7 years ago) parentf807f5b
6 files changed+24−42
src/Text/Pandoc/Readers/HTML.hs+2−7 src/Text/Pandoc/Shared.hs+15 src/Text/Pandoc/Writers/CommonMark.hs+4−14 src/Text/Pandoc/Writers/Markdown.hs+1−9 src/Text/Pandoc/Writers/Muse.hs+1−11 test/html-reader.native+1−1
src/Text/Pandoc/Readers/HTML.hs+2−7
@@ -61,7 +61,7 @@ import Text.Pandoc.Options (
6161 extensionEnabled)
6262import Text.Pandoc.Parsing hiding ((<|>))
6363import Text.Pandoc.Shared (addMetaField, blocksToInlines', crFilter, escapeURI,
64− extractSpaces, safeRead, underlineSpan)
64+ extractSpaces, onlySimpleTableCells, safeRead, underlineSpan)
6565import Text.Pandoc.Walk
6666import Text.Parsec.Error
6767import Text.TeXMath (readMathML, writeTeX)
@@ -488,14 +488,9 @@ pTable = try $ do
488488 TagClose _ <- pSatisfy (matchTagClose "table")
489489 let rows'' = concat rowsLs <> topfoot <> bottomfoot
490490 let rows''' = map (map snd) rows''
491− -- let rows''' = map (map snd) rows''
492491 -- fail on empty table
493492 guard $ not $ null head' && null rows'''
494− let isSinglePlain x = case B.toList x of
495− [] -> True
496− [Plain _] -> True
497− _ -> False
498− let isSimple = all isSinglePlain $ concat (head':rows''')
493+ let isSimple = onlySimpleTableCells $ fmap B.toList <$> head':rows'''
499494 let cols = if null head'
500495 then maximum (map length rows''')
501496 else length head'
src/Text/Pandoc/Shared.hs+15
@@ -59,6 +59,7 @@ module Text.Pandoc.Shared (
5959 isHeaderBlock,
6060 headerShift,
6161 stripEmptyParagraphs,
62+ onlySimpleTableCells,
6263 isTightList,
6364 taskListItemFromAscii,
6465 taskListItemToAscii,
@@ -108,6 +109,7 @@ import Data.List (find, intercalate, intersperse, stripPrefix, sortBy)
108109import Data.Ord (comparing)
109110import qualified Data.Map as M
110111import Data.Maybe (mapMaybe)
112+import Data.Monoid (Any (..))
111113import Data.Sequence (ViewL (..), ViewR (..), viewl, viewr)
112114import qualified Data.Set as Set
113115import qualified Data.Text as T
@@ -571,6 +573,19 @@ stripEmptyParagraphs = walk go
571573 isEmptyParagraph (Para []) = True
572574 isEmptyParagraph _ = False
573575
576+-- | Detect if table rows contain only cells consisting of a single
577+-- paragraph that has no @LineBreak@.
578+onlySimpleTableCells :: [[TableCell]] -> Bool
579+onlySimpleTableCells = all isSimpleCell . concat
580+ where
581+ isSimpleCell [Plain ils] = not (hasLineBreak ils)
582+ isSimpleCell [Para ils ] = not (hasLineBreak ils)
583+ isSimpleCell [] = True
584+ isSimpleCell _ = False
585+ hasLineBreak = getAny . query isLineBreak
586+ isLineBreak LineBreak = Any True
587+ isLineBreak _ = Any False
588+
574589-- | Detect if a list is tight.
575590isTightList :: [[Block]] -> Bool
576591isTightList = all firstIsPlain
src/Text/Pandoc/Writers/CommonMark.hs+4−14
@@ -21,17 +21,16 @@ import Control.Monad.State.Strict (State, get, modify, runState)
2121import Data.Char (isAscii)
2222import Data.Foldable (foldrM)
2323import Data.List (transpose)
24−import Data.Monoid (Any (..))
2524import Data.Text (Text)
2625import qualified Data.Text as T
2726import Network.HTTP (urlEncode)
2827import Text.Pandoc.Class (PandocMonad)
2928import Text.Pandoc.Definition
3029import Text.Pandoc.Options
31−import Text.Pandoc.Shared (isTightList, taskListItemToAscii, linesToPara,
32− substitute, capitalize, isHeaderBlock)
30+import Text.Pandoc.Shared (capitalize, isHeaderBlock, isTightList,
31+ linesToPara, onlySimpleTableCells, substitute, taskListItemToAscii)
3332import Text.Pandoc.Templates (renderTemplate')
34−import Text.Pandoc.Walk (query, walk, walkM)
33+import Text.Pandoc.Walk (walk, walkM)
3534import Text.Pandoc.Writers.HTML (writeHtml5String, tagWithAttributes)
3635import Text.Pandoc.Writers.Shared
3736import Text.Pandoc.XML (toHtml5Entities)
@@ -159,16 +158,7 @@ blockToNodes opts (DefinitionList items) ns =
159158 dlToBullet (term, xs) =
160159 Para term : concat xs
161160blockToNodes opts t@(Table capt aligns _widths headers rows) ns = do
162− let allcells = concat (headers:rows)
163− let isLineBreak LineBreak = Any True
164− isLineBreak _ = Any False
165− let isPlainOrPara [Para _] = True
166− isPlainOrPara [Plain _] = True
167− isPlainOrPara [] = True
168− isPlainOrPara _ = False
169− let isSimple = all isPlainOrPara allcells &&
170− not ( getAny (query isLineBreak allcells) )
171− if isEnabled Ext_pipe_tables opts && isSimple
161+ if isEnabled Ext_pipe_tables opts && onlySimpleTableCells (headers:rows)
172162 then do
173163 -- We construct a table manually as a CUSTOM_BLOCK, for
174164 -- two reasons: (1) cmark-gfm currently doesn't support
src/Text/Pandoc/Writers/Markdown.hs+1−9
@@ -27,7 +27,6 @@ import Data.List (find, group, intersperse, sortBy, stripPrefix, transpose,
2727 isPrefixOf)
2828import qualified Data.Map as M
2929import Data.Maybe (fromMaybe)
30−import Data.Monoid (Any (..))
3130import Data.Ord (comparing)
3231import qualified Data.Set as Set
3332import qualified Data.Scientific as Scientific
@@ -574,14 +573,7 @@ blockToMarkdown' opts t@(Table caption aligns widths headers rows) = do
574573 let caption'' = if null caption || not (isEnabled Ext_table_captions opts)
575574 then blankline
576575 else blankline $$ (": " <> caption') $$ blankline
577− let isLineBreak LineBreak = Any True
578− isLineBreak _ = Any False
579− let hasLineBreak = getAny . query isLineBreak
580− let isSimpleCell [Plain ils] = not (hasLineBreak ils)
581− isSimpleCell [Para ils ] = not (hasLineBreak ils)
582− isSimpleCell [] = True
583− isSimpleCell _ = False
584− let hasSimpleCells = all isSimpleCell (concat (headers:rows))
576+ let hasSimpleCells = onlySimpleTableCells $ headers:rows
585577 let isSimple = hasSimpleCells && all (==0) widths
586578 let isPlainBlock (Plain _) = True
587579 isPlainBlock _ = False
src/Text/Pandoc/Writers/Muse.hs+1−11
@@ -31,7 +31,6 @@ import Control.Monad.State.Strict
3131import Data.Char (isAlphaNum, isAsciiLower, isAsciiUpper, isDigit, isSpace)
3232import Data.Default
3333import Data.List (intersperse, isInfixOf, transpose)
34−import Data.Monoid (Any (..))
3534import qualified Data.Set as Set
3635import Data.Text (Text)
3736import System.FilePath (takeExtension)
@@ -44,7 +43,6 @@ import Text.Pandoc.Shared
4443import Text.Pandoc.Templates (renderTemplate')
4544import Text.Pandoc.Writers.Math
4645import Text.Pandoc.Writers.Shared
47−import Text.Pandoc.Walk
4846
4947type Notes = [[Block]]
5048
@@ -269,15 +267,7 @@ blockToMuse (Table caption aligns widths headers rows) =
269267 blocksToDoc opts blocks =
270268 local (\env -> env { envOptions = opts }) $ blockListToMuse blocks
271269 numcols = maximum (length aligns : length widths : map length (headers:rows))
272− hasSimpleCells = all isSimpleCell (concat (headers:rows))
273− isLineBreak LineBreak = Any True
274− isLineBreak _ = Any False
275− hasLineBreak = getAny . query isLineBreak
276− isSimple = hasSimpleCells && all (== 0) widths
277− isSimpleCell [Plain ils] = not (hasLineBreak ils)
278− isSimpleCell [Para ils ] = not (hasLineBreak ils)
279− isSimpleCell [] = True
280− isSimpleCell _ = False
270+ isSimple = onlySimpleTableCells (headers:rows) && all (== 0) widths
281271blockToMuse (Div _ bs) = flatBlockListToMuse bs
282272blockToMuse Null = return empty
283273
test/html-reader.native+1−1
@@ -415,7 +415,7 @@ Pandoc (Meta {unMeta = fromList [("generator",MetaInlines [Str "pandoc"]),("titl
415415 ,[Plain [Str "5"]]
416416 ,[Plain [Str "6"]]]]
417417,HorizontalRule
418−,Table [] [AlignDefault,AlignDefault,AlignDefault] [0.3333333333333333,0.3333333333333333,0.3333333333333333]
418+,Table [] [AlignDefault,AlignDefault,AlignDefault] [0.0,0.0,0.0]
419419 [[Plain [Str "X"]]
420420 ,[Plain [Str "Y"]]
421421 ,[Plain [Str "Z"]]]