Something like this:
if sys.version_info >= (3, 10):
_UNION_TYPES = {typing.Union, types.UnionType}
else:
_UNION_TYPES = {typing.Union}
def is_union(x):
return typing.get_origin(x) in _UNION_TYPES
Generally, get_origin() and get_args() are very useful for introspection. It should not be necessary to use private objects in the typing module, like _UnionGenericAlias and _SpecialForm.