{-# LANGUAGE OverloadedStrings #-}
{- |
   Module      : Text.Pandoc.Readers.Org
   Copyright   : Copyright (C) 2014-2022 Albert Krewinkel
   License     : GNU GPL, version 2 or above

   Maintainer  : Albert Krewinkel <tarleb+pandoc@moltkeplatz.de>

Conversion of org-mode formatted plain text to 'Pandoc' document.
-}
module Text.Pandoc.Readers.Org ( readOrg ) where

import Text.Pandoc.Readers.Org.Blocks (blockList, meta)
import Text.Pandoc.Readers.Org.ParserState (optionsToParserState)
import Text.Pandoc.Readers.Org.Parsing (OrgParser, readWithM)

import Text.Pandoc.Class.PandocMonad (PandocMonad)
import Text.Pandoc.Definition
import Text.Pandoc.Options
import Text.Pandoc.Parsing (reportLogMessages)
import Text.Pandoc.Sources (ToSources(..), ensureFinalNewlines)
import Control.Monad.Except (throwError)
import Control.Monad.Reader (runReaderT)

-- | Parse org-mode string and return a Pandoc document.
readOrg :: (PandocMonad m, ToSources a)
        => ReaderOptions -- ^ Reader options
        -> a
        -> m Pandoc
readOrg :: forall (m :: * -> *) a.
(PandocMonad m, ToSources a) =>
ReaderOptions -> a -> m Pandoc
readOrg ReaderOptions
opts a
s = do
  Either PandocError Pandoc
parsed <- forall a b c. (a -> b -> c) -> b -> a -> c
flip forall r (m :: * -> *) a. ReaderT r m a -> r -> m a
runReaderT forall a. Default a => a
def forall a b. (a -> b) -> a -> b
$
            forall (m :: * -> *) t st a.
(Monad m, ToSources t) =>
ParserT Sources st m a -> st -> t -> m (Either PandocError a)
readWithM forall (m :: * -> *). PandocMonad m => OrgParser m Pandoc
parseOrg (ReaderOptions -> OrgParserState
optionsToParserState ReaderOptions
opts)
            (Int -> Sources -> Sources
ensureFinalNewlines Int
2 (forall a. ToSources a => a -> Sources
toSources a
s))
  case Either PandocError Pandoc
parsed of
    Right Pandoc
result -> forall (m :: * -> *) a. Monad m => a -> m a
return Pandoc
result
    Left  PandocError
e      -> forall e (m :: * -> *) a. MonadError e m => e -> m a
throwError PandocError
e

--
-- Parser
--
parseOrg :: PandocMonad m => OrgParser m Pandoc
parseOrg :: forall (m :: * -> *). PandocMonad m => OrgParser m Pandoc
parseOrg = do
  [Block]
blocks' <- forall (m :: * -> *). PandocMonad m => OrgParser m [Block]
blockList
  Meta
meta'   <- forall (m :: * -> *). Monad m => OrgParser m Meta
meta
  forall (m :: * -> *) st s.
(PandocMonad m, HasLogMessages st) =>
ParserT s st m ()
reportLogMessages
  forall (m :: * -> *) a. Monad m => a -> m a
return forall a b. (a -> b) -> a -> b
$ Meta -> [Block] -> Pandoc
Pandoc Meta
meta' [Block]
blocks'