@@ -1,184 +1,11 @@
1−{-# LANGUAGE PatternGuards #-}
2−{-# LANGUAGE OverloadedStrings #-}
3−{-# LANGUAGE MultiWayIf #-}
5module Tests.Writers.Powerpoint (tests) where
1module Tests.Writers.Powerpoint (tests) where
3+import Tests.Writers.OOXML (ooxmlTest)
7import Text.Pandoc
4import Text.Pandoc
8import Test.Tasty
5import Test.Tasty
9−import Test.Tasty.Golden.Advanced
10−import Codec.Archive.Zip
12−import qualified Data.ByteString as BS
13−import qualified Data.ByteString.Lazy as BL
14−import qualified Data.Text.IO as T
15−import Data.List (isPrefixOf, isSuffixOf, sort, (\\), intercalate, union)
16−import Data.Maybe (catMaybes, mapMaybe)
18−import Data.Algorithm.Diff
20−compareXMLBool :: Content -> Content -> Bool
21−-- We make a special exception for times at the moment, and just pass
22−-- them because we can't control the utctime when running IO. Besides,
23−-- so long as we have two times, we're okay.
24−compareXMLBool (Elem myElem) (Elem goodElem)
25− | (QName "created" _ (Just "dcterms")) <- elName myElem
26− , (QName "created" _ (Just "dcterms")) <- elName goodElem =
28−compareXMLBool (Elem myElem) (Elem goodElem)
29− | (QName "modified" _ (Just "dcterms")) <- elName myElem
30− , (QName "modified" _ (Just "dcterms")) <- elName goodElem =
32−compareXMLBool (Elem myElem) (Elem goodElem) =
33− elName myElem == elName goodElem &&
34− elAttribs myElem == elAttribs goodElem &&
35− and (zipWith compareXMLBool (elContent myElem) (elContent goodElem))
37−compareXMLBool (Text myCData) (Text goodCData) =
38− cdVerbatim myCData == cdVerbatim goodCData &&
39− cdData myCData == cdData goodCData &&
40− cdLine myCData == cdLine goodCData
42−compareXMLBool (CRef myStr) (CRef goodStr) =
44−compareXMLBool _ _ = False
46−displayDiff :: Content -> Content -> String
47−displayDiff elemA elemB =
48− showDiff (1,1) $ getDiff (lines $ ppContent elemA) (lines $ ppContent elemB)
50−goldenArchive :: FilePath -> IO Archive
51−goldenArchive fp = (toArchive . BL.fromStrict) <$> BS.readFile fp
53−testArchive :: WriterOptions -> FilePath -> IO Archive
54−testArchive opts fp = do
56− bs <- runIOorExplode $ readNative def txt >>= writePowerpoint opts
57− return $ toArchive bs
59−compareFileList :: FilePath -> Archive -> Archive -> Maybe String
60−compareFileList goldenFP goldenArch testArch =
61− let testFiles = filesInArchive testArch
62− goldenFiles = filesInArchive goldenArch
63− diffTestGolden = testFiles \\ goldenFiles
64− diffGoldenTest = goldenFiles \\ testFiles
67− [ if null diffGoldenTest
70− "Files in " ++ goldenFP ++ " but not in generated archive:\n" ++
71− intercalate ", " diffGoldenTest
72− , if null diffTestGolden
75− "Files in generated archive but not in " ++ goldenFP ++ ":\n" ++
76− intercalate ", " diffTestGolden
79− if null $ catMaybes results
81− else Just $ intercalate "\n" $ catMaybes results
83−compareXMLFile' :: FilePath -> Archive -> Archive -> Either String ()
84−compareXMLFile' fp goldenArch testArch = do
85− testEntry <- case findEntryByPath fp testArch of
86− Just entry -> Right entry
88− "Can't extract " ++ fp ++ " from generated archive"
89− testXMLDoc <- case parseXMLDoc $ fromEntry testEntry of
90− Just doc -> Right doc
92− "Can't parse xml in " ++ fp ++ " from generated archive"
94− goldenEntry <- case findEntryByPath fp goldenArch of
95− Just entry -> Right entry
97− "Can't extract " ++ fp ++ " from archive in stored pptx file"
98− goldenXMLDoc <- case parseXMLDoc $ fromEntry goldenEntry of
99− Just doc -> Right doc
101− "Can't parse xml in " ++ fp ++ " from archive in stored pptx file"
103− let testContent = Elem testXMLDoc
104− goldenContent = Elem goldenXMLDoc
106− if compareXMLBool goldenContent testContent
109− "Non-matching xml in " ++ fp ++ ":\n" ++ displayDiff testContent goldenContent
111−compareXMLFile :: FilePath -> Archive -> Archive -> Maybe String
112−compareXMLFile fp goldenArch testArch =
113− case compareXMLFile' fp goldenArch testArch of
117−compareAllXMLFiles :: Archive -> Archive -> Maybe String
118−compareAllXMLFiles goldenArch testArch =
119− let allFiles = filesInArchive goldenArch `union` filesInArchive testArch
120− allXMLFiles = sort $
122− (\fp -> ".xml" `isSuffixOf` fp || ".rels" `isSuffixOf` fp)
125− mapMaybe (\fp -> compareXMLFile fp goldenArch testArch) allXMLFiles
129− else Just $ unlines results
131−compareMediaFile' :: FilePath -> Archive -> Archive -> Either String ()
132−compareMediaFile' fp goldenArch testArch = do
133− testEntry <- case findEntryByPath fp testArch of
134− Just entry -> Right entry
136− "Can't extract " ++ fp ++ " from generated archive"
137− goldenEntry <- case findEntryByPath fp goldenArch of
138− Just entry -> Right entry
140− "Can't extract " ++ fp ++ " from archive in stored pptx file"
142− if fromEntry testEntry == fromEntry goldenEntry
145− "Non-matching binary file: " ++ fp
147−compareMediaFile :: FilePath -> Archive -> Archive -> Maybe String
148−compareMediaFile fp goldenArch testArch =
149− case compareMediaFile' fp goldenArch testArch of
153−compareAllMediaFiles :: Archive -> Archive -> Maybe String
154−compareAllMediaFiles goldenArch testArch =
155− let allFiles = filesInArchive goldenArch `union` filesInArchive testArch
156− allMediaFiles = sort $
158− (\fp -> "/ppt/media/" `isPrefixOf` fp)
161− mapMaybe (\fp -> compareMediaFile fp goldenArch testArch) allMediaFiles
165− else Just $ unlines results
167pptxTest :: String -> WriterOptions -> FilePath -> FilePath -> TestTree
7pptxTest :: String -> WriterOptions -> FilePath -> FilePath -> TestTree
168−pptxTest testName opts nativeFP goldenFP =
8+pptxTest = ooxmlTest writePowerpoint
171− (goldenArchive goldenFP)
172− (testArchive opts nativeFP)
173− (\goldenArch testArch ->
174− let res = catMaybes [ compareFileList goldenFP goldenArch testArch
175− , compareAllXMLFiles goldenArch testArch
176− , compareAllMediaFiles goldenArch testArch
178− in return $ if null res then Nothing else Just $ unlines res)
179− (\a -> BL.writeFile goldenFP $ fromArchive a)
181−--------------------------------------------------------------
183tests :: [TestTree]
10tests :: [TestTree]
184tests = [ pptxTest
11tests = [ pptxTest