packages feed

mdoc-0.1.0.0: src/Mdoc/Parse/MacroArg.hs

-- |
--
-- Module      : Mdoc.Parse.MacroArg
-- Copyright   : (c) 2026 Patrick Brisbin
-- License     : AGPL-3
-- Maintainer  : pbrisbin@gmail.com
-- Stability   : experimental
-- Portability : POSIX
module Mdoc.Parse.MacroArg
  ( parseMacroArg
  ) where

import Mdoc.Prelude

import Data.Time (fromGregorian)
import Mdoc.MacroArg
import Mdoc.Parse
import Mdoc.Parse.Interpolation
import Mdoc.Parse.MacroName

parseMacroArg :: Parser MacroArg
parseMacroArg =
  choice
    [ mdocDate
    , interpolated
    , try quotedComma <|> quoted
    , try callable <|> bare
    ]
    <?> "macro argument"

mdocDate :: Parser MacroArg
mdocDate = do
  void $ string "$Mdocdate"
  arg <- optional $ do
    m <- char ':' *> hspace *> month
    d <- hspace1 *> digits
    y <- hspace1 *> digits
    pure $ fromGregorian (fromIntegral y) m d
  void $ hspace *> char '$'
  pure $ Mdocdate arg
 where
  month :: Parser Int
  month =
    choice
      [ 1 <$ string "January"
      , 2 <$ string "February"
      , 3 <$ string "March"
      , 4 <$ string "April"
      , 5 <$ string "May"
      , 6 <$ string "June"
      , 7 <$ string "July"
      , 8 <$ string "August"
      , 9 <$ string "September"
      , 10 <$ string "October"
      , 11 <$ string "November"
      , 12 <$ string "December"
      ]
      <?> "month name (e.g. January)"

interpolated :: Parser MacroArg
interpolated = InterpolatedArg <$> parseInterpolationArg

callable :: Parser MacroArg
callable = Callable <$> parseMacroName <* peek space1 <?> "callable macro"

quotedComma :: Parser MacroArg
quotedComma = QuotedComma <$> quotedBy '"' <* char ','

quoted :: Parser MacroArg
quoted = Quoted <$> quotedBy '"'

bare :: Parser MacroArg
bare = Bare <$> restOfWord <?> "bare word"