sealed interface Foo<T> permits Impl {} // union type record Impl() implements Foo<String> {} // product type <T> T m(Foo<T> foo) { return switch(foo) { case Impl impl -> "hello"; // flow typing T=String }; }