0 | module Text.TOML.Internal.TStack
2 | import Data.Time.Time
3 | import Data.SortedMap
4 | import Derive.Prelude
6 | import Text.TOML.Lexer
7 | import Text.TOML.Types
11 | %language ElabReflection
18 | data Tag = New | Undef | Def | HDef
20 | %runElab derive "Tag" [Eq,Show,Ord]
23 | data Tree : Type where
24 | TV : TomlValue -> Tree
25 | TT : Tag -> SortedMap String Tree -> Tree
26 | TA : SnocList (SortedMap String Tree) -> SortedMap String Tree -> Tree
30 | TreeTable = SortedMap String Tree
32 | toVal : Tree -> TomlValue
34 | toArr : List TomlValue -> SnocList TreeTable -> TomlValue
37 | toTbl : TreeTable -> TomlTable
38 | toTbl t = assert_total $
map toVal t
41 | toVal (TT x t) = TTbl (toTbl t)
42 | toVal (TA sx x) = toArr [TTbl $
toTbl x] sx
44 | toArr vs [<] = TArr vs
45 | toArr vs (st:<t) = toArr (TTbl (toTbl t) :: vs) st
48 | data TView : Type -> Type where
50 | VT : TView t -> SortedMap String t -> Key -> Tag -> TView t
51 | VA : TView Tree -> TreeTable -> Key -> SnocList TreeTable -> TView Tree
54 | tagAsHDef : TView t -> TView t
55 | tagAsHDef (VT v t k _) = VT v t k HDef
58 | keys : List Key -> TView t -> List Key
60 | keys ks (VT v _ k _) = keys (k::ks) v
61 | keys ks (VA v _ k _) = keys (k::ks) v
63 | existsErr : (List Key -> TomlParseError) -> List Key -> TView t -> TErr
64 | existsErr f add view =
65 | let ks := keys add view
66 | in B (Custom $
f ks) (foldMap bounds ks)
69 | exists : TomlValue -> List Key -> TView t -> TErr
70 | exists (TArr _) = existsErr StaticArray
71 | exists (TTbl _) = existsErr InlineTableExists
72 | exists _ = existsErr ValueExists
75 | vexists : TView t -> TErr
76 | vexists (VA v _ k _) = existsErr TableArray [k] v
77 | vexists v = existsErr TableExists [] v
79 | new : TView t -> List Key -> TView t
81 | new v (k :: ks) = new (VT v empty k New) ks
84 | view : TView Tree -> TreeTable -> List Key -> Either TErr (TView Tree,TreeTable)
85 | view v t [] = Right (v,t)
87 | case lookup k.key t of
88 | Nothing => Right (new (VT v t k New) ks, empty)
89 | Just (TT tt t2) => view (VT v t k tt) t2 ks
90 | Just (TA st t2) => view (VA v t k st) t2 ks
91 | Just (TV val) => Left $
exists val [k] v
94 | tview : TreeTable -> List Key -> Either TErr (TView Tree,TreeTable)
96 | view VR t ks >>= \case
97 | (v@(VT _ _ _ x), t) => if x < Def then Right (v,t) else Left (vexists v)
98 | (v,t) => Left (vexists v)
101 | reduceT : Tag -> TreeTable -> TView Tree -> TreeTable
103 | reduceT x t (VT v t2 k y) = reduceT x (insert k.key (TT (max x y) t) t2) v
104 | reduceT x t (VA v t2 k st) = reduceT x (insert k.key (TA st t) t2) v
106 | noHDef : TView a -> Either TErr ()
107 | noHDef VR = Right ()
108 | noHDef v@(VT w _ _ x) = if x < HDef then noHDef w else Left (vexists v)
109 | noHDef v@(VA {}) = Left (vexists v)
112 | addVal : TreeTable -> SnocList Key -> TomlValue -> Either TErr TreeTable
113 | addVal t sk tv = do
114 | (VT v t k New,_) <- view VR t (sk <>> []) | (v,_) => Left (vexists v)
116 | Right $
reduceT Def (insert k.key (TV tv) t) v