@@ -3,6 +3,7 @@
33module OpenAPI.Checker.Subtree
44 ( Steppable (..)
55 , Step (..)
6+ , TraceRoot
67 , Trace
78 , Traced
89 , Traced'
@@ -69,7 +70,15 @@ class
6970 -- | How to get from an @a@ node to a @b@ node
7071 data Step a b :: Type
7172
72−type Trace = Paths Step OpenApi
73+data TraceRoot
74+
75+instance Steppable TraceRoot OpenApi where
76+ data Step TraceRoot OpenApi
77+ = ClientSchema
78+ | ServerSchema
79+ deriving stock (Eq, Ord, Show)
80+
81+type Trace = Paths Step TraceRoot
7382
7483type Traced' a b = Env (Trace a) b
7584
@@ -117,16 +126,15 @@ type CompatFormula' q f r = Compose CompatM (FormulaF q f r)
117126
118127type SemanticCompatFormula = CompatFormula' Behave AnIssue 'APILevel
119128
120−type StructuralCompatFormula = CompatFormula' UnitQuiver Proxy ()
129+type StructuralCompatFormula = CompatFormula' VoidQuiver Proxy ()
121130
122−data UnitQuiver a b where
123− UnitQuiver :: UnitQuiver () ()
131+data VoidQuiver a b where
124132
125−deriving stock instance Eq (UnitQuiver a b)
133+deriving stock instance Eq (VoidQuiver a b)
126134
127−deriving stock instance Ord (UnitQuiver a b)
135+deriving stock instance Ord (VoidQuiver a b)
128136
129−deriving stock instance Show (UnitQuiver a b)
137+deriving stock instance Show (VoidQuiver a b)
130138
131139class (Typeable t, Issuable (SubtreeLevel t)) => Subtree (t :: Type) where
132140 type CheckEnv t :: [Type]
@@ -155,7 +163,7 @@ checkCompatibility
155163 -> Behavior (SubtreeLevel t)
156164 -> ProdCons (Traced t)
157165 -> SemanticCompatFormula ()
158−checkCompatibility e bhv = memo SemanticMemoKey $ \pc ->
166+checkCompatibility e bhv = memo bhv SemanticMemoKey $ \pc ->
159167 case runCompatFormula $ checkSubstructure e pc of
160168 Left _ -> checkSemanticCompatibility e bhv pc
161169 Right () -> pure ()
@@ -165,7 +173,7 @@ checkSubstructure
165173 => HList xs
166174 -> ProdCons (Traced t)
167175 -> StructuralCompatFormula ()
168−checkSubstructure e = memo StructuralMemoKey $ checkStructuralCompatibility e
176+checkSubstructure e = memo Root StructuralMemoKey $ checkStructuralCompatibility e
169177
170178structuralMaybe
171179 :: (Subtree a, HasAll (CheckEnv a) xs)
@@ -260,7 +268,7 @@ issueAt :: Issuable l => Paths q r l -> Issue l -> CompatFormula' q AnIssue r a
260268issueAt xs issue = Compose $ pure $ anError $ AnItem xs $ AnIssue issue
261269
262270structuralIssue :: StructuralCompatFormula a
263−structuralIssue = Compose $ pure $ anError $ AnItem (step UnitQuiver) Proxy
271+structuralIssue = Compose $ pure $ anError $ AnItem Root Proxy
264272
265273anyOfAt
266274 :: Issuable l
@@ -283,11 +291,17 @@ fixpointKnot =
283291 }
284292
285293memo
286− :: (Typeable (r :: k), Typeable q, Typeable f, Typeable k, Typeable a)
287− => MemoKey
294+ :: (Typeable (l :: k), Typeable q, Typeable f, Typeable k, Typeable a)
295+ => Paths q r l
296+ -> MemoKey
288297 -> (ProdCons (Traced a) -> CompatFormula' q f r ())
289298 -> (ProdCons (Traced a) -> CompatFormula' q f r ())
290−memo k f pc = Compose $ memoWithKnot fixpointKnot (getCompose $ f pc) (k, ask <$> pc)
299+memo bhv k f pc = Compose $ do
300+ formula' <- memoWithKnot fixpointKnot (do
301+ formula <- getCompose $ f pc
302+ pure $ mapErrors (P.filter bhv) formula
303+ ) (k, ask <$> pc)
304+ pure $ mapErrors (P.embed bhv) formula'
291305
292306data MemoKey = SemanticMemoKey | StructuralMemoKey
293307 deriving stock (Eq, Ord)