module Symparsec.Parser.End where

import Symparsec.Parser.Common
import DeFun.Core ( Con1, con1 )
import Singleraeh.Tuple ( SUnit(..) )
import Singleraeh.Either ( SEither(..) )
import GHC.TypeLits ( symbolSing )
import TypeLevelShow.Doc ( singDoc )

-- | Assert end of symbol, or fail.
type End :: PParser () ()
type End = 'PParser
    (FailChSym "End" (Text "expected end of string"))
    (Con1 Right)
    '()

sEnd :: SParser SUnit SUnit End
sEnd :: SParser SUnit SUnit End
sEnd = SParserChSym
  SUnit SUnit (FailChSym "End" ('Text "expected end of string"))
-> SParserEndSym SUnit SUnit (Con1 'Right)
-> SUnit '()
-> SParser SUnit SUnit End
forall {s} {r} (ss :: s -> Type) (sr :: r -> Type)
       (pCh :: ParserChSym s r) (pEnd :: ParserEndSym s r) (s0 :: s).
SParserChSym ss sr pCh
-> SParserEndSym ss sr pEnd
-> ss s0
-> SParser ss sr ('PParser pCh pEnd s0)
SParser (SSymbol "End"
-> SDoc ('Text "expected end of string")
-> SParserChSym
     SUnit SUnit (FailChSym "End" ('Text "expected end of string"))
forall {s} {r} (name :: Symbol) (e :: PDoc) (ss :: s -> Type)
       (sr :: r -> Type).
SSymbol name -> SDoc e -> SParserChSym ss sr (FailChSym name e)
failChSym SSymbol "End"
forall (n :: Symbol). KnownSymbol n => SSymbol n
symbolSing SDoc ('Text "expected end of string")
forall (doc :: PDoc). SingDoc doc => SDoc doc
singDoc) (LamRep SUnit (SResultEnd SUnit) (Con1 'Right)
-> SParserEndSym SUnit SUnit (Con1 'Right)
forall {a1} {b1} (a2 :: a1 -> Type) (b2 :: b1 -> Type)
       (con :: a1 -> b1).
LamRep a2 b2 (Con1 con) -> Lam a2 b2 (Con1 con)
con1 SUnit x -> SEither SE SUnit ('Right x)
SUnit x -> SEither SE SUnit (App (Con1 'Right) x)
forall {r} {l} (sr :: r -> Type) (r1 :: r) (sl :: l -> Type).
sr r1 -> SEither sl sr ('Right r1)
LamRep SUnit (SResultEnd SUnit) (Con1 'Right)
SRight) SUnit '()
SUnit

-- TODO orphan instance. if I need to, make some dumb type family idk.
instance SingParser End where
    type PS  End = SUnit
    type PR  End = SUnit
    singParser' :: SParser (PS End) (PR End) End
singParser' = SParser SUnit SUnit End
SParser (PS End) (PR End) End
sEnd