This one is maybe the best. Except I’d make the supertype a Union instead of an abstract type (that way both you and the compiler’s subtyping know there will not be more subtypes added later):
struct Bar end
struct Baz end
const BarOrBaz = Union{Bar, Baz}
struct Foo{B <: BarOrBaz} end
However keep in mind this design still allows invalid types such as Foo{BarOrBaz} or Foo{Union{}}.
One thing you could perhaps do is restrict the type parameter to be a subtype of a concrete type, so the only valid types would be Foo{Union{}} and Foo{Concrete}:
struct Concrete end
struct Foo{P <: Concrete} end