    {-# LANGUAGE LambdaCase          #-}
    {-# LANGUAGE OverloadedStrings   #-}
    {-# LANGUAGE ScopedTypeVariables #-}
    {-# LANGUAGE TypeApplications    #-}
    {- |
       Module      : Text.Pandoc.Lua.Module.Utils
       Copyright   : © 2017-2026 Albert Krewinkel
       License     : GNU GPL, version 2 or above

       Maintainer  : Albert Krewinkel <albert+pandoc@tarleb.com>
       Stability   : alpha

    Utility module for Lua, exposing internal helper functions.
    -}
    module Text.Pandoc.Lua.Module.Utils
      ( documentedModule
      , sha1
      ) where

    import Control.Applicative ((<|>))
    import Control.Monad ((<$!>))
    import Control.Monad.Except (MonadError (throwError))
    import Crypto.Hash (hashWith, SHA1(SHA1))
    import Data.Data (showConstr, toConstr)
    import Data.Default (def)
    import Data.Maybe (fromMaybe)
    import Data.Version (Version, makeVersion)
    import HsLua as Lua
    import HsLua.Module.Version (peekVersionFuzzy, pushVersion)
    import Text.Pandoc.Citeproc (getReferences, processCitations)
    import Text.Pandoc.Definition
    import Text.Pandoc.Error (PandocError (PandocLuaError))
    import Text.Pandoc.Filter (applyJSONFilter)
    import Text.Pandoc.Format (FlavoredFormat (formatName), parseFlavoredFormat)
    import Text.Pandoc.Lua.Documentation (renderDocumentation)
    import Text.Pandoc.Lua.Filter (runFilterFile')
    import Text.Pandoc.Lua.Marshal.AST
    import Text.Pandoc.Lua.Marshal.Format (peekFlavoredFormat)
    import Text.Pandoc.Lua.Marshal.Reference
    import Text.Pandoc.Lua.PandocLua (PandocLua (unPandocLua))
    import Text.Pandoc.Options (WriterOptions (writerExtensions))
    import Text.Pandoc.Writers (Writer (..), getWriter)

    import qualified Data.Map as Map
    import qualified Data.Text as T
    import qualified Text.Pandoc.Builder as B
    import qualified Text.Pandoc.Shared as Shared
    import qualified Text.Pandoc.UTF8 as UTF8
    import qualified Text.Pandoc.Writers.Shared as Shared

    -- | Push the "pandoc.utils" module to the Lua stack.
    documentedModule :: Module PandocError
    documentedModule :: Module PandocError
    documentedModule = Name -> Module PandocError
    forall e. Name -> Module e
    defmodule Name
    "pandoc.utils"
      Module PandocError -> Text -> Module PandocError
    forall a. HasDescription a => a -> Text -> a
    `withDescription` [Text] -> Text
    T.unlines
        [ Text
    "This module exposes internal pandoc functions and utility"
        , Text
    "functions."
        ]
      Module PandocError
    -> [DocumentedFunction PandocError] -> Module PandocError
    forall e. Module e -> [DocumentedFunction e] -> Module e
    `withFunctions`
        [ DocumentedFunction PandocError
    forall e. LuaError e => DocumentedFunction e
    blocks_to_inlines DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    2,Int
    3]
        , DocumentedFunction PandocError
    citeproc          DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    19,Int
    1]
        , DocumentedFunction PandocError
    documentation     DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    3,Int
    8,Int
    4]
        , DocumentedFunction PandocError
    forall e. LuaError e => DocumentedFunction e
    equals            DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    5]
        , DocumentedFunction PandocError
    forall e. LuaError e => DocumentedFunction e
    from_simple_table DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    11]
        , DocumentedFunction PandocError
    forall e. LuaError e => DocumentedFunction e
    make_sections     DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    8]
        , DocumentedFunction PandocError
    forall e. DocumentedFunction e
    normalize_date    DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    0,Int
    6]
        , DocumentedFunction PandocError
    references        DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    17]
        , DocumentedFunction PandocError
    run_json_filter   DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    1,Int
    1]
        , DocumentedFunction PandocError
    run_lua_filter    DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    3,Int
    2,Int
    1]
        , DocumentedFunction PandocError
    forall e. DocumentedFunction e
    sha1              DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    0,Int
    6]
        , DocumentedFunction PandocError
    forall e. LuaError e => DocumentedFunction e
    stringify         DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    0,Int
    6]
        , DocumentedFunction PandocError
    forall e. LuaError e => DocumentedFunction e
    to_roman_numeral  DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    0,Int
    6]
        , DocumentedFunction PandocError
    to_simple_table   DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    11]
        , DocumentedFunction PandocError
    forall e. DocumentedFunction e
    type'             DocumentedFunction PandocError
    -> Version -> DocumentedFunction PandocError
    forall e. DocumentedFunction e -> Version -> DocumentedFunction e
    `since` [Int] -> Version
    v[Int
    2,Int
    17]

        , Name
    -> (Version -> LuaE PandocError Version)
    -> HsFnPrecursor PandocError (Version -> LuaE PandocError Version)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "Version"
          ### liftPure (id @Version)
          HsFnPrecursor PandocError (Version -> LuaE PandocError Version)
    -> Parameter PandocError Version
    -> HsFnPrecursor PandocError (LuaE PandocError Version)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError Version
    -> TypeSpec -> Text -> Text -> Parameter PandocError Version
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError Version
    forall e. LuaError e => Peeker e Version
    peekVersionFuzzy TypeSpec
    "Version|string|{integer,...}|number"
                Text
    "v" Text
    "version description"
          HsFnPrecursor PandocError (LuaE PandocError Version)
    -> FunctionResults PandocError Version
    -> DocumentedFunction PandocError
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher PandocError Version
    -> TypeSpec -> Text -> FunctionResults PandocError Version
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher PandocError Version
    forall e. LuaError e => Pusher e Version
    pushVersion TypeSpec
    "Version" Text
    "new Version object"
          #? "Creates a Version object."
        ]
     where
      v :: [Int] -> Version
    v = [Int] -> Version
    makeVersion

    blocks_to_inlines :: LuaError e => DocumentedFunction e
    blocks_to_inlines :: forall e. LuaError e => DocumentedFunction e
    blocks_to_inlines = Name
    -> ([Block] -> Maybe [Inline] -> LuaE e [Inline])
    -> HsFnPrecursor e ([Block] -> Maybe [Inline] -> LuaE e [Inline])
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "blocks_to_inlines"
      ### (\blks mSep -> do
              let sep = maybe Shared.defaultBlocksSeparator B.fromList mSep
              return $ B.toList (Shared.blocksToInlinesWithSep sep blks))
      HsFnPrecursor e ([Block] -> Maybe [Inline] -> LuaE e [Inline])
    -> Parameter e [Block]
    -> HsFnPrecursor e (Maybe [Inline] -> LuaE e [Inline])
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e [Block] -> TypeSpec -> Text -> Text -> Parameter e [Block]
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter (Peeker e Block -> Peeker e [Block]
    forall a e. LuaError e => Peeker e a -> Peeker e [a]
    peekList Peeker e Block
    forall e. LuaError e => Peeker e Block
    peekBlock) TypeSpec
    "Blocks"
            Text
    "blocks"
            Text
    "List of [[Block]] elements to be flattened."
      HsFnPrecursor e (Maybe [Inline] -> LuaE e [Inline])
    -> Parameter e (Maybe [Inline])
    -> HsFnPrecursor e (LuaE e [Inline])
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Parameter e [Inline] -> Parameter e (Maybe [Inline])
    forall e a. Parameter e a -> Parameter e (Maybe a)
    opt (Peeker e [Inline]
    -> TypeSpec -> Text -> Text -> Parameter e [Inline]
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter (Peeker e Inline -> Peeker e [Inline]
    forall a e. LuaError e => Peeker e a -> Peeker e [a]
    peekList Peeker e Inline
    forall e. LuaError e => Peeker e Inline
    peekInline) TypeSpec
    "Inlines" Text
    "sep"
               (Text
    "List of [[Inline]] elements inserted as separator between\n" Text -> Text -> Text
    forall a. Semigroup a => a -> a -> a
    <>
                Text
    "two consecutive blocks; defaults to `{pandoc.LineBreak()}`."))
      HsFnPrecursor e (LuaE e [Inline])
    -> FunctionResults e [Inline] -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e [Inline] -> TypeSpec -> Text -> FunctionResults e [Inline]
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e [Inline]
    forall e. LuaError e => Pusher e [Inline]
    pushInlines TypeSpec
    "Inlines" Text
    ""
      #? T.unlines
      [ "Squash a list of blocks into a list of inlines."
      , ""
      , "Usage"
      , ""
      , "    local blocks = {"
      , "      pandoc.Para{ pandoc.Str 'Paragraph1' },"
      , "      pandoc.Para{ pandoc.Emph 'Paragraph2' }"
      , "    }"
      , "    local inlines = pandoc.utils.blocks_to_inlines(blocks)"
      , "    assert("
      , "      inlines == pandoc.Inlines {"
      , "        pandoc.Str 'Paragraph1',"
      , "        pandoc.Linebreak(),"
      , "        pandoc.Emph{ pandoc.Str 'Paragraph2' }"
      , "      }"
      , "    )"
      ]

    citeproc :: DocumentedFunction PandocError
    citeproc :: DocumentedFunction PandocError
    citeproc = Name
    -> (Pandoc -> LuaE PandocError Pandoc)
    -> HsFnPrecursor PandocError (Pandoc -> LuaE PandocError Pandoc)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "citeproc"
      ### unPandocLua . processCitations
      HsFnPrecursor PandocError (Pandoc -> LuaE PandocError Pandoc)
    -> Parameter PandocError Pandoc
    -> HsFnPrecursor PandocError (LuaE PandocError Pandoc)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError Pandoc
    -> TypeSpec -> Text -> Text -> Parameter PandocError Pandoc
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError Pandoc
    forall e. LuaError e => Peeker e Pandoc
    peekPandoc TypeSpec
    "Pandoc" Text
    "doc" Text
    "document"
      HsFnPrecursor PandocError (LuaE PandocError Pandoc)
    -> FunctionResults PandocError Pandoc
    -> DocumentedFunction PandocError
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher PandocError Pandoc
    -> TypeSpec -> Text -> FunctionResults PandocError Pandoc
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher PandocError Pandoc
    forall e. LuaError e => Pusher e Pandoc
    pushPandoc TypeSpec
    "Pandoc" Text
    "processed document"
      #?  T.unlines
          [ "Process the citations in the file, replacing them with "
          , "rendered citations and adding a bibliography. "
          , "See the manual section on citation rendering for details."
          , ""
          , "Usage:"
          , ""
          , "    -- Lua filter that behaves like `--citeproc`"
          , "    function Pandoc (doc)"
          , "      return pandoc.utils.citeproc(doc)"
          , "    end"
          ]

    documentation :: DocumentedFunction PandocError
    documentation :: DocumentedFunction PandocError
    documentation = Name
    -> (StackIndex
        -> Maybe FlavoredFormat -> LuaE PandocError (Either [Block] Text))
    -> HsFnPrecursor
         PandocError
         (StackIndex
          -> Maybe FlavoredFormat -> LuaE PandocError (Either [Block] Text))
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "documentation"
      ### (\idx mformat -> do
              docobj <- getdocumentation idx >>= \case
                TypeNil -> fail "Undocumented object"
                _ -> forcePeek $ peekDocumentationObject top
              let blocks = renderDocumentation docobj
              if maybe mempty formatName mformat == "blocks"
                then pure . Left $ B.toList blocks
                else unPandocLua $ do
                  flvrd <- maybe (parseFlavoredFormat "ansi") pure mformat
                  getWriter flvrd >>= \case
                    (TextWriter w, es) -> Right <$>
                      w def{ writerExtensions = es } (B.doc blocks)
                    _ -> throwError $ PandocLuaError
                      "ByteString writers are not supported here.")
      HsFnPrecursor
      PandocError
      (StackIndex
       -> Maybe FlavoredFormat -> LuaE PandocError (Either [Block] Text))
    -> Parameter PandocError StackIndex
    -> HsFnPrecursor
         PandocError
         (Maybe FlavoredFormat -> LuaE PandocError (Either [Block] Text))
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError StackIndex
    -> TypeSpec -> Text -> Text -> Parameter PandocError StackIndex
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError StackIndex
    forall a. a -> Peek PandocError a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure TypeSpec
    "any" Text
    "object" Text
    "Retrieve documentation for this object"
      HsFnPrecursor
      PandocError
      (Maybe FlavoredFormat -> LuaE PandocError (Either [Block] Text))
    -> Parameter PandocError (Maybe FlavoredFormat)
    -> HsFnPrecursor
         PandocError (LuaE PandocError (Either [Block] Text))
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Parameter PandocError FlavoredFormat
    -> Parameter PandocError (Maybe FlavoredFormat)
    forall e a. Parameter e a -> Parameter e (Maybe a)
    opt (Peeker PandocError FlavoredFormat
    -> TypeSpec -> Text -> Text -> Parameter PandocError FlavoredFormat
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError FlavoredFormat
    peekFlavoredFormat TypeSpec
    "string|table" Text
    "format"
                Text
    "result format; defaults to `'ansi'`")
      HsFnPrecursor PandocError (LuaE PandocError (Either [Block] Text))
    -> FunctionResults PandocError (Either [Block] Text)
    -> DocumentedFunction PandocError
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher PandocError (Either [Block] Text)
    -> TypeSpec
    -> Text
    -> FunctionResults PandocError (Either [Block] Text)
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult (([Block] -> LuaE PandocError ())
    -> (Text -> LuaE PandocError ())
    -> Pusher PandocError (Either [Block] Text)
    forall a c b. (a -> c) -> (b -> c) -> Either a b -> c
    either [Block] -> LuaE PandocError ()
    forall e. LuaError e => Pusher e [Block]
    pushBlocks Text -> LuaE PandocError ()
    forall e. Pusher e Text
    pushText) TypeSpec
    "string|Blocks"
            Text
    "rendered documentation"
      #? "Return the documentation for a function or module defined by pandoc.\
         \ Throws an error if there is no documentation for the given object.\n\
         \\n\
         \The result format can be any textual format accepted by `pandoc.write`,\
         \ and the documentation will be returned in that format.\
         \ Additionally, the special format `blocks` is accepted, in which case\
         \ the documentation is returned as [[Blocks]]."

    equals :: LuaError e => DocumentedFunction e
    equals :: forall e. LuaError e => DocumentedFunction e
    equals = Name
    -> (StackIndex -> StackIndex -> LuaE e Bool)
    -> HsFnPrecursor e (StackIndex -> StackIndex -> LuaE e Bool)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "equals"
      ### equal
      HsFnPrecursor e (StackIndex -> StackIndex -> LuaE e Bool)
    -> Parameter e StackIndex
    -> HsFnPrecursor e (StackIndex -> LuaE e Bool)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e StackIndex
    -> TypeSpec -> Text -> Text -> Parameter e StackIndex
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e StackIndex
    forall a. a -> Peek e a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure TypeSpec
    "any" Text
    "element1" Text
    ""
      HsFnPrecursor e (StackIndex -> LuaE e Bool)
    -> Parameter e StackIndex -> HsFnPrecursor e (LuaE e Bool)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e StackIndex
    -> TypeSpec -> Text -> Text -> Parameter e StackIndex
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e StackIndex
    forall a. a -> Peek e a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure TypeSpec
    "any" Text
    "element2" Text
    ""
      HsFnPrecursor e (LuaE e Bool)
    -> FunctionResults e Bool -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e Bool -> TypeSpec -> Text -> FunctionResults e Bool
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e Bool
    forall e. Pusher e Bool
    pushBool TypeSpec
    "boolean"
            Text
    "Whether the two objects represent the same element"
      #? T.unlines
      [ "Test equality of AST elements. Elements in Lua are considered"
      , "equal if and only if the objects obtained by unmarshaling are"
      , "equal."
      , ""
      , "**This function is deprecated.** Use the normal Lua `==` equality"
      , "operator instead."
      ]

    -- | Converts an old/simple table into a normal table block element.
    from_simple_table :: LuaError e => DocumentedFunction e
    from_simple_table :: forall e. LuaError e => DocumentedFunction e
    from_simple_table = Name
    -> (SimpleTable -> LuaE e Block)
    -> HsFnPrecursor e (SimpleTable -> LuaE e Block)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "from_simple_table"
      ### liftPure
          (\(SimpleTable capt aligns widths head' body) ->
              Table
              nullAttr
              (Caption Nothing [Plain capt | not (null capt)])
              (zipWith (\a w -> (a, toColWidth w)) aligns widths)
              (TableHead nullAttr [blockListToRow head' | not (null head') ])
              [TableBody nullAttr 0 [] $ map blockListToRow body | not (null body)]
              (TableFoot nullAttr []))
      HsFnPrecursor e (SimpleTable -> LuaE e Block)
    -> Parameter e SimpleTable -> HsFnPrecursor e (LuaE e Block)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e SimpleTable
    -> TypeSpec -> Text -> Text -> Parameter e SimpleTable
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e SimpleTable
    forall e. LuaError e => Peeker e SimpleTable
    peekSimpleTable TypeSpec
    "SimpleTable" Text
    "simple_tbl" Text
    ""
      HsFnPrecursor e (LuaE e Block)
    -> FunctionResults e Block -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e Block -> TypeSpec -> Text -> FunctionResults e Block
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e Block
    forall e. LuaError e => Pusher e Block
    pushBlock TypeSpec
    "Block" Text
    "table block element"
      #? T.unlines
      [ "Creates a [[Table]] block element from a [[SimpleTable]]. This is"
      , "useful for dealing with legacy code which was written for pandoc"
      , "versions older than 2.10."
      , ""
      , "Usage:"
      , ""
      , "    local simple = pandoc.SimpleTable(table)"
      , "    -- modify, using pre pandoc 2.10 methods"
      , "    simple.caption = pandoc.SmallCaps(simple.caption)"
      , "    -- create normal table block again"
      , "    table = pandoc.utils.from_simple_table(simple)"
      ]
     where
      blockListToRow :: [[Block]] -> Row
      blockListToRow :: [[Block]] -> Row
    blockListToRow = Attr -> [Cell] -> Row
    Row Attr
    nullAttr ([Cell] -> Row) -> ([[Block]] -> [Cell]) -> [[Block]] -> Row
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ([Block] -> Cell) -> [[Block]] -> [Cell]
    forall a b. (a -> b) -> [a] -> [b]
    map (Blocks -> Cell
    B.simpleCell (Blocks -> Cell) -> ([Block] -> Blocks) -> [Block] -> Cell
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . [Block] -> Blocks
    forall a. [a] -> Many a
    B.fromList)

      toColWidth :: Double -> ColWidth
      toColWidth :: Double -> ColWidth
    toColWidth Double
    0 = ColWidth
    ColWidthDefault
      toColWidth Double
    w = Double -> ColWidth
    ColWidth Double
    w

    make_sections :: LuaError e => DocumentedFunction e
    make_sections :: forall e. LuaError e => DocumentedFunction e
    make_sections = Name
    -> (Bool -> Maybe Int -> [Block] -> LuaE e [Block])
    -> HsFnPrecursor e (Bool -> Maybe Int -> [Block] -> LuaE e [Block])
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "make_sections"
      ### liftPure3 Shared.makeSections
      HsFnPrecursor e (Bool -> Maybe Int -> [Block] -> LuaE e [Block])
    -> Parameter e Bool
    -> HsFnPrecursor e (Maybe Int -> [Block] -> LuaE e [Block])
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e Bool -> TypeSpec -> Text -> Text -> Parameter e Bool
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e Bool
    forall e. Peeker e Bool
    peekBool TypeSpec
    "boolean" Text
    "number_sections"
          (Text
    "whether section divs should get an additional `number`\n" Text -> Text -> Text
    forall a. Semigroup a => a -> a -> a
    <>
           Text
    "attribute containing the section number.")
      HsFnPrecursor e (Maybe Int -> [Block] -> LuaE e [Block])
    -> Parameter e (Maybe Int)
    -> HsFnPrecursor e ([Block] -> LuaE e [Block])
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e (Maybe Int)
    -> TypeSpec -> Text -> Text -> Parameter e (Maybe Int)
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter (\StackIndex
    i -> (Maybe Int
    forall a. Maybe a
    Nothing Maybe Int -> Peek e () -> Peek e (Maybe Int)
    forall a b. a -> Peek e b -> Peek e a
    forall (f :: * -> *) a b. Functor f => a -> f b -> f a
    <$ Peeker e ()
    forall e. Peeker e ()
    peekNil StackIndex
    i) Peek e (Maybe Int) -> Peek e (Maybe Int) -> Peek e (Maybe Int)
    forall a. Peek e a -> Peek e a -> Peek e a
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
    <|> (Int -> Maybe Int
    forall a. a -> Maybe a
    Just (Int -> Maybe Int) -> Peek e Int -> Peek e (Maybe Int)
    forall (m :: * -> *) a b. Monad m => (a -> b) -> m a -> m b
    <$!> Peeker e Int
    forall a e. (Integral a, Read a) => Peeker e a
    peekIntegral StackIndex
    i))
            TypeSpec
    "integer|nil" Text
    "baselevel"
            Text
    "shift top-level headings to this level"
      HsFnPrecursor e ([Block] -> LuaE e [Block])
    -> Parameter e [Block] -> HsFnPrecursor e (LuaE e [Block])
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e [Block] -> TypeSpec -> Text -> Text -> Parameter e [Block]
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter (Peeker e Block -> Peeker e [Block]
    forall a e. LuaError e => Peeker e a -> Peeker e [a]
    peekList Peeker e Block
    forall e. LuaError e => Peeker e Block
    peekBlock) TypeSpec
    "Blocks"
            Text
    "blocks" Text
    "list of blocks to process"
      HsFnPrecursor e (LuaE e [Block])
    -> FunctionResults e [Block] -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e [Block] -> TypeSpec -> Text -> FunctionResults e [Block]
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e [Block]
    forall e. LuaError e => Pusher e [Block]
    pushBlocks TypeSpec
    "Blocks"
            Text
    "blocks with sections"
      #? T.unlines
      [ "Converts a list of [[Block]] elements into sections."
      , "`Div`s will be created beginning at each `Header`"
      , "and containing following content until the next `Header`"
      , "of comparable level.  If `number_sections` is true,"
      , "a `number` attribute will be added to each `Header`"
      , "containing the section number. If `base_level` is"
      , "non-null, `Header` levels will be reorganized so"
      , "that there are no gaps, and so that the base level"
      , "is the level specified."
      ]

    normalize_date :: DocumentedFunction e
    normalize_date :: forall e. DocumentedFunction e
    normalize_date = Name
    -> (Text -> LuaE e (Maybe Text))
    -> HsFnPrecursor e (Text -> LuaE e (Maybe Text))
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "normalize_date"
      ### liftPure Shared.normalizeDate
      HsFnPrecursor e (Text -> LuaE e (Maybe Text))
    -> Parameter e Text -> HsFnPrecursor e (LuaE e (Maybe Text))
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e Text -> TypeSpec -> Text -> Text -> Parameter e Text
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e Text
    forall e. Peeker e Text
    peekText TypeSpec
    "string" Text
    "date" Text
    "the date string"
      HsFnPrecursor e (LuaE e (Maybe Text))
    -> FunctionResults e (Maybe Text) -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e (Maybe Text)
    -> TypeSpec -> Text -> FunctionResults e (Maybe Text)
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult (LuaE e () -> (Text -> LuaE e ()) -> Pusher e (Maybe Text)
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe LuaE e ()
    forall e. LuaE e ()
    pushnil Text -> LuaE e ()
    forall e. Pusher e Text
    pushText) TypeSpec
    "string|nil"
            Text
    "normalized date, or nil if normalization failed."
      #? T.unwords
      [ "Parse a date and convert (if possible) to \"YYYY-MM-DD\" format. We"
      , "limit years to the range 1601-9999 (ISO 8601 accepts greater than"
      , "or equal to 1583, but MS Word only accepts dates starting 1601)."
      , "Returns nil instead of a string if the conversion failed."
      ]

    -- | List of references in CSL format.
    references :: DocumentedFunction PandocError
    references :: DocumentedFunction PandocError
    references = Name
    -> (Pandoc -> LuaE PandocError [Reference Inlines])
    -> HsFnPrecursor
         PandocError (Pandoc -> LuaE PandocError [Reference Inlines])
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "references"
      ### (unPandocLua . getReferences Nothing)
      HsFnPrecursor
      PandocError (Pandoc -> LuaE PandocError [Reference Inlines])
    -> Parameter PandocError Pandoc
    -> HsFnPrecursor PandocError (LuaE PandocError [Reference Inlines])
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError Pandoc
    -> TypeSpec -> Text -> Text -> Parameter PandocError Pandoc
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError Pandoc
    forall e. LuaError e => Peeker e Pandoc
    peekPandoc TypeSpec
    "Pandoc" Text
    "doc" Text
    "document"
      HsFnPrecursor PandocError (LuaE PandocError [Reference Inlines])
    -> FunctionResults PandocError [Reference Inlines]
    -> DocumentedFunction PandocError
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher PandocError [Reference Inlines]
    -> TypeSpec
    -> Text
    -> FunctionResults PandocError [Reference Inlines]
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult (Pusher PandocError (Reference Inlines)
    -> Pusher PandocError [Reference Inlines]
    forall e a. LuaError e => Pusher e a -> Pusher e [a]
    pushPandocList Pusher PandocError (Reference Inlines)
    forall e. LuaError e => Pusher e (Reference Inlines)
    pushReference) TypeSpec
    "table"
           Text
    "lift of references."
      #? T.unlines
      [ "Get references defined inline in the metadata and via an external"
      , "bibliography. Only references that are actually cited in the"
      , "document (either with a genuine citation or with `nocite`) are"
      , "returned. URL variables are converted to links."
      , ""
      , "The structure used represent reference values corresponds to that"
      , "used in CSL JSON; the return value can be use as `references`"
      , "metadata, which is one of the values used by pandoc and citeproc"
      , "when generating bibliographies."
      , ""
      , "Usage:"
      , ""
      , "    -- Include all cited references in document"
      , "    function Pandoc (doc)"
      , "      doc.meta.references = pandoc.utils.references(doc)"
      , "      doc.meta.bibliography = nil"
      , "      return doc"
      , "    end"
      ]

    -- | Run a filter from a file.
    run_lua_filter :: DocumentedFunction PandocError
    run_lua_filter :: DocumentedFunction PandocError
    run_lua_filter = Name
    -> (Pandoc
        -> String -> Maybe StackIndex -> LuaE PandocError Pandoc)
    -> HsFnPrecursor
         PandocError
         (Pandoc -> String -> Maybe StackIndex -> LuaE PandocError Pandoc)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "run_lua_filter"
      ### (\doc fp mbenv -> do
             envIdx <- maybe copyOfGlobalTable pure mbenv
             runFilterFile' envIdx fp doc)
      HsFnPrecursor
      PandocError
      (Pandoc -> String -> Maybe StackIndex -> LuaE PandocError Pandoc)
    -> Parameter PandocError Pandoc
    -> HsFnPrecursor
         PandocError (String -> Maybe StackIndex -> LuaE PandocError Pandoc)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError Pandoc
    -> TypeSpec -> Text -> Text -> Parameter PandocError Pandoc
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError Pandoc
    forall e. LuaError e => Peeker e Pandoc
    peekPandoc TypeSpec
    "Pandoc" Text
    "doc" Text
    "the Pandoc document to filter"
      HsFnPrecursor
      PandocError (String -> Maybe StackIndex -> LuaE PandocError Pandoc)
    -> Parameter PandocError String
    -> HsFnPrecursor
         PandocError (Maybe StackIndex -> LuaE PandocError Pandoc)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError String
    -> TypeSpec -> Text -> Text -> Parameter PandocError String
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError String
    forall e. Peeker e String
    peekString TypeSpec
    "string" Text
    "filter" Text
    "filepath of the filter to run"
      HsFnPrecursor
      PandocError (Maybe StackIndex -> LuaE PandocError Pandoc)
    -> Parameter PandocError (Maybe StackIndex)
    -> HsFnPrecursor PandocError (LuaE PandocError Pandoc)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Parameter PandocError StackIndex
    -> Parameter PandocError (Maybe StackIndex)
    forall e a. Parameter e a -> Parameter e (Maybe a)
    opt (Peeker PandocError StackIndex
    -> TypeSpec -> Text -> Text -> Parameter PandocError StackIndex
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter (Name
    -> (StackIndex -> LuaE PandocError Bool)
    -> Peeker PandocError StackIndex
    -> Peeker PandocError StackIndex
    forall e a.
    Name -> (StackIndex -> LuaE e Bool) -> Peeker e a -> Peeker e a
    typeChecked Name
    "table" StackIndex -> LuaE PandocError Bool
    forall e. StackIndex -> LuaE e Bool
    istable Peeker PandocError StackIndex
    forall a. a -> Peek PandocError a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure) TypeSpec
    "table" Text
    "env"
                Text
    "environment to load and run the filter in")
      HsFnPrecursor PandocError (LuaE PandocError Pandoc)
    -> FunctionResults PandocError Pandoc
    -> DocumentedFunction PandocError
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher PandocError Pandoc
    -> TypeSpec -> Text -> FunctionResults PandocError Pandoc
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher PandocError Pandoc
    forall e. LuaError e => Pusher e Pandoc
    pushPandoc TypeSpec
    "Pandoc" Text
    "filtered document"
      #? ( "Filter the given doc by passing it through a Lua filter." <>
           "\n\nThe filter will be run in the current Lua process." <>
           "\n"
         )
      where
        copynext :: LuaError e => StackIndex -> LuaE e StackIndex
        copynext :: forall e. LuaError e => StackIndex -> LuaE e StackIndex
    copynext StackIndex
    to =
          StackIndex -> LuaE e Bool
    forall e. LuaError e => StackIndex -> LuaE e Bool
    Lua.next (CInt -> StackIndex
    nth CInt
    2) LuaE e Bool -> (Bool -> LuaE e StackIndex) -> LuaE e StackIndex
    forall a b. LuaE e a -> (a -> LuaE e b) -> LuaE e b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= \case
            Bool
    False -> StackIndex -> LuaE e StackIndex
    forall a. a -> LuaE e a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure StackIndex
    to
            Bool
    True -> do
              StackIndex -> LuaE e ()
    forall e. StackIndex -> LuaE e ()
    pushvalue (CInt -> StackIndex
    nth CInt
    2)
              StackIndex -> LuaE e ()
    forall e. StackIndex -> LuaE e ()
    insert (CInt -> StackIndex
    nth CInt
    2)
              StackIndex -> LuaE e ()
    forall e. LuaError e => StackIndex -> LuaE e ()
    rawset StackIndex
    to
              StackIndex -> LuaE e StackIndex
    forall e. LuaError e => StackIndex -> LuaE e StackIndex
    copynext StackIndex
    to
        copyOfGlobalTable :: LuaError e => LuaE e StackIndex
        copyOfGlobalTable :: forall e. LuaError e => LuaE e StackIndex
    copyOfGlobalTable = do
          LuaE e ()
    forall e. LuaE e ()
    newtable
          LuaE e ()
    forall e. LuaE e ()
    pushglobaltable
          LuaE e ()
    forall e. LuaE e ()
    pushnil
          (StackIndex -> LuaE e StackIndex
    forall e. LuaError e => StackIndex -> LuaE e StackIndex
    copynext (StackIndex -> LuaE e StackIndex)
    -> LuaE e StackIndex -> LuaE e StackIndex
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
    =<< StackIndex -> LuaE e StackIndex
    forall e. StackIndex -> LuaE e StackIndex
    absindex (CInt -> StackIndex
    nth CInt
    3)) LuaE e StackIndex -> LuaE e () -> LuaE e StackIndex
    forall a b. LuaE e a -> LuaE e b -> LuaE e a
    forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
    <* Int -> LuaE e ()
    forall e. Int -> LuaE e ()
    pop Int
    1 -- pop source table

    -- | Process the document with a JSON filter.
    run_json_filter :: DocumentedFunction PandocError
    run_json_filter :: DocumentedFunction PandocError
    run_json_filter = Name
    -> (Pandoc -> String -> Maybe [String] -> LuaE PandocError Pandoc)
    -> HsFnPrecursor
         PandocError
         (Pandoc -> String -> Maybe [String] -> LuaE PandocError Pandoc)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "run_json_filter"
      ### (\doc filterPath margs -> do
              args <- case margs of
                        Just xs -> return xs
                        Nothing -> do
                          Lua.getglobal "FORMAT"
                          (forcePeek ((:[]) <$!> peekString top) <* pop 1)
              applyJSONFilter def args filterPath doc
          )
      HsFnPrecursor
      PandocError
      (Pandoc -> String -> Maybe [String] -> LuaE PandocError Pandoc)
    -> Parameter PandocError Pandoc
    -> HsFnPrecursor
         PandocError (String -> Maybe [String] -> LuaE PandocError Pandoc)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError Pandoc
    -> TypeSpec -> Text -> Text -> Parameter PandocError Pandoc
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError Pandoc
    forall e. LuaError e => Peeker e Pandoc
    peekPandoc TypeSpec
    "Pandoc" Text
    "doc" Text
    "the Pandoc document to filter"
      HsFnPrecursor
      PandocError (String -> Maybe [String] -> LuaE PandocError Pandoc)
    -> Parameter PandocError String
    -> HsFnPrecursor
         PandocError (Maybe [String] -> LuaE PandocError Pandoc)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError String
    -> TypeSpec -> Text -> Text -> Parameter PandocError String
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError String
    forall e. Peeker e String
    peekString TypeSpec
    "string" Text
    "filter" Text
    "filter to run"
      HsFnPrecursor
      PandocError (Maybe [String] -> LuaE PandocError Pandoc)
    -> Parameter PandocError (Maybe [String])
    -> HsFnPrecursor PandocError (LuaE PandocError Pandoc)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Parameter PandocError [String]
    -> Parameter PandocError (Maybe [String])
    forall e a. Parameter e a -> Parameter e (Maybe a)
    opt (Peeker PandocError [String]
    -> TypeSpec -> Text -> Text -> Parameter PandocError [String]
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter (Peeker PandocError String -> Peeker PandocError [String]
    forall a e. LuaError e => Peeker e a -> Peeker e [a]
    peekList Peeker PandocError String
    forall e. Peeker e String
    peekString) TypeSpec
    "{string,...}" Text
    "args"
               Text
    "list of arguments passed to the filter. Defaults to `{FORMAT}`.")
      HsFnPrecursor PandocError (LuaE PandocError Pandoc)
    -> FunctionResults PandocError Pandoc
    -> DocumentedFunction PandocError
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher PandocError Pandoc
    -> TypeSpec -> Text -> FunctionResults PandocError Pandoc
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher PandocError Pandoc
    forall e. LuaError e => Pusher e Pandoc
    pushPandoc TypeSpec
    "Pandoc" Text
    "filtered document"
      #? "Filter the given doc by passing it through a JSON filter."

    -- | Documented Lua function to compute the hash of a string.
    sha1 :: DocumentedFunction e
    sha1 :: forall e. DocumentedFunction e
    sha1 = Name
    -> (ByteString -> LuaE e String)
    -> HsFnPrecursor e (ByteString -> LuaE e String)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "sha1"
      ### liftPure (show . hashWith SHA1)
      HsFnPrecursor e (ByteString -> LuaE e String)
    -> Parameter e ByteString -> HsFnPrecursor e (LuaE e String)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e ByteString
    -> TypeSpec -> Text -> Text -> Parameter e ByteString
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e ByteString
    forall e. Peeker e ByteString
    peekByteString TypeSpec
    "string" Text
    "input" Text
    ""
      HsFnPrecursor e (LuaE e String)
    -> FunctionResults e String -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e String -> TypeSpec -> Text -> FunctionResults e String
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e String
    forall e. String -> LuaE e ()
    pushString TypeSpec
    "string" Text
    "hexadecimal hash value"
      #? "Computes the SHA1 hash of the given string input."

    -- | Convert pandoc structure to a string with formatting removed.
    -- Footnotes are skipped (since we don't want their contents in link
    -- labels).
    stringify :: LuaError e => DocumentedFunction e
    stringify :: forall e. LuaError e => DocumentedFunction e
    stringify = Name
    -> (StackIndex -> LuaE e Text)
    -> HsFnPrecursor e (StackIndex -> LuaE e Text)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "stringify"
      ### (\idx ->
             forcePeek . retrieving "stringifyable element" $
             choice
             [ (fmap Shared.stringify . peekPandoc)
             , (fmap Shared.stringify . peekInline)
             , (fmap Shared.stringify . peekBlock)
             , (fmap Shared.stringify . peekCaption)
             , (fmap Shared.stringify . peekCell)
             , (fmap Shared.stringify . peekCitation)
             , (fmap Shared.stringify . peekTableHead)
             , (fmap Shared.stringify . peekTableFoot)
             , (fmap stringifyMetaValue . peekMetaValue)
             , (fmap (const "") . peekAttr)
             , (fmap (const "") . peekListAttributes)
             ] idx)
      HsFnPrecursor e (StackIndex -> LuaE e Text)
    -> Parameter e StackIndex -> HsFnPrecursor e (LuaE e Text)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e StackIndex
    -> TypeSpec -> Text -> Text -> Parameter e StackIndex
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e StackIndex
    forall a. a -> Peek e a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure TypeSpec
    "Pandoc|Block|Inline|Caption|Cell|MetaValue"
            Text
    "element" Text
    "some pandoc AST element"
      HsFnPrecursor e (LuaE e Text)
    -> FunctionResults e Text -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e Text -> TypeSpec -> Text -> FunctionResults e Text
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e Text
    forall e. Pusher e Text
    pushText TypeSpec
    "string"
            Text
    "A plain string representation of the given element."
      #? T.unlines
      [ "Converts the given element (Pandoc, Meta, Block, or Inline) into"
      , "a string with all formatting removed."
      ]
     where
      stringifyMetaValue :: MetaValue -> T.Text
      stringifyMetaValue :: MetaValue -> Text
    stringifyMetaValue MetaValue
    mv = case MetaValue
    mv of
        MetaBool Bool
    b   -> Text -> Text
    T.toLower (Text -> Text) -> Text -> Text
    forall a b. (a -> b) -> a -> b
    $ String -> Text
    T.pack (Bool -> String
    forall a. Show a => a -> String
    show Bool
    b)
        MetaString Text
    s -> Text
    s
        MetaList [MetaValue]
    xs  -> [Text] -> Text
    forall a. Monoid a => [a] -> a
    mconcat ([Text] -> Text) -> [Text] -> Text
    forall a b. (a -> b) -> a -> b
    $ (MetaValue -> Text) -> [MetaValue] -> [Text]
    forall a b. (a -> b) -> [a] -> [b]
    map MetaValue -> Text
    stringifyMetaValue [MetaValue]
    xs
        MetaMap Map Text MetaValue
    m    -> [Text] -> Text
    forall a. Monoid a => [a] -> a
    mconcat ([Text] -> Text) -> [Text] -> Text
    forall a b. (a -> b) -> a -> b
    $ ((Text, MetaValue) -> Text) -> [(Text, MetaValue)] -> [Text]
    forall a b. (a -> b) -> [a] -> [b]
    map (MetaValue -> Text
    stringifyMetaValue (MetaValue -> Text)
    -> ((Text, MetaValue) -> MetaValue) -> (Text, MetaValue) -> Text
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (Text, MetaValue) -> MetaValue
    forall a b. (a, b) -> b
    snd) (Map Text MetaValue -> [(Text, MetaValue)]
    forall k a. Map k a -> [(k, a)]
    Map.toList Map Text MetaValue
    m)
        MetaValue
    _            -> MetaValue -> Text
    forall a. Walkable Inline a => a -> Text
    Shared.stringify MetaValue
    mv

    to_roman_numeral :: LuaError e => DocumentedFunction e
    to_roman_numeral :: forall e. LuaError e => DocumentedFunction e
    to_roman_numeral = Name
    -> (Int -> LuaE e Text) -> HsFnPrecursor e (Int -> LuaE e Text)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "to_roman_numeral"
      ### liftPure Shared.toRomanNumeral
      HsFnPrecursor e (Int -> LuaE e Text)
    -> Parameter e Int -> HsFnPrecursor e (LuaE e Text)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e Int -> TypeSpec -> Text -> Text -> Parameter e Int
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter (forall a e. (Integral a, Read a) => Peeker e a
    peekIntegral @Int) TypeSpec
    "integer" Text
    "n"
            Text
    "positive integer below 4000"
      HsFnPrecursor e (LuaE e Text)
    -> FunctionResults e Text -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e Text -> TypeSpec -> Text -> FunctionResults e Text
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e Text
    forall e. Pusher e Text
    pushText TypeSpec
    "string" Text
    "A roman numeral."
      #? T.unlines
      [ "Converts an integer < 4000 to uppercase roman numeral."
      , ""
      , "Usage:"
      , ""
      , "    local to_roman_numeral = pandoc.utils.to_roman_numeral"
      , "    local pandoc_birth_year = to_roman_numeral(2006)"
      , "    -- pandoc_birth_year == 'MMVI'"
      ]

    -- | Converts a table into an old/simple table.
    to_simple_table :: DocumentedFunction PandocError
    to_simple_table :: DocumentedFunction PandocError
    to_simple_table = Name
    -> (Block -> LuaE PandocError SimpleTable)
    -> HsFnPrecursor
         PandocError (Block -> LuaE PandocError SimpleTable)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "to_simple_table"
      ### (\case
              Table _attr caption specs thead tbodies tfoot -> do
                let (capt, aligns, widths, headers, rows) =
                      Shared.toLegacyTable caption specs thead tbodies tfoot
                return $ SimpleTable capt aligns widths headers rows
              blk -> Lua.failLua $ mconcat
                     [ "Expected Table, got ", showConstr (toConstr blk), "." ])
      HsFnPrecursor PandocError (Block -> LuaE PandocError SimpleTable)
    -> Parameter PandocError Block
    -> HsFnPrecursor PandocError (LuaE PandocError SimpleTable)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker PandocError Block
    -> TypeSpec -> Text -> Text -> Parameter PandocError Block
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker PandocError Block
    forall e. LuaError e => Peeker e Block
    peekTable TypeSpec
    "Block" Text
    "tbl" Text
    "a table"
      HsFnPrecursor PandocError (LuaE PandocError SimpleTable)
    -> FunctionResults PandocError SimpleTable
    -> DocumentedFunction PandocError
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher PandocError SimpleTable
    -> TypeSpec -> Text -> FunctionResults PandocError SimpleTable
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher PandocError SimpleTable
    forall e. LuaError e => SimpleTable -> LuaE e ()
    pushSimpleTable TypeSpec
    "SimpleTable" Text
    "SimpleTable object"
      #? T.unlines
      [ "Converts a table into an old/simple table."
      , ""
      , "Usage:"
      , ""
      , "    local simple = pandoc.utils.to_simple_table(table)"
      , "    -- modify, using pre pandoc 2.10 methods"
      , "    simple.caption = pandoc.SmallCaps(simple.caption)"
      , "    -- create normal table block again"
      , "    table = pandoc.utils.from_simple_table(simple)"
      ]
     where
      peekTable :: LuaError e => Peeker e Block
      peekTable :: forall e. LuaError e => Peeker e Block
    peekTable StackIndex
    idx = Peeker e Block
    forall e. LuaError e => Peeker e Block
    peekBlock StackIndex
    idx Peek e Block -> (Block -> Peek e Block) -> Peek e Block
    forall a b. Peek e a -> (a -> Peek e b) -> Peek e b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= \case
        t :: Block
    t@(Table {}) -> Block -> Peek e Block
    forall a. a -> Peek e a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Block
    t
        Block
    b -> ByteString -> Peek e Block
    forall a e. ByteString -> Peek e a
    Lua.failPeek (ByteString -> Peek e Block) -> ByteString -> Peek e Block
    forall a b. (a -> b) -> a -> b
    $ [ByteString] -> ByteString
    forall a. Monoid a => [a] -> a
    mconcat
             [ ByteString
    "Expected Table, got "
             , String -> ByteString
    UTF8.fromString (String -> ByteString) -> String -> ByteString
    forall a b. (a -> b) -> a -> b
    $ Constr -> String
    showConstr (Block -> Constr
    forall a. Data a => a -> Constr
    toConstr Block
    b)
             , ByteString
    "." ]

    type' :: DocumentedFunction e
    type' :: forall e. DocumentedFunction e
    type' = Name
    -> (StackIndex -> LuaE e ByteString)
    -> HsFnPrecursor e (StackIndex -> LuaE e ByteString)
    forall a e. Name -> a -> HsFnPrecursor e a
    defun Name
    "type"
      ### (\idx -> getmetafield idx "__name" >>= \case
              TypeString -> fromMaybe mempty <$> tostring top
              _ -> ltype idx >>= typename)
      HsFnPrecursor e (StackIndex -> LuaE e ByteString)
    -> Parameter e StackIndex -> HsFnPrecursor e (LuaE e ByteString)
    forall e a b.
    HsFnPrecursor e (a -> b) -> Parameter e a -> HsFnPrecursor e b
    <#> Peeker e StackIndex
    -> TypeSpec -> Text -> Text -> Parameter e StackIndex
    forall e a. Peeker e a -> TypeSpec -> Text -> Text -> Parameter e a
    parameter Peeker e StackIndex
    forall a. a -> Peek e a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure TypeSpec
    "any" Text
    "value" Text
    "any Lua value"
      HsFnPrecursor e (LuaE e ByteString)
    -> FunctionResults e ByteString -> DocumentedFunction e
    forall e a.
    HsFnPrecursor e (LuaE e a)
    -> FunctionResults e a -> DocumentedFunction e
    =#> Pusher e ByteString
    -> TypeSpec -> Text -> FunctionResults e ByteString
    forall e a. Pusher e a -> TypeSpec -> Text -> FunctionResults e a
    functionResult Pusher e ByteString
    forall e. Pusher e ByteString
    pushByteString TypeSpec
    "string" Text
    "type of the given value"
      #? T.unlines
      [ "Pandoc-friendly version of Lua's default `type` function, returning"
      , "type information similar to what is presented in the manual."
      , ""
      , "The function works by checking the metafield `__name`. If the"
      , "argument has a string-valued metafield `__name`, then it returns"
      , "that string. Otherwise it behaves just like the normal `type`"
      , "function."
      , ""
      , "Usage:"
      , ""
      , "    -- Prints one of 'string', 'boolean', 'Inlines', 'Blocks',"
      , "    -- 'table', and 'nil', corresponding to the Haskell constructors"
      , "    -- MetaString, MetaBool, MetaInlines, MetaBlocks, MetaMap,"
      , "    -- and an unset value, respectively."
      , ""
      , "    function Meta (meta)"
      , "      print('type of metavalue `author`:', pandoc.utils.type(meta.author))"
      , "    end"
      ]