summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLaurentRDC <>2020-06-19 15:22:00 (GMT)
committerhdiff <hdiff@hdiff.luite.com>2020-06-19 15:22:00 (GMT)
commit621c1be90fb6d89f648fbea69012c2b95d2e5ce6 (patch)
treeea678146203fca87afc0f9c65ee9db4a41344089
parentc867a5ea03b68c705faf151813c18bd285085ec6 (diff)
version 0.7.1.0HEAD0.7.1.0master
-rw-r--r--CHANGELOG.md6
-rw-r--r--README.md2
-rw-r--r--benchmark/MatplotlibGallery.hs8
-rw-r--r--benchmark/bench.hs14
-rw-r--r--pandoc-plot.cabal10
-rw-r--r--src/Text/Pandoc/Filter/Plot.hs47
-rw-r--r--src/Text/Pandoc/Filter/Plot/Monad.hs61
-rw-r--r--src/Text/Pandoc/Filter/Plot/Monad/Logging.hs99
-rw-r--r--src/Text/Pandoc/Filter/Plot/Monad/Types.hs1
-rw-r--r--src/Text/Pandoc/Filter/Plot/Parse.hs2
-rw-r--r--src/Text/Pandoc/Filter/Plot/Renderers.hs7
-rw-r--r--src/Text/Pandoc/Filter/Plot/Renderers/Matlab.hs2
-rw-r--r--src/Text/Pandoc/Filter/Plot/Renderers/Prelude.hs18
-rw-r--r--stack.yaml2
-rw-r--r--tests/Common.hs20
15 files changed, 160 insertions, 139 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 1fd1d15..8c5ada5 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -2,8 +2,14 @@
pandoc-plot uses [Semantic Versioning](http://semver.org/spec/v2.0.0.html)
+Release 0.7.1.0
+---------------
+
+* Better multi-threaded logging. Only one thread (the logging thread) performs IO on the log file. This prevents hang-ups when working on large documents.
+
Release 0.7.0.0
---------------
+
* Added documentation on using `pandoc-plot` with LaTeX documents as well.
* Added preliminary support for logging to `pandoc-plot`. You can turn on this feature in the configuration as follows:
diff --git a/README.md b/README.md
index 2ebcc2b..deb2a40 100644
--- a/README.md
+++ b/README.md
@@ -1,5 +1,5 @@
<!--
-The file README.md is automatically generated by the tools/mkreadme script
+The file README.md is automatically generated by the mkreadme.ps1 script
Do not edit manually
-->
diff --git a/benchmark/MatplotlibGallery.hs b/benchmark/MatplotlibGallery.hs
index a92dea4..feb2976 100644
--- a/benchmark/MatplotlibGallery.hs
+++ b/benchmark/MatplotlibGallery.hs
@@ -19,8 +19,8 @@ galleryItem fp = do
strToExp :: String -> Q Exp
strToExp s = return $ VarE 'fromString `AppE` LitE (StringL s)
-galleryItem1 :: Q Exp
+galleryItem1, galleryItem2, galleryItem3, galleryItem4 :: Q Exp
galleryItem1 = galleryItem "benchmark/gallery_item_1.py"
-
-galleryItem2 :: Q Exp
-galleryItem2 = galleryItem "benchmark/gallery_item_2.py" \ No newline at end of file
+galleryItem2 = galleryItem "benchmark/gallery_item_2.py"
+galleryItem3 = galleryItem "benchmark/gallery_item_3.py"
+galleryItem4 = galleryItem "benchmark/gallery_item_4.py" \ No newline at end of file
diff --git a/benchmark/bench.hs b/benchmark/bench.hs
index be2b7ac..21d9dad 100644
--- a/benchmark/bench.hs
+++ b/benchmark/bench.hs
@@ -6,19 +6,25 @@ import Text.Pandoc.Definition
import Text.Pandoc.Filter.Plot
import Text.Pandoc.Filter.Plot.Internal
-import MatplotlibGallery (galleryItem1, galleryItem2)
+import MatplotlibGallery ( galleryItem1, galleryItem2
+ , galleryItem3, galleryItem4
+ )
main :: IO ()
main =
defaultMain [
envWithCleanup (return ()) (\_ -> cleanupEnv) $ \_ ->
bgroup "main" [
- bench "filter" $ nfIO (plotTransform defaultConfiguration benchDoc)
+ bench "filter-async" $ nfIO (plotTransform plotConfig benchDoc)
+ , bench "filter" $ nfIO (makePlot plotConfig benchDoc)
]
]
+plotConfig :: Configuration
+plotConfig = defaultConfiguration {logVerbosity=Silent, logSink =StdErr}
+
cleanupEnv :: IO ()
-cleanupEnv = cleanOutputDirs defaultConfiguration benchDoc >> return ()
+cleanupEnv = cleanOutputDirs plotConfig benchDoc >> return ()
codeBlock :: Script -> Block
@@ -28,4 +34,6 @@ codeBlock = CodeBlock (mempty, [cls Matplotlib], mempty)
benchDoc :: Pandoc
benchDoc = Pandoc mempty [ codeBlock $(galleryItem1)
, codeBlock $(galleryItem2)
+ , codeBlock $(galleryItem3)
+ , codeBlock $(galleryItem4)
] \ No newline at end of file
diff --git a/pandoc-plot.cabal b/pandoc-plot.cabal
index ee05492..ec57462 100644
--- a/pandoc-plot.cabal
+++ b/pandoc-plot.cabal
@@ -1,5 +1,5 @@
name: pandoc-plot
-version: 0.7.0.0
+version: 0.7.1.0
cabal-version: >= 1.12
synopsis: A Pandoc filter to include figures generated from code blocks using your plotting toolkit of choice.
description: A Pandoc filter to include figures generated from code blocks. Keep the document and code in the same location. Output is captured and included as a figure.
@@ -12,6 +12,7 @@ maintainer: Laurent P. René de Cotret
license: GPL-2
license-file: LICENSE
build-type: Simple
+tested-with: GHC == 8.6.5, GHC == 8.8.3
extra-source-files:
CHANGELOG.md
LICENSE
@@ -61,13 +62,12 @@ library
, hashable >= 1 && < 2
, pandoc >= 2.8 && < 3
, pandoc-types >= 1.20 && < 2
- , async >= 2 && < 3
+ , lifted-async >= 0.10 && < 1
, shakespeare >= 2.0 && < 3
, text >= 1 && < 2
- , time >= 1 && < 2
, typed-process >= 0.2.1 && < 1
, yaml >= 0.8 && < 1
- , mtl >= 2.2 && < 2.3
+ , mtl >= 2.2 && < 3
default-language: Haskell2010
executable pandoc-plot
@@ -122,7 +122,7 @@ benchmark benchmark-pandoc-plot
build-depends: base
, pandoc-plot
, pandoc-types
- , criterion >= 1.0 && < 1.6
+ , criterion >= 1.0 && < 2
, template-haskell > 2.7 && < 3
, text
ghc-options: -Wall -Wcompat -rtsopts -O2 -threaded -with-rtsopts=-N
diff --git a/src/Text/Pandoc/Filter/Plot.hs b/src/Text/Pandoc/Filter/Plot.hs
index 7a57ad6..ebd17dc 100644
--- a/src/Text/Pandoc/Filter/Plot.hs
+++ b/src/Text/Pandoc/Filter/Plot.hs
@@ -89,8 +89,7 @@ module Text.Pandoc.Filter.Plot (
, readDoc
) where
-import Control.Concurrent.Async (mapConcurrently)
-
+import Control.Concurrent.Async.Lifted (mapConcurrently)
import Data.Text (Text, unpack)
import Text.Pandoc.Definition (Pandoc(..), Block)
@@ -108,8 +107,8 @@ import Text.Pandoc.Filter.Plot.Internal
plotTransform :: Configuration -- ^ Configuration for default values
-> Pandoc -- ^ Input document
-> IO Pandoc
-plotTransform conf (Pandoc meta blocks) =
- mapConcurrently (makePlot conf) blocks >>= return . Pandoc meta
+plotTransform conf (Pandoc meta blocks) =
+ runPlotM conf $ mapConcurrently make blocks >>= return . Pandoc meta
-- | Highest-level function that can be walked over a Pandoc tree.
@@ -127,33 +126,29 @@ makePlot :: Walkable Block a
=> Configuration -- ^ Configuration for default values
-> a -- ^ Input block or document
-> IO a
-makePlot conf = walkM (make conf)
+makePlot conf = runPlotM conf . walkM make
-make :: Configuration
- -> Block
- -> IO Block
-make conf blk =
- either (const (return blk) ) return =<< makeEither conf blk
+-- | Try to process the block with `pandoc-plot`. If a failure happens (or the block)
+-- was not meant to become a figure, return the block as-is.
+make :: Block -> PlotM Block
+make blk = either (const (return blk) ) return =<< makeEither blk
-makeEither :: Configuration
- -> Block
- -> IO (Either PandocPlotError Block)
-makeEither conf block = runPlotM conf (go block)
+-- | Try to process the block with `pandoc-plot`, documenting the error.
+makeEither :: Block -> PlotM (Either PandocPlotError Block)
+makeEither block =
+ parseFigureSpec block
+ >>= maybe
+ (return $ Right block)
+ (\s -> runScriptIfNecessary s >>= handleResult s)
where
- go :: Block -> PlotM (Either PandocPlotError Block)
- go blk = parseFigureSpec blk
- >>= maybe
- (return $ Right blk)
- (\s -> runScriptIfNecessary s >>= handleResult s)
- where
- -- Logging of errors has been taken care of in @runScriptIfNecessary@
- handleResult :: FigureSpec -> ScriptResult -> PlotM (Either PandocPlotError Block)
- handleResult spec ScriptSuccess = return $ Right $ toImage (captionFormat conf) spec
- handleResult _ (ScriptFailure msg code) = return $ Left (ScriptRuntimeError msg code)
- handleResult _ (ScriptChecksFailed msg) = return $ Left (ScriptChecksFailedError msg)
- handleResult _ (ToolkitNotInstalled tk') = return $ Left (ToolkitNotInstalledError tk')
+ -- Logging of errors has been taken care of in @runScriptIfNecessary@
+ handleResult :: FigureSpec -> ScriptResult -> PlotM (Either PandocPlotError Block)
+ handleResult _ (ScriptFailure msg code) = return $ Left (ScriptRuntimeError msg code)
+ handleResult _ (ScriptChecksFailed msg) = return $ Left (ScriptChecksFailedError msg)
+ handleResult _ (ToolkitNotInstalled tk') = return $ Left (ToolkitNotInstalledError tk')
+ handleResult spec ScriptSuccess = asks envConfig >>= \c -> return $ Right $ toImage (captionFormat c) spec
data PandocPlotError
diff --git a/src/Text/Pandoc/Filter/Plot/Monad.hs b/src/Text/Pandoc/Filter/Plot/Monad.hs
index 9edce2b..b54bb87 100644
--- a/src/Text/Pandoc/Filter/Plot/Monad.hs
+++ b/src/Text/Pandoc/Filter/Plot/Monad.hs
@@ -13,6 +13,7 @@ This module defines the @PlotM@ monad and related capabilities.
module Text.Pandoc.Filter.Plot.Monad (
Configuration(..)
, PlotM
+ , RuntimeEnv(..)
, runPlotM
-- * Running external commands
, runCommand
@@ -27,14 +28,19 @@ module Text.Pandoc.Filter.Plot.Monad (
, liftIO
, ask
, asks
+ , asksConfig
-- * Base types
, module Text.Pandoc.Filter.Plot.Monad.Types
) where
+
+import Control.Concurrent.Chan (writeChan)
+
import Control.Monad.Reader
import Data.ByteString.Lazy (toStrict)
import Data.Text (Text, pack, unpack)
+import qualified Data.Text as T
import Data.Text.Encoding (decodeUtf8With)
import Data.Text.Encoding.Error (lenientDecode)
@@ -47,39 +53,56 @@ import Text.Pandoc.Definition (Format(..))
import Prelude hiding (log, fst, snd)
-import Text.Pandoc.Filter.Plot.Monad.Logging
+import Text.Pandoc.Filter.Plot.Monad.Logging as Log
import Text.Pandoc.Filter.Plot.Monad.Types
+
-- | pandoc-plot monad
-type PlotM a = ReaderT Configuration LoggingM a
+type PlotM a = ReaderT RuntimeEnv IO a
+
+
+data RuntimeEnv =
+ RuntimeEnv { envConfig :: Configuration
+ , envLogger :: Logger
+ }
+-- | Get access to configuration within the @PlotM@ monad.
+asksConfig :: (Configuration -> a) -> PlotM a
+asksConfig f = asks (f . envConfig)
--- | Evaluate a @PlotM@ action
+
+-- | Evaluate a @PlotM@ action.
runPlotM :: Configuration -> PlotM a -> IO a
runPlotM conf v =
let verbosity = logVerbosity conf
sink = logSink conf
- in runLoggingM verbosity sink (runReaderT v conf)
-
-
-debug :: Text -> PlotM ()
-debug t = lift $ log "DEBUG| " Debug t
-
-
-err :: Text -> PlotM ()
-err t = lift $ log "ERROR| " Error t
+ in withLogger verbosity sink $
+ \logger -> runReaderT v (RuntimeEnv conf logger)
-warning :: Text -> PlotM ()
-warning t = lift $ log "WARN | " Warning t
+debug, err, warning, info :: Text -> PlotM ()
+debug = log "DEBUG| " Debug
+err = log "ERROR| " Error
+warning = log "WARN | " Warning
+info = log "INFO | " Info
-info :: Text -> PlotM ()
-info t = lift $ log "INFO | " Info t
+-- | General purpose logging.
+log :: Text -- ^ Header.
+ -> Verbosity -- ^ Verbosity of the message.
+ -> Text -- ^ Message (can be multiple lines).
+ -> PlotM ()
+log h v t = do
+ logger <- asks envLogger
+ when (v >= lVerbosity logger) $
+ liftIO $ do
+ let lines' = [l' | l' <- T.lines t]
+ forM_ lines' $ \l -> writeChan (lChannel logger) (Just (h <> l <> "\n"))
--- | Run a command within the @PlotM@ monad. Stdout and Stderr
--- are read and decoded. Logging happens at the debug level.
+-- | Run a command within the @PlotM@ monad. Stderr stream
+-- is read and decoded, while Stdout is ignored.
+-- Logging happens at the debug level.
runCommand :: Text -> PlotM (ExitCode, Text)
runCommand command = do
(ec, processOutput') <- liftIO
@@ -108,7 +131,7 @@ runCommand command = do
-- ---
-- title: My document
-- author: John Doe
--- plot-configuration: /path/to/file.yml
+-- plot-configuration: path\to\file.yml
-- ---
-- @
--
diff --git a/src/Text/Pandoc/Filter/Plot/Monad/Logging.hs b/src/Text/Pandoc/Filter/Plot/Monad/Logging.hs
index 60f6ef0..16ffa25 100644
--- a/src/Text/Pandoc/Filter/Plot/Monad/Logging.hs
+++ b/src/Text/Pandoc/Filter/Plot/Monad/Logging.hs
@@ -15,27 +15,25 @@ Logging primitives.
module Text.Pandoc.Filter.Plot.Monad.Logging
( Verbosity(..)
, LogSink(..)
- , LoggingM
- , runLoggingM
- , log
+ , Logger(..)
+ , withLogger
) where
-import Control.Monad.Trans (liftIO)
-import Control.Monad.Writer.Strict (WriterT, runWriterT, tell)
+import Control.Concurrent (forkIO)
+import Control.Concurrent.Chan (Chan, newChan, readChan, writeChan)
+import Control.Concurrent.MVar (MVar, newEmptyMVar, putMVar, takeMVar)
-import Data.Char (toLower)
-import Data.List (sortOn)
-import Data.String (IsString(..))
-import Data.Text (Text, unpack)
-import qualified Data.Text as T
-import Data.Text.IO (hPutStr)
-import Data.Time.Clock.System (getSystemTime, SystemTime(..))
+import Control.Monad (forever)
+
+import Data.Char (toLower)
+import Data.String (IsString(..))
+import Data.Text (Text, unpack)
+import Data.Text.IO (hPutStr)
import Data.Yaml
-import System.IO (stderr, withFile, IOMode (AppendMode) )
+import System.IO (stderr, withFile, IOMode (AppendMode) )
-import Prelude hiding (log, fst, snd)
-- | Verbosity of the logger.
@@ -52,40 +50,45 @@ data LogSink = StdErr -- ^ Standard error stream.
| LogFile FilePath -- ^ Appended to file.
deriving (Eq, Show)
-type LogMessage = (Verbosity, SystemTime, Text)
-type LoggingM = WriterT [LogMessage] IO
+-- | The logging implementation is very similar to Hakyll's.
+data Logger = Logger
+ { lVerbosity :: Verbosity
+ , lChannel :: Chan (Maybe Text)
+ , lSink :: Text -> IO ()
+ , lSync :: MVar ()
+ }
-runLoggingM :: Verbosity -> LogSink -> LoggingM a -> IO a
-runLoggingM Silent _ = runLoggingM' Silent $ mapM_ (return . trd)
-runLoggingM v StdErr = runLoggingM' v $ mapM_ (hPutStr stderr . trd)
-runLoggingM v (LogFile fp) = runLoggingM' v $ mapM_ (\m -> withFile fp AppendMode $ \h -> hPutStr h (trd m))
+-- | Perform an IO action with a logger. Using this function
+-- ensures that logging will be gracefully shut down.
+withLogger :: Verbosity -> LogSink -> (Logger -> IO a) -> IO a
+withLogger v s f = do
+ logger <- Logger <$> pure v
+ <*> newChan
+ <*> pure (sink s)
+ <*> newEmptyMVar
+ -- The logger either logs messages (if Just "message"),
+ -- or stops working on Nothing.
+ _ <- forkIO $ forever $
+ readChan (lChannel logger)
+ >>= maybe (putMVar (lSync logger) ()) (lSink logger)
-runLoggingM' :: Verbosity -- ^ Minimum verbosity to keep
- -> ([LogMessage] -> IO ()) -- ^ Log sink
- -> LoggingM a
- -> IO a
-runLoggingM' v f m = do
- (r, t) <- runWriterT m
- -- Messages with lower level than minimum are discarded
- -- We also re-order messages to be chronological
- let t' = sortOn snd $ filter (\message -> fst message >= v) t
- liftIO $ f t'
- return r
+ result <- f logger
+
+ -- Flushing the logger
+ -- To signal to the logger that logging duties are over,
+ -- we append Nothing to the channel, and wait for it to finish
+ -- dealing with all items in the channel.
+ writeChan (lChannel logger) Nothing
+ () <- takeMVar (lSync logger)
+ return result
--- | General logging function.
--- Input text will be decomposed into lines, with each
--- line becoming a log line.
-log :: Text -- ^ Header
- -> Verbosity
- -> Text -- ^ Message
- -> LoggingM ()
-log h v t = do
- timestamp <- liftIO $ getSystemTime
- tell [(v, timestamp, h <> l <> "\n") | l <- T.lines t]
+ where
+ sink StdErr = hPutStr stderr
+ sink (LogFile fp) = \t -> withFile fp AppendMode $ \h -> hPutStr h t
instance IsString Verbosity where
@@ -101,16 +104,4 @@ instance IsString Verbosity where
instance FromJSON Verbosity where
parseJSON (String t) = pure $ fromString . unpack $ t
- parseJSON _ = fail $ "Could not parse the logging verbosity."
-
-
-fst :: (a,b,c) -> a
-fst (a,_,_) = a
-
-
-snd :: (a,b,c) -> b
-snd (_,b,_) = b
-
-
-trd :: (a,b,c) -> c
-trd (_,_,c) = c \ No newline at end of file
+ parseJSON _ = fail $ "Could not parse the logging verbosity." \ No newline at end of file
diff --git a/src/Text/Pandoc/Filter/Plot/Monad/Types.hs b/src/Text/Pandoc/Filter/Plot/Monad/Types.hs
index 11fdf14..bb1e7f6 100644
--- a/src/Text/Pandoc/Filter/Plot/Monad/Types.hs
+++ b/src/Text/Pandoc/Filter/Plot/Monad/Types.hs
@@ -33,7 +33,6 @@ module Text.Pandoc.Filter.Plot.Monad.Types (
import Data.Char (toLower)
import Data.Hashable (hash)
import Data.List (intersperse)
-import Data.Semigroup (Semigroup (..))
import Data.String (IsString (..))
import Data.Text (Text)
import Data.Yaml
diff --git a/src/Text/Pandoc/Filter/Plot/Parse.hs b/src/Text/Pandoc/Filter/Plot/Parse.hs
index 21b4e42..ce81c64 100644
--- a/src/Text/Pandoc/Filter/Plot/Parse.hs
+++ b/src/Text/Pandoc/Filter/Plot/Parse.hs
@@ -69,7 +69,7 @@ parseFigureSpec block@(CodeBlock (id', classes, attrs) content) = do
figureSpec :: Toolkit -> PlotM FigureSpec
figureSpec toolkit = do
- conf <- ask
+ conf <- asks envConfig
let extraAttrs' = parseExtraAttrs toolkit attrs'
header = comment toolkit $ "Generated by pandoc-plot " <> ((pack . showVersion) version)
defaultPreamble = preambleSelector toolkit conf
diff --git a/src/Text/Pandoc/Filter/Plot/Renderers.hs b/src/Text/Pandoc/Filter/Plot/Renderers.hs
index 9091dd5..4ba0bbd 100644
--- a/src/Text/Pandoc/Filter/Plot/Renderers.hs
+++ b/src/Text/Pandoc/Filter/Plot/Renderers.hs
@@ -30,7 +30,7 @@ module Text.Pandoc.Filter.Plot.Renderers (
, OutputSpec(..)
) where
-import Control.Concurrent.Async (forConcurrently)
+import Control.Concurrent.Async.Lifted (forConcurrently)
import Data.List ((\\))
import Data.Map.Strict (Map)
@@ -175,9 +175,8 @@ unavailableToolkits conf = runPlotM conf unavailableToolkitsM
-- | Monadic version of @availableToolkits@.
availableToolkitsM :: PlotM [Toolkit]
availableToolkitsM = do
- conf <- ask
- mtks <- liftIO $ forConcurrently toolkits $ \tk -> do
- available <- runPlotM conf $ toolkitAvailable tk
+ mtks <- forConcurrently toolkits $ \tk -> do
+ available <- toolkitAvailable tk
if available
then return $ Just tk
else return Nothing
diff --git a/src/Text/Pandoc/Filter/Plot/Renderers/Matlab.hs b/src/Text/Pandoc/Filter/Plot/Renderers/Matlab.hs
index 090f182..4d36108 100644
--- a/src/Text/Pandoc/Filter/Plot/Renderers/Matlab.hs
+++ b/src/Text/Pandoc/Filter/Plot/Renderers/Matlab.hs
@@ -40,7 +40,7 @@ matlabCommand OutputSpec{..} = do
-- Therefore, we cannot rely on this behavior to know if matlab is present,
-- like other toolkits.
matlabAvailable :: PlotM Bool
-matlabAvailable = asks matlabExe >>= (\exe -> liftIO $ existsOnPath (exe <> exeExtension))
+matlabAvailable = asksConfig matlabExe >>= (\exe -> liftIO $ existsOnPath (exe <> exeExtension))
matlabCapture :: FigureSpec -> FilePath -> Script
diff --git a/src/Text/Pandoc/Filter/Plot/Renderers/Prelude.hs b/src/Text/Pandoc/Filter/Plot/Renderers/Prelude.hs
index 2b4105f..5d39133 100644
--- a/src/Text/Pandoc/Filter/Plot/Renderers/Prelude.hs
+++ b/src/Text/Pandoc/Filter/Plot/Renderers/Prelude.hs
@@ -56,15 +56,15 @@ tryToFindExe fp = findExecutable fp >>= maybe (return fp) return
-- | Path to the executable of a toolkit. If the executable can
-- be found, then it will be the full path to it.
executable :: Toolkit -> PlotM FilePath
-executable Matplotlib = asks matplotlibExe >>= liftIO . tryToFindExe
-executable PlotlyPython = asks plotlyPythonExe >>= liftIO . tryToFindExe
-executable PlotlyR = asks plotlyRExe >>= liftIO . tryToFindExe
-executable Matlab = asks matlabExe >>= liftIO . tryToFindExe
-executable Mathematica = asks mathematicaExe >>= liftIO . tryToFindExe
-executable Octave = asks octaveExe >>= liftIO . tryToFindExe
-executable GGPlot2 = asks ggplot2Exe >>= liftIO . tryToFindExe
-executable GNUPlot = asks gnuplotExe >>= liftIO . tryToFindExe
-executable Graphviz = asks graphvizExe >>= liftIO . tryToFindExe
+executable Matplotlib = asksConfig matplotlibExe >>= liftIO . tryToFindExe
+executable PlotlyPython = asksConfig plotlyPythonExe >>= liftIO . tryToFindExe
+executable PlotlyR = asksConfig plotlyRExe >>= liftIO . tryToFindExe
+executable Matlab = asksConfig matlabExe >>= liftIO . tryToFindExe
+executable Mathematica = asksConfig mathematicaExe >>= liftIO . tryToFindExe
+executable Octave = asksConfig octaveExe >>= liftIO . tryToFindExe
+executable GGPlot2 = asksConfig ggplot2Exe >>= liftIO . tryToFindExe
+executable GNUPlot = asksConfig gnuplotExe >>= liftIO . tryToFindExe
+executable Graphviz = asksConfig graphvizExe >>= liftIO . tryToFindExe
-- | Internal description of all information
diff --git a/stack.yaml b/stack.yaml
index 0a80fd7..5d7d85c 100644
--- a/stack.yaml
+++ b/stack.yaml
@@ -1,4 +1,4 @@
-resolver: lts-15.16 # GHC 8.8.3
+resolver: lts-16.0 # GHC 8.8.3
packages:
- .
diff --git a/tests/Common.hs b/tests/Common.hs
index 764b203..b0aca46 100644
--- a/tests/Common.hs
+++ b/tests/Common.hs
@@ -43,7 +43,7 @@ testFileCreation tk =
ensureDirectoryExistsAndEmpty tempDir
let cb = (addDirectory tempDir $ codeBlock tk (trivialContent tk))
- _ <- make defaultTestConfig cb
+ _ <- runPlotM defaultTestConfig $ make cb
filesCreated <- length <$> listDirectory tempDir
assertEqual "" 2 filesCreated
@@ -58,7 +58,7 @@ testFileInclusion tk =
let cb = (addPreamble (include tk) $
addDirectory tempDir $ codeBlock tk (trivialContent tk))
- _ <- make defaultTestConfig cb
+ _ <- runPlotM defaultTestConfig $ make cb
inclusion <- readFile (include tk)
sourcePath <- head . filter (isExtensionOf "txt") <$> listDirectory tempDir
src <- readFile (tempDir </> sourcePath)
@@ -84,7 +84,7 @@ testSaveFormat tk =
let fmt = head (supportedSaveFormats tk)
cb = (addSaveFormat fmt $
addDirectory tempDir $ codeBlock tk (trivialContent tk))
- _ <- make defaultTestConfig cb
+ _ <- runPlotM defaultTestConfig $ make cb
numberjpgFiles <-
length <$> filter (isExtensionOf (extension fmt)) <$>
listDirectory tempDir
@@ -108,8 +108,8 @@ testWithSource tk =
$ addDirectory tempDir
$ addCaption expected
$ codeBlock tk (trivialContent tk)
- blockNoSource <- make defaultTestConfig noSource
- blockWithSource <- make defaultTestConfig withSource
+ blockNoSource <- runPlotM defaultTestConfig $ make noSource
+ blockWithSource <- runPlotM defaultTestConfig $ make withSource
-- In the case where source=false, the caption is used verbatim.
-- Otherwise, links will be appended to the caption; hence, the caption
@@ -148,7 +148,7 @@ testOverrideConfiguration tk =
let cb = addDirectory tempDir
$ addSaveFormat PNG
$ codeBlock tk (trivialContent tk)
- _ <- make config cb
+ _ <- runPlotM config $ make cb
numberPngFiles <-
length <$> filter (isExtensionOf (extension PNG)) <$>
@@ -175,7 +175,7 @@ testMarkdownFormattingCaption1 tk =
$ addCaption "**caption**"
$ codeBlock tk (trivialContent tk)
fmt = B.Format "markdown"
- result <- make (defaultTestConfig {captionFormat=fmt}) cb
+ result <- runPlotM (defaultTestConfig {captionFormat=fmt}) $ make cb
assertIsInfix expected (extractCaption result)
where
extractCaption (B.Para blocks) = extractImageCaption . head $ blocks
@@ -200,7 +200,7 @@ testMarkdownFormattingCaption2 tk =
$ addCaption "[title](https://google.com)"
$ codeBlock tk (trivialContent tk)
fmt = B.Format "markdown"
- result <- make (defaultTestConfig {captionFormat=fmt}) cb
+ result <- runPlotM (defaultTestConfig {captionFormat=fmt}) $ make cb
assertIsInfix expected (extractCaption result)
where
extractCaption (B.Para blocks) = extractImageCaption . head $ blocks
@@ -222,7 +222,7 @@ testCleanOutputDirs tk =
let cb = addDirectory tempDir
$ codeBlock tk (trivialContent tk)
- result <- make defaultTestConfig cb
+ result <- runPlotM defaultTestConfig $ make cb
cleanedDirs <- cleanOutputDirs defaultTestConfig cb
assertEqual "" [tempDir] cleanedDirs
@@ -244,7 +244,7 @@ testChecksFail tk =
ensureDirectoryExistsAndEmpty tempDir
let cb = addDirectory tempDir $ codeBlock Matplotlib "plt.show()"
- result <- makeEither defaultTestConfig cb
+ result <- runPlotM defaultTestConfig $ makeEither cb
let expectedCheck :: Either PandocPlotError a -> Bool
expectedCheck (Left (ScriptChecksFailedError _)) = True
expectedCheck _ = False