Can anyone explain why this does not compile: module rec A : sig type t end = struct type z = { x : B.t } type t = z let foo t = B.foo t.x t (* Error: This expression has type t but an expression was expected of type A.t *) end and B : sig type t val foo : B.t -> A.t -> unit end = struct type t let foo _ _ = () end Note that if there's no type aliasing in A, it will succeed: module rec A : sig type t end = struct type t = { x : B.t } let foo t = B.foo t.x t end and B : sig type t val foo : B.t -> A.t -> unit end = struct type t let foo _ _ = () end Thanks!