From 6663c20f3cd07a4ce8ff76453baa03e5b9ef6f6e Mon Sep 17 00:00:00 2001 From: Marcos Magueta Date: Wed, 23 Sep 2026 02:53:18 -0300 Subject: stop treating tuple as a partial bind and consider type --- lib/kernel/EphemeralRelation.ml | 31 ++++++++++++++++++++++--------- 1 file changed, 22 insertions(+), 9 deletions(-) (limited to 'lib/kernel/EphemeralRelation.ml') diff --git a/lib/kernel/EphemeralRelation.ml b/lib/kernel/EphemeralRelation.ml index 3fb8e72..8e2d2e4 100644 --- a/lib/kernel/EphemeralRelation.ml +++ b/lib/kernel/EphemeralRelation.ml @@ -98,19 +98,32 @@ module Make (D : DERIVATION) = struct (* Membership of a derived relation is decided by the derivation and not by a lookup, so it is asked of the generator under the - binding the tuple itself fixes. *) + binding the tuple itself fixes. Only a tuple carrying exactly the + described attributes can be a member, and it must match one whole. *) method contains (tuple : Concepts.Tuple.t) = let open Utilities.Result in let binding = tuple.Concepts.Tuple.attributes in let bound = Protocols.Generative.bound binding in - let* () = if decides declaration bound then Ok () else Error (Error.undecidable bound) in - let* cursor = D.generate plan binding in - Fun.protect - ~finally:(fun () -> Protocols.Handle.release cursor) - (fun () -> - let* scan = Protocols.Cursor.require cursor in - let* first = Protocols.Cursor.next scan in - Ok (Option.is_some first) ) + let* description = D.describe plan in + let described = BatMap.String.keys description |> BatSet.String.of_enum in + if not (BatSet.String.equal described bound) then Ok false + else + let* () = if decides declaration bound then Ok () else Error (Error.undecidable bound) in + let* cursor = D.generate plan binding in + let expected = Concepts.Tuple.hash tuple in + Fun.protect + ~finally:(fun () -> Protocols.Handle.release cursor) + (fun () -> + let* scan = Protocols.Cursor.require cursor in + let rec seek () = + let* found = Protocols.Cursor.next scan in + match found with + | None -> Ok false + | Some member -> + if Concepts.Hash.hash_equals (Concepts.Tuple.hash member) expected then Ok true + else seek () + in + seek () ) method protocols : Protocols.Handle.protocol list = let carried = -- cgit v1.2.3