Skip to content

Commit

Permalink
fix(api): ensure that nulls can be cast to any type to allow caller p…
Browse files Browse the repository at this point in the history
…romotion
  • Loading branch information
cpcloud committed Jul 5, 2022
1 parent b8f4120 commit fab4393
Showing 1 changed file with 16 additions and 4 deletions.
20 changes: 16 additions & 4 deletions ibis/expr/datatypes/core.py
Original file line number Diff line number Diff line change
Expand Up @@ -1234,13 +1234,15 @@ def _get_timedelta_units(


def higher_precedence(left: DataType, right: DataType) -> DataType:
nullable = left.nullable or right.nullable

if castable(left, right, upcast=True):
return right
return right(nullable=nullable)
elif castable(right, left, upcast=True):
return left
return left(nullable=nullable)

raise IbisTypeError(
f'Cannot compute precedence for {left} and {right} types'
f'Cannot compute precedence for `{left}` and `{right}` types'
)


Expand Down Expand Up @@ -1421,7 +1423,17 @@ def can_cast_any(source: DataType, target: DataType, **kwargs) -> bool:

@castable.register(Null, DataType)
def can_cast_null(source: DataType, target: DataType, **kwargs) -> bool:
return target.nullable
# The null type is castable to any type, even if the target type is *not*
# nullable.
#
# We handle the promotion of `null + !T -> T` at the `castable` call site.
#
# It might be possible to build a system with a single function that tries
# to promote types and use the exception to indicate castability, but that
# is a deeper refactor to be tackled later.
#
# See https://github.com/ibis-project/ibis/issues/2891 for the bug report
return True


Integral = TypeVar('Integral', SignedInteger, UnsignedInteger)
Expand Down

0 comments on commit fab4393

Please sign in to comment.