    {-# LANGUAGE OverloadedStrings, ScopedTypeVariables, CPP #-}
    {- |
    Module      : Text.Pandoc.Image
    Copyright   : Copyright (C) 2020-2024 John MacFarlane
    License     : GNU GPL, version 2 or above

    Maintainer  : John MacFarlane <jgm@berkeley.edu>
    Stability   : alpha
    Portability : portable

    Functions for converting images.
    -}
    module Text.Pandoc.Image ( svgToPng ) where
    import Text.Pandoc.Process (pipeProcess)
    import qualified Data.ByteString.Lazy as L
    import System.Exit
    import Data.Text (Text)
    import Text.Pandoc.Shared (tshow)
    import qualified Control.Exception as E
    import Control.Monad.IO.Class (MonadIO(liftIO))

    -- | Convert svg image to png. rsvg-convert
    -- is used and must be available on the path.
    svgToPng :: MonadIO m
             => Int           -- ^ DPI
             -> L.ByteString  -- ^ Input image as bytestring
             -> m (Either Text L.ByteString)
    svgToPng :: forall (m :: * -> *).
    MonadIO m =>
    Int -> ByteString -> m (Either Text ByteString)
    svgToPng Int
    dpi ByteString
    bs = do
      let dpi' :: String
    dpi' = Int -> String
    forall a. Show a => a -> String
    show Int
    dpi
      IO (Either Text ByteString) -> m (Either Text ByteString)
    forall a. IO a -> m a
    forall (m :: * -> *) a. MonadIO m => IO a -> m a
    liftIO (IO (Either Text ByteString) -> m (Either Text ByteString))
    -> IO (Either Text ByteString) -> m (Either Text ByteString)
    forall a b. (a -> b) -> a -> b
    $ IO (Either Text ByteString)
    -> (SomeException -> IO (Either Text ByteString))
    -> IO (Either Text ByteString)
    forall e a. Exception e => IO a -> (e -> IO a) -> IO a
    E.catch
           (do (exit, out) <- Maybe [(String, String)]
    -> String -> [String] -> ByteString -> IO (ExitCode, ByteString)
    pipeProcess Maybe [(String, String)]
    forall a. Maybe a
    Nothing String
    "rsvg-convert"
                              [String
    "-f",String
    "png",String
    "-a",String
    "--dpi-x",String
    dpi',String
    "--dpi-y",String
    dpi']
                              ByteString
    bs
               return $ if exit == ExitSuccess
                  then Right out
                  else Left "conversion from SVG failed")
           (\(SomeException
    e :: E.SomeException) -> Either Text ByteString -> IO (Either Text ByteString)
    forall a. a -> IO a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (Either Text ByteString -> IO (Either Text ByteString))
    -> Either Text ByteString -> IO (Either Text ByteString)
    forall a b. (a -> b) -> a -> b
    $ Text -> Either Text ByteString
    forall a b. a -> Either a b
    Left (Text -> Either Text ByteString) -> Text -> Either Text ByteString
    forall a b. (a -> b) -> a -> b
    $
               Text
    "check that rsvg-convert is in path.\n" Text -> Text -> Text
    forall a. Semigroup a => a -> a -> a
    <> SomeException -> Text
    forall a. Show a => a -> Text
    tshow SomeException
    e)