From 96bec6b54c65fc6e91570d4b659a5ce270b643cc Mon Sep 17 00:00:00 2001 From: Robert Kruszewski Date: Sat, 26 Sep 2026 21:33:43 +0000 Subject: [PATCH 1/3] Replace VortexError's variants with a kind, and give every error one VortexError carried one enum variant per dependency that could fail (Arrow, FlatBuffers, ObjectStore, Jiff, Tokio, TryFromInt, Prost, Fmt) plus two structural wrappers (Context, Shared). None were constructed by name outside the `From` impls or matched on, and the only classification callers could act on, the `vx_error_code` the C API exports, reported OTHER for nearly everything: 1966 `vortex_err!` sites and all 1133 `vortex_ensure!` and `vortex_panic!` sites gave no kind at all. It was the equivalent of a codebase that only ever raises bare `Exception`. The error type VortexError is now a struct holding a `VortexErrorKind`, a message, an optional source and a backtrace, `Arc`-backed so it is cheaply `Clone`. Errors from dependencies are classified by what they mean to Vortex and kept as `Error::source`, where callers downcast. `Context` becomes a message prefix that preserves kind, source and backtrace; `Shared` goes away. `size_of::()` drops from 88 bytes to 56, and the `?` conversion path no longer formats eagerly. The kinds are the C API's existing codes with two additions and one removal: - NotFound, for a name lookup that found nothing: a missing field, an unknown encoding id, an absent segment. Python raises KeyError here. - Overflow, for a numeric value that will not fit its target, the largest group that was hiding in Other. `From` produces it, so `?` on a `try_from` classifies itself. - Compute is removed. Every other kind names what went wrong; Compute named where it happened, which the enum's own docs say a kind must not do. Its 11 sites were all Overflow, MismatchedTypes or Serde. NotFound and Overflow take C codes 10 and 11; Compute's slot 2 is retired and not reused, so no existing code moves. cbindgen regenerated cinclude/vortex.h and the hand-written C++ mirror in lang/cpp matches. The macros `vortex_err!`, `vortex_bail!`, `vortex_ensure!`, `vortex_ensure_eq!` and `vortex_panic!` now require a leading `Kind:` before any message; the untagged arm is replaced by a compile error naming the fix, with compile_fail doctests keeping it that way. The three canned arms (`MismatchedTypes: expected, actual` and the like) are gone: a literal is an expr, so `vortex_bail!(MismatchedTypes: "Expected {:?}", x)` matched the canned arm and rendered its braces verbatim. The 32 sites that used them spell their message out. The macros no longer inject `use std::backtrace::Backtrace;` into caller scope. `vortex_ensure_eq!(a, b)` with no message still reports AssertionFailed, showing both expressions and values. A check on the caller's input names its kind alone, `vortex_ensure_eq!(a, b, InvalidArgument)`, and keeps that output. The sites Every construction site now names its kind, each chosen by reading the site. The rules that settle the ambiguous ones: a check on what the caller passed in is InvalidArgument or MismatchedTypes, and a length mismatch is never a type error; a check that a kernel, rewrite or executor kept its own contract is AssertionFailed; a check made while decoding metadata or a wire format is Serde; a child index nobody can satisfy is OutOfBounds however it is phrased. Io covers operating-system and device-driver calls, so the CUDA, nvcomp and CUB status failures are Io, as Python's OSError would be. The sites left Other carry it explicitly, so each reads as a decision. `From` sent every Arrow failure to Other; each variant now maps to its kind (ArithmeticOverflow to Overflow, SchemaError to MismatchedTypes, the file-format variants to Serde, and so on). `From` maps a date that does not exist or a misused unit to InvalidArgument. pco's Corruption and InsufficientData map to Serde. 44 sites wrapped an inner VortexError in a fresh `vortex_err!`, which replaced its kind with a guess and nested its whole Display, backtrace included, in the new message. A text scan cannot tell those from the same shape around an io::Error, so a throwaway build probed every `map_err` closure with a marker type whose must_use warning fires only for a VortexError. The 29 that wrapped edition-registration calls lose the `map_err`; the rest use `with_context`, or the `vortex_panic!(err, "...")` form, which keep the kind. STYLE.md now says to do that. Python The Python bindings turned every VortexError into RuntimeError, so none of this reached Python. Each kind now raises its analogue: OutOfBounds IndexError NotFound KeyError Overflow OverflowError InvalidArgument ValueError Serde ValueError MismatchedTypes TypeError NotImplemented NotImplementedError AssertionFailed AssertionError Io OSError Other RuntimeError Signed-off-by: Robert Kruszewski Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01S7EtMqoZ91rrCCh9vS2yTm --- STYLE.md | 16 +- encodings/alp/src/alp/array.rs | 28 +- encodings/alp/src/alp/compress.rs | 4 +- encodings/alp/src/alp/compute/compare.rs | 4 +- encodings/alp/src/alp/ops.rs | 2 +- encodings/alp/src/alp/plugin.rs | 24 +- encodings/alp/src/alp_rd/array.rs | 35 +- encodings/alp/src/alp_rd/mod.rs | 2 +- encodings/bytebool/src/array.rs | 18 +- encodings/bytebool/src/compute.rs | 10 +- encodings/datetime-parts/src/array.rs | 22 +- encodings/datetime-parts/src/canonical.rs | 4 +- encodings/datetime-parts/src/compress.rs | 2 +- encodings/datetime-parts/src/compute/take.rs | 8 +- encodings/datetime-parts/src/ops.rs | 6 +- encodings/datetime-parts/src/timestamp.rs | 4 +- .../decimal-byte-parts/benches/common/mod.rs | 2 +- .../benches/dbp_assemble.rs | 6 +- .../decimal-byte-parts/benches/dbp_split.rs | 2 +- .../src/decimal_byte_parts/array.rs | 28 +- .../src/decimal_byte_parts/assemble.rs | 12 +- .../src/decimal_byte_parts/plugin/mod.rs | 4 +- .../src/decimal_byte_parts/plugin/v1.rs | 12 +- .../src/decimal_byte_parts/plugin/v2.rs | 15 +- encodings/fastlanes/benches/for_decode.rs | 2 +- .../array/bitpack_compress/blocked.rs | 34 +- .../array/bitpack_compress/global.rs | 22 +- .../array/bitpack_decompress/blocked.rs | 6 +- .../array/bitpack_decompress/global.rs | 2 +- .../fastlanes/src/bitpacking/array/mod.rs | 38 +- .../fastlanes/src/bitpacking/array/tests.rs | 2 +- .../src/bitpacking/array/unpack_iter.rs | 6 +- .../fastlanes/src/bitpacking/compute/take.rs | 10 +- .../fastlanes/src/bitpacking/plugin/mod.rs | 12 +- .../fastlanes/src/bitpacking/plugin/tests.rs | 38 +- .../fastlanes/src/bitpacking/plugin/v1.rs | 8 +- .../fastlanes/src/bitpacking/plugin/v2.rs | 6 +- .../fastlanes/src/bitpacking/vtable/mod.rs | 10 +- encodings/fastlanes/src/delta/array/mod.rs | 2 +- encodings/fastlanes/src/delta/compute/cast.rs | 6 +- encodings/fastlanes/src/delta/tests.rs | 2 +- encodings/fastlanes/src/delta/vtable/mod.rs | 33 +- .../fastlanes/src/delta/vtable/validity.rs | 16 +- .../fastlanes/src/for_/array/for_compress.rs | 2 +- .../src/for_/array/for_decompress.rs | 2 +- encodings/fastlanes/src/for_/array/mod.rs | 8 +- encodings/fastlanes/src/for_/plugin/mod.rs | 8 +- encodings/fastlanes/src/for_/plugin/tests.rs | 4 +- encodings/fastlanes/src/for_/plugin/v1.rs | 4 +- encodings/fastlanes/src/for_/plugin/v2.rs | 6 +- encodings/fastlanes/src/for_/tests.rs | 4 +- encodings/fastlanes/src/for_/vtable/mod.rs | 28 +- .../fastlanes/src/for_/vtable/operations.rs | 6 +- encodings/fastlanes/src/rle/array/mod.rs | 2 +- .../fastlanes/src/rle/array/rle_decompress.rs | 10 +- encodings/fastlanes/src/rle/probe.rs | 14 +- encodings/fastlanes/src/rle/vtable/mod.rs | 20 +- encodings/fsst/src/array.rs | 25 +- encodings/fsst/src/canonical.rs | 18 +- encodings/fsst/src/compress.rs | 4 +- encodings/fsst/src/compute/compare.rs | 2 +- encodings/fsst/src/dfa/flat_contains.rs | 2 +- encodings/fsst/src/dfa/prefix.rs | 2 +- encodings/fsst/src/slice.rs | 2 +- encodings/onpair/src/array.rs | 31 +- encodings/onpair/src/canonical.rs | 14 +- encodings/onpair/src/compute/compare.rs | 4 +- encodings/onpair/src/decode.rs | 14 +- encodings/onpair/src/ops.rs | 10 +- encodings/onpair/src/tests.rs | 8 +- encodings/parquet-variant/src/array.rs | 26 +- encodings/parquet-variant/src/arrow.rs | 12 +- .../src/json_to_variant_tests.rs | 18 +- encodings/parquet-variant/src/kernel.rs | 57 +- encodings/parquet-variant/src/operations.rs | 15 +- encodings/parquet-variant/src/vtable.rs | 83 ++- encodings/pco/src/array.rs | 49 +- encodings/runend/src/array.rs | 18 +- encodings/runend/src/compute/take.rs | 2 +- encodings/runend/src/iter.rs | 6 +- encodings/runend/src/probe.rs | 6 +- encodings/sequence/src/array.rs | 42 +- encodings/sequence/src/compute/min_max.rs | 9 +- encodings/sequence/src/compute/take.rs | 14 +- encodings/sequence/src/model_tests.rs | 2 +- encodings/sparse/src/canonical.rs | 20 +- encodings/sparse/src/compute/sum.rs | 4 +- encodings/sparse/src/lib.rs | 24 +- encodings/uuid/src/arrow.rs | 2 +- encodings/uuid/src/metadata.rs | 2 +- encodings/uuid/src/vtable.rs | 47 +- encodings/zigzag/src/array.rs | 16 +- encodings/zigzag/src/compress.rs | 4 +- encodings/zstd/src/array.rs | 76 +-- encodings/zstd/src/lib.rs | 8 +- encodings/zstd/src/zstd_buffers.rs | 34 +- fuzz/fuzz_targets/array_ops.rs | 2 +- fuzz/fuzz_targets/compress_gpu.rs | 2 +- fuzz/fuzz_targets/compress_roundtrip.rs | 2 +- fuzz/fuzz_targets/fsst_like.rs | 2 +- fuzz/fuzz_targets/row_encode.rs | 2 +- fuzz/src/array/compare.rs | 4 +- fuzz/src/array/fill_null.rs | 2 +- fuzz/src/array/mask.rs | 2 +- fuzz/src/array/mod.rs | 16 +- fuzz/src/array/scalar_at.rs | 2 +- fuzz/src/array/search_sorted.rs | 4 +- fuzz/src/array/sum/mod.rs | 4 +- fuzz/src/array/sum/tests.rs | 4 +- fuzz/src/fsst_like.rs | 2 +- fuzz/src/gpu/mod.rs | 2 +- fuzz/src/lib.rs | 2 - lang/cpp/include/vortex/error.hpp | 3 +- lang/cpp/src/array.cpp | 2 +- vortex-array/benches/row_fn_bool_retry.rs | 2 +- vortex-array/benches/row_fn_output.rs | 4 +- vortex-array/src/aggregate_fn/accumulator.rs | 18 +- .../src/aggregate_fn/accumulator_grouped.rs | 12 +- vortex-array/src/aggregate_fn/combined.rs | 20 +- .../aggregate_fn/fns/all_non_distinct/mod.rs | 12 +- .../src/aggregate_fn/fns/bounded_max/mod.rs | 10 +- .../src/aggregate_fn/fns/bounded_min/mod.rs | 4 +- .../src/aggregate_fn/fns/count/mod.rs | 2 +- .../src/aggregate_fn/fns/first/mod.rs | 2 +- .../src/aggregate_fn/fns/is_constant/mod.rs | 6 +- .../src/aggregate_fn/fns/is_sorted/mod.rs | 2 +- vortex-array/src/aggregate_fn/fns/last/mod.rs | 2 +- vortex-array/src/aggregate_fn/fns/mean/mod.rs | 4 +- .../src/aggregate_fn/fns/min_max/mod.rs | 6 +- .../aggregate_fn/fns/min_max/varbinview.rs | 2 +- .../src/aggregate_fn/fns/nan_count/mod.rs | 5 +- .../src/aggregate_fn/fns/null_count/mod.rs | 3 +- vortex-array/src/aggregate_fn/fns/sum/bool.rs | 2 +- .../src/aggregate_fn/fns/sum/constant.rs | 27 +- .../src/aggregate_fn/fns/sum/decimal.rs | 2 +- vortex-array/src/aggregate_fn/fns/sum/mod.rs | 12 +- .../src/aggregate_fn/fns/sum/primitive.rs | 32 +- .../src/aggregate_fn/fns/sum_v2/mod.rs | 30 +- .../fns/uncompressed_size_in_bytes/bool.rs | 2 +- .../fns/uncompressed_size_in_bytes/decimal.rs | 10 +- .../fixed_size_list.rs | 2 +- .../uncompressed_size_in_bytes/list_view.rs | 10 +- .../fns/uncompressed_size_in_bytes/mod.rs | 32 +- .../uncompressed_size_in_bytes/primitive.rs | 13 +- .../fns/uncompressed_size_in_bytes/struct_.rs | 4 +- .../fns/uncompressed_size_in_bytes/union.rs | 2 +- .../uncompressed_size_in_bytes/varbinview.rs | 24 +- vortex-array/src/aggregate_fn/foreign.rs | 14 +- vortex-array/src/aggregate_fn/proto.rs | 15 +- .../src/aggregate_fn/storage_pushdown.rs | 4 +- vortex-array/src/aggregate_fn/vtable.rs | 6 +- vortex-array/src/array/erased.rs | 33 +- vortex-array/src/array/foreign.rs | 2 +- vortex-array/src/array/mod.rs | 20 +- vortex-array/src/array/plugin.rs | 4 +- vortex-array/src/array/probe/array.rs | 16 +- vortex-array/src/array/probe/repeated.rs | 14 +- vortex-array/src/array/vtable/mod.rs | 8 +- vortex-array/src/array/vtable/operations.rs | 2 +- vortex-array/src/arrays/bool/array.rs | 10 +- .../src/arrays/bool/compute/boolean.rs | 2 +- .../src/arrays/bool/compute/fill_null.rs | 2 +- vortex-array/src/arrays/bool/compute/mask.rs | 4 +- vortex-array/src/arrays/bool/compute/take.rs | 11 +- vortex-array/src/arrays/bool/test_harness.rs | 2 +- vortex-array/src/arrays/bool/vtable/mod.rs | 16 +- vortex-array/src/arrays/chunked/array.rs | 4 +- .../src/arrays/chunked/compute/take.rs | 19 +- .../src/arrays/chunked/vtable/canonical.rs | 16 +- vortex-array/src/arrays/chunked/vtable/mod.rs | 26 +- .../src/arrays/chunked/vtable/operations.rs | 2 +- .../constant/compute/uncompressed_size.rs | 4 +- .../src/arrays/constant/vtable/canonical.rs | 10 +- .../src/arrays/constant/vtable/mod.rs | 8 +- vortex-array/src/arrays/datetime/mod.rs | 6 +- vortex-array/src/arrays/decimal/array.rs | 4 +- .../src/arrays/decimal/compute/cast.rs | 10 +- .../src/arrays/decimal/compute/rules.rs | 6 +- vortex-array/src/arrays/decimal/utils.rs | 4 +- vortex-array/src/arrays/decimal/vtable/mod.rs | 8 +- vortex-array/src/arrays/dict/array.rs | 12 +- vortex-array/src/arrays/dict/vtable/mod.rs | 10 +- .../src/arrays/dict/vtable/operations.rs | 4 +- vortex-array/src/arrays/extension/array.rs | 2 +- .../src/arrays/extension/vtable/mod.rs | 16 +- .../src/arrays/extension/vtable/operations.rs | 2 +- vortex-array/src/arrays/filter/array.rs | 2 +- .../src/arrays/filter/execute/take.rs | 2 +- .../src/arrays/filter/execute/take/rank.rs | 4 +- vortex-array/src/arrays/filter/vtable.rs | 14 +- .../arrays/fixed_size_list/compute/take.rs | 30 +- .../src/arrays/fixed_size_list/vtable/mod.rs | 22 +- vortex-array/src/arrays/fixed_width/array.rs | 4 +- .../src/arrays/fixed_width/take/mod.rs | 4 +- .../src/arrays/fixed_width/take/records.rs | 2 +- .../src/arrays/fixed_width/take/slices.rs | 29 +- vortex-array/src/arrays/fixed_width/vtable.rs | 6 +- .../src/arrays/interleave/execute/bool.rs | 6 +- .../src/arrays/interleave/execute/mod.rs | 2 +- .../arrays/interleave/execute/primitive.rs | 6 +- vortex-array/src/arrays/interleave/mod.rs | 24 +- vortex-array/src/arrays/list/array.rs | 8 +- .../src/arrays/list/compute/filter.rs | 14 +- vortex-array/src/arrays/list/compute/take.rs | 39 +- vortex-array/src/arrays/list/vtable/mod.rs | 16 +- vortex-array/src/arrays/listview/array.rs | 38 +- vortex-array/src/arrays/listview/rebuild.rs | 6 +- .../src/arrays/listview/vtable/mod.rs | 18 +- vortex-array/src/arrays/map/array.rs | 6 +- vortex-array/src/arrays/map/compute/cast.rs | 2 +- vortex-array/src/arrays/map/compute/mod.rs | 2 +- vortex-array/src/arrays/map/vtable/mod.rs | 18 +- vortex-array/src/arrays/masked/array.rs | 6 +- vortex-array/src/arrays/masked/vtable/mod.rs | 14 +- .../src/arrays/masked/vtable/operations.rs | 2 +- vortex-array/src/arrays/null/compute/cast.rs | 2 +- vortex-array/src/arrays/null/compute/take.rs | 2 +- vortex-array/src/arrays/null/mod.rs | 10 +- vortex-array/src/arrays/patched/array.rs | 18 +- .../src/arrays/patched/compute/compare.rs | 8 +- vortex-array/src/arrays/patched/vtable/mod.rs | 4 +- .../src/arrays/piecewise_sequence/mod.rs | 28 +- .../src/arrays/piecewise_sequence/vtable.rs | 40 +- .../src/arrays/primitive/array/cast.rs | 2 +- .../src/arrays/primitive/array/conversion.rs | 2 +- .../src/arrays/primitive/array/mod.rs | 6 +- .../src/arrays/primitive/compute/cast.rs | 20 +- .../src/arrays/primitive/compute/zip.rs | 2 +- .../src/arrays/primitive/vtable/mod.rs | 14 +- vortex-array/src/arrays/scalar_fn/array.rs | 8 +- vortex-array/src/arrays/scalar_fn/plugin.rs | 2 +- vortex-array/src/arrays/scalar_fn/rules.rs | 6 +- .../src/arrays/scalar_fn/vtable/mod.rs | 14 +- .../src/arrays/scalar_fn/vtable/validity.rs | 4 +- vortex-array/src/arrays/slice/array.rs | 2 +- vortex-array/src/arrays/slice/vtable.rs | 16 +- vortex-array/src/arrays/struct_/array.rs | 12 +- .../src/arrays/struct_/compute/cast.rs | 2 +- .../src/arrays/struct_/compute/rules.rs | 2 +- vortex-array/src/arrays/struct_/vtable/mod.rs | 20 +- .../src/arrays/struct_/vtable/operations.rs | 2 +- vortex-array/src/arrays/union/array.rs | 10 +- vortex-array/src/arrays/union/tests/mod.rs | 2 +- vortex-array/src/arrays/union/tests/take.rs | 2 +- vortex-array/src/arrays/union/vtable/mod.rs | 22 +- .../src/arrays/union/vtable/operations.rs | 4 +- .../src/arrays/union/vtable/validate.rs | 12 +- vortex-array/src/arrays/validation_tests.rs | 16 +- vortex-array/src/arrays/varbin/array.rs | 10 +- vortex-array/src/arrays/varbin/builder.rs | 28 +- .../src/arrays/varbin/compute/compare.rs | 2 +- .../src/arrays/varbin/compute/filter.rs | 28 +- .../src/arrays/varbin/compute/take.rs | 73 ++- vortex-array/src/arrays/varbin/mod.rs | 3 +- vortex-array/src/arrays/varbin/vtable/mod.rs | 18 +- vortex-array/src/arrays/varbinview/array.rs | 12 +- .../arrays/varbinview/compute/fill_null.rs | 4 +- .../src/arrays/varbinview/compute/take.rs | 13 +- .../src/arrays/varbinview/compute/zip.rs | 2 +- vortex-array/src/arrays/varbinview/tests.rs | 2 +- .../src/arrays/varbinview/vtable/mod.rs | 24 +- vortex-array/src/arrays/variant/mod.rs | 18 +- vortex-array/src/arrays/variant/vtable/mod.rs | 22 +- vortex-array/src/builders/bool.rs | 2 +- vortex-array/src/builders/child.rs | 2 +- vortex-array/src/builders/decimal.rs | 6 +- vortex-array/src/builders/dict/bytes.rs | 8 +- vortex-array/src/builders/dict/mod.rs | 4 +- vortex-array/src/builders/dict/primitive.rs | 10 +- vortex-array/src/builders/extension.rs | 2 +- vortex-array/src/builders/fixed_size_list.rs | 16 +- .../src/builders/lazy_null_builder.rs | 2 +- vortex-array/src/builders/list.rs | 8 +- vortex-array/src/builders/listview.rs | 10 +- vortex-array/src/builders/map.rs | 6 +- vortex-array/src/builders/mod.rs | 4 +- vortex-array/src/builders/null.rs | 2 +- vortex-array/src/builders/primitive.rs | 2 +- vortex-array/src/builders/struct_.rs | 8 +- vortex-array/src/builders/tests.rs | 2 +- vortex-array/src/builders/validity.rs | 2 +- vortex-array/src/builders/varbinview.rs | 4 +- vortex-array/src/canonical.rs | 58 +- .../src/compute/conformance/binary_numeric.rs | 7 +- vortex-array/src/compute/conformance/cast.rs | 7 +- .../src/compute/conformance/consistency.rs | 6 +- vortex-array/src/dtype/decimal/mod.rs | 10 +- vortex-array/src/dtype/decimal/precision.rs | 8 +- vortex-array/src/dtype/decimal/types.rs | 4 +- vortex-array/src/dtype/dtype_impl.rs | 10 +- vortex-array/src/dtype/extension/erased.rs | 2 +- vortex-array/src/dtype/field_mask.rs | 6 +- vortex-array/src/dtype/map.rs | 2 +- vortex-array/src/dtype/ptype.rs | 4 +- vortex-array/src/dtype/serde/flatbuffers.rs | 87 ++- vortex-array/src/dtype/serde/proto.rs | 20 +- vortex-array/src/dtype/struct_.rs | 10 +- vortex-array/src/dtype/union.rs | 14 +- vortex-array/src/executor.rs | 23 +- vortex-array/src/expr/bound_expression.rs | 4 +- vortex-array/src/expr/expression.rs | 10 +- vortex-array/src/expr/exprs.rs | 6 +- vortex-array/src/expr/lambda/mod.rs | 10 +- vortex-array/src/expr/lambda/tests.rs | 4 +- vortex-array/src/expr/optimize.rs | 9 +- vortex-array/src/expr/proto.rs | 6 +- vortex-array/src/expr/traversal/fold.rs | 4 +- vortex-array/src/extension/datetime/date.rs | 16 +- vortex-array/src/extension/datetime/time.rs | 30 +- .../src/extension/datetime/timestamp.rs | 21 +- vortex-array/src/extension/datetime/unit.rs | 2 +- .../src/extension/tests/divisible_int.rs | 14 +- vortex-array/src/mask.rs | 2 +- vortex-array/src/mask_future.rs | 2 +- vortex-array/src/metadata.rs | 2 +- vortex-array/src/optimizer/mod.rs | 2 +- vortex-array/src/optimizer/rules.rs | 4 +- vortex-array/src/patches.rs | 67 +- vortex-array/src/scalar/cast.rs | 16 +- vortex-array/src/scalar/constructor.rs | 16 +- vortex-array/src/scalar/convert/decimal.rs | 22 +- .../src/scalar/convert/from_scalar.rs | 98 +-- vortex-array/src/scalar/convert/primitive.rs | 18 +- vortex-array/src/scalar/downcast.rs | 32 +- vortex-array/src/scalar/proto.rs | 46 +- vortex-array/src/scalar/scalar_impl.rs | 8 +- vortex-array/src/scalar/scalar_value.rs | 2 +- vortex-array/src/scalar/tests/casting.rs | 8 +- vortex-array/src/scalar/truncation.rs | 4 +- vortex-array/src/scalar/typed_view/binary.rs | 2 +- vortex-array/src/scalar/typed_view/bool.rs | 2 +- .../scalar/typed_view/decimal/arithmetic.rs | 2 +- .../src/scalar/typed_view/decimal/dvalue.rs | 8 +- .../scalar/typed_view/decimal/integer_cast.rs | 2 +- .../src/scalar/typed_view/decimal/scalar.rs | 4 +- .../src/scalar/typed_view/decimal/tests.rs | 10 +- .../src/scalar/typed_view/extension/mod.rs | 4 +- .../src/scalar/typed_view/extension/tests.rs | 4 +- vortex-array/src/scalar/typed_view/list.rs | 12 +- vortex-array/src/scalar/typed_view/map.rs | 12 +- .../src/scalar/typed_view/primitive/pvalue.rs | 53 +- .../src/scalar/typed_view/primitive/scalar.rs | 10 +- vortex-array/src/scalar/typed_view/struct_.rs | 14 +- vortex-array/src/scalar/typed_view/union.rs | 4 +- vortex-array/src/scalar/typed_view/utf8.rs | 2 +- vortex-array/src/scalar/typed_view/variant.rs | 2 +- vortex-array/src/scalar/validate.rs | 64 +- vortex-array/src/scalar_fn/erased.rs | 2 +- vortex-array/src/scalar_fn/fns/between/mod.rs | 6 +- .../src/scalar_fn/fns/binary/boolean.rs | 16 +- .../scalar_fn/fns/binary/compare/boolean.rs | 6 +- .../src/scalar_fn/fns/binary/compare/bytes.rs | 6 +- .../scalar_fn/fns/binary/compare/decimal.rs | 8 +- .../src/scalar_fn/fns/binary/compare/mod.rs | 10 +- .../scalar_fn/fns/binary/compare/nested.rs | 4 +- .../scalar_fn/fns/binary/compare/primitive.rs | 2 +- vortex-array/src/scalar_fn/fns/binary/mod.rs | 6 +- .../src/scalar_fn/fns/binary/numeric/mod.rs | 6 +- .../src/scalar_fn/fns/binary/numeric/row.rs | 7 +- vortex-array/src/scalar_fn/fns/byte_length.rs | 12 +- vortex-array/src/scalar_fn/fns/case_when.rs | 14 +- vortex-array/src/scalar_fn/fns/cast/mod.rs | 20 +- vortex-array/src/scalar_fn/fns/dynamic.rs | 2 +- vortex-array/src/scalar_fn/fns/ext_storage.rs | 4 +- .../src/scalar_fn/fns/fill_null/kernel.rs | 2 +- .../src/scalar_fn/fns/fill_null/mod.rs | 26 +- vortex-array/src/scalar_fn/fns/get_item.rs | 4 +- vortex-array/src/scalar_fn/fns/is_nan.rs | 2 +- vortex-array/src/scalar_fn/fns/like/mod.rs | 9 +- .../src/scalar_fn/fns/like/pattern.rs | 2 +- .../src/scalar_fn/fns/list_contains/mod.rs | 12 +- .../fns/list_contains/prepared/data.rs | 12 +- vortex-array/src/scalar_fn/fns/list_length.rs | 6 +- vortex-array/src/scalar_fn/fns/list_sum.rs | 14 +- vortex-array/src/scalar_fn/fns/literal.rs | 2 +- vortex-array/src/scalar_fn/fns/mask/kernel.rs | 4 +- vortex-array/src/scalar_fn/fns/mask/mod.rs | 2 +- vortex-array/src/scalar_fn/fns/merge.rs | 18 +- vortex-array/src/scalar_fn/fns/not/mod.rs | 2 +- vortex-array/src/scalar_fn/fns/pack.rs | 2 +- .../src/scalar_fn/fns/replace_time_zone.rs | 20 +- vortex-array/src/scalar_fn/fns/select.rs | 12 +- vortex-array/src/scalar_fn/fns/stat.rs | 2 +- .../src/scalar_fn/fns/variant_get/mod.rs | 22 +- vortex-array/src/scalar_fn/fns/zip/mod.rs | 4 +- vortex-array/src/scalar_fn/foreign.rs | 2 +- .../src/scalar_fn/internal/row_count.rs | 6 +- vortex-array/src/scalar_fn/typed.rs | 2 +- .../src/scalar_fn/unstable/row/batch/args.rs | 2 +- .../unstable/row/batch/execute/output.rs | 6 +- .../scalar_fn/unstable/row/batch/planning.rs | 2 +- .../src/scalar_fn/unstable/row/batch/tests.rs | 14 +- .../scalar_fn/unstable/row/execute/owned.rs | 16 +- .../unstable/row/execute/packed_bool.rs | 6 +- .../scalar_fn/unstable/row/execute/retry.rs | 4 +- .../scalar_fn/unstable/row/execute/sink.rs | 18 +- .../scalar_fn/unstable/row/execute/tests.rs | 8 +- .../src/scalar_fn/unstable/row/row_fn.rs | 2 +- .../unstable/row/types/element/bool.rs | 6 +- .../unstable/row/types/element/primitive.rs | 8 +- .../row/types/element/tuple/element_tuple.rs | 4 +- .../unstable/row/types/element/tuple/tests.rs | 4 +- .../unstable/row/types/element/utf8.rs | 8 +- .../scalar_fn/unstable/row/visitor/check.rs | 4 +- .../scalar_fn/unstable/row/visitor/plan.rs | 12 +- .../unstable/row/visitor/row_visitor.rs | 6 +- .../src/scalar_fn/unstable/row/vtable.rs | 10 +- vortex-array/src/scalar_fn/vtable.rs | 4 +- vortex-array/src/serde.rs | 57 +- vortex-array/src/session/mod.rs | 4 +- vortex-array/src/stats/flatbuffers.rs | 10 +- vortex-array/src/stats/stats_set.rs | 6 +- vortex-array/src/test_harness/trace/mod.rs | 2 +- vortex-array/src/test_harness/trace/tests.rs | 32 +- vortex-array/src/validity.rs | 12 +- vortex-arrow/src/convert.rs | 44 +- vortex-arrow/src/datum.rs | 2 +- vortex-arrow/src/dtype.rs | 18 +- vortex-arrow/src/executor/bool.rs | 2 +- vortex-arrow/src/executor/byte.rs | 10 +- vortex-arrow/src/executor/decimal.rs | 32 +- vortex-arrow/src/executor/dictionary.rs | 4 +- vortex-arrow/src/executor/fixed_size_list.rs | 6 +- vortex-arrow/src/executor/list.rs | 6 +- vortex-arrow/src/executor/list_view.rs | 6 +- vortex-arrow/src/executor/map.rs | 4 +- vortex-arrow/src/executor/mod.rs | 4 +- vortex-arrow/src/executor/null.rs | 2 +- vortex-arrow/src/executor/run_end.rs | 21 +- vortex-arrow/src/executor/struct_.rs | 4 +- vortex-arrow/src/executor/temporal.rs | 8 +- vortex-arrow/src/run_end_import.rs | 2 +- vortex-arrow/src/scalar.rs | 38 +- vortex-arrow/src/session.rs | 24 +- vortex-bench/src/conversions.rs | 5 +- vortex-bench/src/datasets/mod.rs | 2 +- vortex-bench/src/lib.rs | 10 +- vortex-bench/src/measurements.rs | 20 +- vortex-bench/src/public_bi.rs | 15 +- vortex-bench/src/runner.rs | 8 +- vortex-bench/src/statpopgen/builder.rs | 4 +- vortex-bench/src/statpopgen/vcf_conversion.rs | 54 +- vortex-bench/src/vector_dataset/convert.rs | 37 +- vortex-btrblocks/src/schemes/float/alprd.rs | 2 +- .../src/schemes/integer/sequence.rs | 4 +- vortex-btrblocks/tests/decimal_config.rs | 8 +- vortex-buffer/src/alignment.rs | 12 +- vortex-buffer/src/allocation.rs | 2 +- vortex-buffer/src/arrow.rs | 4 +- vortex-buffer/src/buffer.rs | 32 +- vortex-buffer/src/buffer_mut.rs | 29 +- vortex-buffer/src/const_.rs | 2 +- vortex-buffer/src/string.rs | 4 +- vortex-cloud/src/registry/tests.rs | 11 +- vortex-compressor/src/compressor/cascade.rs | 3 +- .../src/compressor/constant/tests.rs | 4 +- .../src/compressor/structural.rs | 2 +- vortex-compressor/src/compressor/tests.rs | 4 +- vortex-compressor/src/stats/float.rs | 6 +- vortex-compressor/src/stats/varbinview.rs | 2 +- vortex-cuda/benches/dynamic_dispatch_cuda.rs | 28 +- vortex-cuda/benches/filter_cuda.rs | 12 +- vortex-cuda/benches/zstd_cuda.rs | 12 +- vortex-cuda/ffi/src/lib.rs | 44 +- vortex-cuda/src/arrow/canonical.rs | 96 +-- vortex-cuda/src/arrow/dictionary_tests.rs | 8 +- vortex-cuda/src/arrow/list_view.rs | 42 +- vortex-cuda/src/arrow/mod.rs | 50 +- vortex-cuda/src/arrow/offsets.rs | 10 +- vortex-cuda/src/canonical.rs | 2 +- vortex-cuda/src/cub.rs | 14 +- vortex-cuda/src/device_buffer.rs | 51 +- vortex-cuda/src/dynamic_dispatch/mod.rs | 26 +- .../src/dynamic_dispatch/plan_builder.rs | 28 +- vortex-cuda/src/executor.rs | 16 +- vortex-cuda/src/file.rs | 4 +- vortex-cuda/src/hybrid_dispatch/mod.rs | 8 +- vortex-cuda/src/kernel/arrays/constant.rs | 14 +- vortex-cuda/src/kernel/arrays/dict.rs | 4 +- vortex-cuda/src/kernel/arrays/list.rs | 4 +- vortex-cuda/src/kernel/arrays/masked.rs | 4 +- vortex-cuda/src/kernel/encodings/alp.rs | 4 +- vortex-cuda/src/kernel/encodings/bitpacked.rs | 10 +- .../src/kernel/encodings/date_time_parts.rs | 10 +- .../kernel/encodings/decimal_byte_parts.rs | 4 +- vortex-cuda/src/kernel/encodings/delta.rs | 8 +- vortex-cuda/src/kernel/encodings/for_.rs | 9 +- vortex-cuda/src/kernel/encodings/fsst.rs | 5 +- vortex-cuda/src/kernel/encodings/onpair.rs | 36 +- vortex-cuda/src/kernel/encodings/runend.rs | 12 +- vortex-cuda/src/kernel/encodings/sequence.rs | 6 +- vortex-cuda/src/kernel/encodings/zigzag.rs | 10 +- vortex-cuda/src/kernel/encodings/zstd.rs | 11 +- .../src/kernel/encodings/zstd_buffers.rs | 10 +- vortex-cuda/src/kernel/filter/mod.rs | 16 +- vortex-cuda/src/kernel/mod.rs | 18 +- vortex-cuda/src/kernel/patches/mod.rs | 2 +- vortex-cuda/src/kernel/patches/types.rs | 2 +- vortex-cuda/src/kernel/slice/mod.rs | 4 +- vortex-cuda/src/layout.rs | 12 +- vortex-cuda/src/pinned.rs | 67 +- vortex-cuda/src/pooled_read_at.rs | 11 +- vortex-cuda/src/pooled_read_at/file.rs | 12 +- vortex-cuda/src/pooled_read_at/file/direct.rs | 22 +- vortex-cuda/src/pooled_read_at/file/tests.rs | 6 +- vortex-cuda/src/session.rs | 4 +- vortex-cuda/src/stream.rs | 16 +- vortex-cuda/src/stream_pool.rs | 14 +- vortex-datafusion/examples/vortex_table.rs | 2 +- vortex-datafusion/src/convert/scalars.rs | 35 +- vortex-datafusion/src/convert/stats/tests.rs | 2 +- vortex-datafusion/src/persistent/format.rs | 8 +- vortex-datafusion/src/v2/source.rs | 2 +- vortex-duckdb/src/convert/dtype.rs | 41 +- vortex-duckdb/src/convert/expr.rs | 16 +- vortex-duckdb/src/convert/scalar.rs | 51 +- vortex-duckdb/src/convert/table_filter.rs | 12 +- vortex-duckdb/src/convert/vector.rs | 10 +- vortex-duckdb/src/copy.rs | 8 +- vortex-duckdb/src/duckdb/connection.rs | 6 +- vortex-duckdb/src/duckdb/data_chunk.rs | 4 +- vortex-duckdb/src/duckdb/database.rs | 14 +- vortex-duckdb/src/duckdb/function.rs | 4 +- vortex-duckdb/src/duckdb/logical_type.rs | 18 +- vortex-duckdb/src/duckdb/macro_.rs | 16 +- vortex-duckdb/src/duckdb/query_result.rs | 4 +- vortex-duckdb/src/duckdb/table_filter.rs | 2 +- vortex-duckdb/src/duckdb/value.rs | 16 +- vortex-duckdb/src/duckdb/vector.rs | 4 +- vortex-duckdb/src/exporter/canonical.rs | 6 +- vortex-duckdb/src/exporter/chunked.rs | 2 +- vortex-duckdb/src/exporter/decimal.rs | 4 +- vortex-duckdb/src/exporter/extension.rs | 2 +- vortex-duckdb/src/exporter/mod.rs | 4 +- vortex-duckdb/src/exporter/uuid.rs | 2 +- vortex-duckdb/src/ffi.rs | 6 +- vortex-duckdb/src/lib.rs | 2 - vortex-duckdb/src/projection.rs | 6 +- vortex-duckdb/src/table_function.rs | 4 +- vortex-edition/src/lib.rs | 16 +- vortex-edition/src/session.rs | 18 +- vortex-edition/src/test_harness.rs | 2 +- vortex-edition/src/tests.rs | 6 +- vortex-error/src/lib.rs | 588 ++++++++---------- vortex-error/tests/ensure.rs | 64 +- vortex-error/tests/fmt.rs | 9 +- vortex-error/tests/kind.rs | 189 ++++++ .../src/analysis/referenced_field_paths.rs | 2 +- vortex-expr/src/stats/rewrite.rs | 2 +- vortex-expr/src/transform/bound_partition.rs | 6 +- vortex-ffi/cinclude/vortex.h | 14 +- vortex-ffi/examples/hello_vortex.rs | 4 +- vortex-ffi/src/array.rs | 28 +- vortex-ffi/src/data_source.rs | 2 +- vortex-ffi/src/dtype.rs | 12 +- vortex-ffi/src/error.rs | 47 +- vortex-ffi/src/lib.rs | 4 +- vortex-ffi/src/scalar.rs | 14 +- vortex-ffi/src/scan.rs | 10 +- vortex-ffi/src/session.rs | 2 +- vortex-ffi/src/sink.rs | 6 +- vortex-ffi/src/string.rs | 5 +- vortex-ffi/src/struct_array.rs | 2 +- vortex-file/src/footer/deserializer.rs | 26 +- vortex-file/src/footer/field_sizes.rs | 2 +- vortex-file/src/footer/mod.rs | 6 +- vortex-file/src/footer/postscript.rs | 12 +- vortex-file/src/footer/serializer.rs | 6 +- vortex-file/src/lib.rs | 5 - vortex-file/src/multi/mod.rs | 8 +- vortex-file/src/multi/uri.rs | 8 +- vortex-file/src/open.rs | 6 +- vortex-file/src/read/driver.rs | 2 +- vortex-file/src/read/request.rs | 6 +- vortex-file/src/segments/source.rs | 29 +- vortex-file/src/segments/writer.rs | 4 +- vortex-file/src/writer.rs | 14 +- vortex-file/tests/common/mod.rs | 5 - vortex-io/src/filesystem/glob.rs | 13 +- vortex-io/src/object_store/read_at.rs | 4 +- vortex-io/src/read_at.rs | 2 +- vortex-io/src/request/mod.rs | 6 +- vortex-io/src/request/source.rs | 10 +- vortex-io/src/request/source/tests.rs | 2 +- vortex-io/src/runtime/blocking_pool.rs | 18 +- vortex-io/src/runtime/handle.rs | 2 +- vortex-io/src/runtime/single.rs | 6 +- vortex-io/src/runtime/tokio.rs | 4 +- vortex-ipc/src/iterator.rs | 8 +- vortex-ipc/src/messages/decoder.rs | 8 +- vortex-ipc/src/messages/encoder.rs | 4 +- vortex-ipc/src/messages/reader_async.rs | 2 +- vortex-ipc/src/messages/reader_buf.rs | 2 +- vortex-ipc/src/messages/reader_sync.rs | 4 +- vortex-ipc/src/stream.rs | 12 +- vortex-jni/src/data_source.rs | 14 +- vortex-jni/src/errors.rs | 2 +- vortex-jni/src/expression.rs | 89 +-- vortex-jni/src/file.rs | 10 +- vortex-jni/src/io/mod.rs | 2 +- vortex-jni/src/io/read_at.rs | 21 +- vortex-jni/src/io/write.rs | 4 +- vortex-jni/src/object_store.rs | 9 +- vortex-jni/src/runtime.rs | 2 +- vortex-jni/src/scan.rs | 18 +- vortex-jni/src/session.rs | 2 - vortex-jni/src/writer.rs | 42 +- vortex-json/src/dtype.rs | 6 +- vortex-json/src/json_to_variant.rs | 10 +- vortex-json/src/lib.rs | 4 - vortex-layout/examples/reverse_index/main.rs | 8 +- vortex-layout/src/arrays/shared/vtable.rs | 10 +- vortex-layout/src/children.rs | 12 +- vortex-layout/src/layouts/chunked/mod.rs | 4 +- vortex-layout/src/layouts/chunked/reader.rs | 4 +- vortex-layout/src/layouts/dict/mod.rs | 8 +- vortex-layout/src/layouts/dict/writer.rs | 6 +- vortex-layout/src/layouts/file_stats.rs | 2 +- vortex-layout/src/layouts/flat/mod.rs | 8 +- vortex-layout/src/layouts/flat/writer.rs | 2 +- vortex-layout/src/layouts/foreign/mod.rs | 2 +- vortex-layout/src/layouts/indexed/mod.rs | 30 +- .../src/layouts/indexed/test_harness.rs | 10 +- vortex-layout/src/layouts/indexed/tests.rs | 44 +- vortex-layout/src/layouts/indexed/writer.rs | 8 +- vortex-layout/src/layouts/list/mod.rs | 21 +- vortex-layout/src/layouts/list/writer.rs | 4 +- vortex-layout/src/layouts/repartition.rs | 2 +- vortex-layout/src/layouts/row_idx/expr.rs | 2 +- vortex-layout/src/layouts/struct_/mod.rs | 12 +- vortex-layout/src/layouts/struct_/reader.rs | 16 +- vortex-layout/src/layouts/struct_/writer.rs | 6 +- .../aggregates/bloom_filter/canonical/bool.rs | 4 +- .../aggregates/bloom_filter/canonical/mod.rs | 2 +- .../zoned/aggregates/bloom_filter/mod.rs | 19 +- .../bloom_filter/partial/aggregate.rs | 2 +- .../aggregates/bloom_filter/partial/mod.rs | 2 +- .../aggregates/bloom_filter/partial/scalar.rs | 2 +- .../aggregates/bloom_filter/partial/serde.rs | 4 +- .../aggregates/bloom_filter/scalar_fn.rs | 21 +- vortex-layout/src/layouts/zoned/builder.rs | 2 +- vortex-layout/src/layouts/zoned/mod.rs | 26 +- vortex-layout/src/layouts/zoned/reader.rs | 4 +- vortex-layout/src/layouts/zoned/schema.rs | 6 +- vortex-layout/src/layouts/zoned/writer.rs | 2 +- vortex-layout/src/layouts/zoned/zone_map.rs | 8 +- vortex-layout/src/plan/physical/children.rs | 11 +- vortex-layout/src/plan/physical/lower.rs | 12 +- vortex-layout/src/plan/physical/mod.rs | 2 +- .../src/plan/physical/operators/concat.rs | 8 +- .../src/plan/physical/operators/filter.rs | 2 +- .../src/plan/physical/operators/mod.rs | 6 +- .../src/plan/physical/operators/pack.rs | 16 +- .../src/plan/physical/operators/scan.rs | 2 +- .../src/plan/physical/optimizer/rules.rs | 8 +- .../src/plan/physical/pipeline/scan.rs | 31 +- .../physical/pipeline/scheduling_tests.rs | 16 +- .../src/plan/physical/pipeline/synthetic.rs | 2 +- .../src/plan/physical/pipeline/tests.rs | 10 +- .../src/plan/physical/plans/concat.rs | 14 +- vortex-layout/src/plan/physical/plans/eval.rs | 6 +- .../src/plan/physical/plans/filter.rs | 4 +- .../src/plan/physical/plans/legacy_stats.rs | 4 +- .../src/plan/physical/plans/list_pack.rs | 26 +- vortex-layout/src/plan/physical/plans/pack.rs | 53 +- .../src/plan/physical/plans/row_idx.rs | 16 +- .../src/plan/physical/plans/share.rs | 4 +- vortex-layout/src/plan/physical/plans/take.rs | 14 +- .../src/plan/physical/plans/zoned.rs | 18 +- vortex-layout/src/plan/physical/selection.rs | 2 +- vortex-layout/src/plan/physical/tests.rs | 128 ++-- vortex-layout/src/plan/physical/typed.rs | 6 +- vortex-layout/src/plan/physical/vtable.rs | 2 +- vortex-layout/src/reader.rs | 6 +- vortex-layout/src/scan/execution/adaptor.rs | 8 +- .../src/scan/execution/projection.rs | 2 +- vortex-layout/src/scan/filter.rs | 4 +- vortex-layout/src/scan/layout.rs | 2 +- vortex-layout/src/scan/multi.rs | 4 +- vortex-layout/src/scan/repeated_scan.rs | 4 +- vortex-layout/src/scan/scan_builder.rs | 29 +- vortex-layout/src/scan/split_by.rs | 8 +- vortex-layout/src/scan/test.rs | 10 +- vortex-layout/src/scan/v2/io.rs | 12 +- vortex-layout/src/scan/v2/tests.rs | 6 +- vortex-layout/src/segments/test.rs | 2 +- vortex-layout/src/serde.rs | 19 +- vortex-layout/src/test.rs | 2 +- vortex-mask/src/bitops.rs | 10 +- vortex-mask/src/lib.rs | 4 +- vortex-python-cuda/src/lib.rs | 23 +- vortex-python/src/arrays/py/vtable.rs | 18 +- vortex-python/src/arrays/range_to_sequence.rs | 6 +- vortex-python/src/dtype/decimal.rs | 4 +- vortex-python/src/dtype/primitive.rs | 2 +- vortex-python/src/dtype/struct_.rs | 4 +- vortex-python/src/error.rs | 28 +- vortex-python/src/iter/python.rs | 2 +- vortex-python/src/object_store/resolve.rs | 6 +- vortex-python/src/python_repr.rs | 2 +- vortex-python/src/readable.rs | 6 +- vortex-python/src/scalar/into_py.rs | 2 +- vortex-python/src/scalar/struct_.rs | 2 +- vortex-python/test/test_file_arrow_indices.py | 2 +- vortex-row/src/codec.rs | 51 +- vortex-row/src/encode.rs | 6 +- vortex-row/src/encoder.rs | 8 +- vortex-row/src/options.rs | 4 +- vortex-row/src/size.rs | 9 +- vortex-scan/src/lib.rs | 2 +- vortex-scan/src/planning/driver/mod.rs | 22 +- vortex-scan/src/planning/next.rs | 2 +- vortex-scan/src/planning/tests/scripted.rs | 10 +- vortex-scan/src/selection.rs | 2 +- vortex-scan/src/strict_sorted_buffer.rs | 2 +- vortex-session/src/session.rs | 2 +- vortex-spatial/src/aggregate_fn/aabb.rs | 2 +- vortex-spatial/src/extension/coordinate.rs | 12 +- vortex-spatial/src/extension/linestring.rs | 83 +-- vortex-spatial/src/extension/mod.rs | 32 +- .../src/extension/multilinestring.rs | 89 +-- vortex-spatial/src/extension/multipoint.rs | 71 ++- vortex-spatial/src/extension/multipolygon.rs | 92 +-- vortex-spatial/src/extension/point.rs | 14 +- vortex-spatial/src/extension/polygon.rs | 92 +-- vortex-spatial/src/extension/rect.rs | 19 +- vortex-spatial/src/extension/wkb.rs | 16 +- vortex-spatial/src/lib.rs | 4 - vortex-spatial/src/scalar_fn/collect.rs | 15 +- vortex-spatial/src/scalar_fn/contains.rs | 4 +- vortex-spatial/src/scalar_fn/convex_hull.rs | 8 +- vortex-spatial/src/scalar_fn/envelope.rs | 10 +- vortex-spatial/src/scalar_fn/intersects.rs | 4 +- vortex-spatial/src/scalar_fn/length.rs | 13 +- vortex-spatial/src/scalar_fn/make_line.rs | 14 +- vortex-spatial/src/scalar_fn/row.rs | 4 +- vortex-spatial/src/test_harness.rs | 2 +- vortex-spatial/src/tests/point.rs | 4 +- vortex-spatial/src/tests/rect.rs | 6 +- vortex-spatial/src/tests/wkb.rs | 2 +- vortex-tensor/src/lib.rs | 4 - vortex-tensor/src/scalar_fns/l2_norm.rs | 4 +- vortex-tensor/src/scalar_fns/l2_normalize.rs | 7 +- vortex-tensor/src/scalar_fns/row.rs | 20 +- .../src/types/fixed_shape_tensor/matcher.rs | 2 +- .../src/types/fixed_shape_tensor/metadata.rs | 8 +- .../src/types/fixed_shape_tensor/proto.rs | 3 +- .../src/types/fixed_shape_tensor/vtable.rs | 8 +- vortex-tensor/src/types/vector/matcher.rs | 2 +- vortex-tensor/src/types/vector/mod.rs | 6 +- vortex-tensor/src/utils.rs | 24 +- vortex-test/compat-gen/src/adapter.rs | 8 +- vortex-test/compat-gen/src/check.rs | 11 +- .../fixtures/arrays/datasets/clickbench.rs | 41 +- vortex-test/compat-gen/src/fixtures/mod.rs | 2 +- vortex-test/compat-gen/src/generate.rs | 8 +- vortex-tui/src/browse/ui/segments.rs | 4 +- vortex-tui/src/inspect.rs | 22 +- vortex-tui/src/query.rs | 6 +- vortex-tui/src/segments.rs | 2 +- vortex-tui/src/tree.rs | 2 +- .../common_encoding_tree_throughput.rs | 4 +- vortex/benches/pipeline.rs | 2 +- vortex/src/editions/mod.rs | 4 - vortex/src/editions/tests.rs | 15 +- 765 files changed, 5203 insertions(+), 4616 deletions(-) create mode 100644 vortex-error/tests/kind.rs diff --git a/STYLE.md b/STYLE.md index b65a1de164f..05ef59a5b61 100644 --- a/STYLE.md +++ b/STYLE.md @@ -54,8 +54,20 @@ - `vortex_panic!` for handling invariant violations - `vortex_ensure!` and `vortex_ensure_eq!` for checking conditions. Prefer `vortex_ensure_eq!(a, b)` with no message: the error already shows both expressions and values. - Add a message only for context the expressions lack, and never repeat the values in it. -- Add context to errors using `.with_context()` + Add a message only for context the expressions lack, and never repeat the values in it. With no + message the error is `AssertionFailed`; when the check is on the caller's input rather than an + internal invariant, name the kind alone, as in `vortex_ensure_eq!(a, b, InvalidArgument)`. +- Every message names its `VortexErrorKind`, as in `vortex_bail!(InvalidArgument: "...")`; the + macros reject a message without one. Choose the kind by what went wrong, the way Python picks an + exception class: `InvalidArgument` (`ValueError`) for a value the callee rejects, + `MismatchedTypes` (`TypeError`) for the wrong dtype, `OutOfBounds` (`IndexError`) for a position + past the end, `NotFound` (`KeyError`) for a name that resolves to nothing, `Overflow` + (`OverflowError`) for a value that does not fit its target, `NotImplemented`, `Serde` for an + unreadable wire or file format, `Io` for a failed system or driver call, `AssertionFailed` for a + broken internal invariant, and `Other` only when nothing else fits. Never classify by where the + failure happened. +- Add context to an existing error with `.with_context()`, which keeps its kind; do not format it + into a new `vortex_err!`, which discards the kind. - Include backtraces for better debugging - Use `VortexExpect` trait when unwrapping is appropriate with proper error context. diff --git a/encodings/alp/src/alp/array.rs b/encodings/alp/src/alp/array.rs index 5e667eba8b0..075841b2ecb 100644 --- a/encodings/alp/src/alp/array.rs +++ b/encodings/alp/src/alp/array.rs @@ -98,7 +98,7 @@ impl VTable for ALP { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ALPArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ALPArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -144,7 +144,7 @@ impl VTable for ALP { let encoded_ptype = match &dtype { DType::Primitive(PType::F32, n) => DType::Primitive(PType::I32, *n), DType::Primitive(PType::F64, n) => DType::Primitive(PType::I64, *n), - d => vortex_bail!(MismatchedTypes: "f32 or f64", d), + d => vortex_bail!(MismatchedTypes: "expected type: f32 or f64 but instead got {}", d), }; let encoded = children.get(0, &encoded_ptype, len)?; @@ -275,7 +275,7 @@ impl ALPData { encoded.dtype(), DType::Primitive(PType::I32 | PType::I64, _) ), - "ALP encoded ints have invalid DType {}", + MismatchedTypes: "ALP encoded ints have invalid DType {}", encoded.dtype(), ); @@ -284,15 +284,15 @@ impl ALPData { let Exponents { e, f } = exponents; match encoded.dtype().as_ptype() { PType::I32 => { - vortex_ensure!(exponents.e <= f32::MAX_EXPONENT, "e out of bounds: {e}"); - vortex_ensure!(exponents.f <= f32::MAX_EXPONENT, "f out of bounds: {f}"); + vortex_ensure!(exponents.e <= f32::MAX_EXPONENT, InvalidArgument: "e out of bounds: {e}"); + vortex_ensure!(exponents.f <= f32::MAX_EXPONENT, InvalidArgument: "f out of bounds: {f}"); if let Some(patches) = patches { Self::validate_patches::(patches, encoded)?; } } PType::I64 => { - vortex_ensure!(e <= f64::MAX_EXPONENT, "e out of bounds: {e}"); - vortex_ensure!(f <= f64::MAX_EXPONENT, "f out of bounds: {f}"); + vortex_ensure!(e <= f64::MAX_EXPONENT, InvalidArgument: "e out of bounds: {e}"); + vortex_ensure!(f <= f64::MAX_EXPONENT, InvalidArgument: "f out of bounds: {f}"); if let Some(patches) = patches { Self::validate_patches::(patches, encoded)?; @@ -303,7 +303,7 @@ impl ALPData { // Validate patches if let Some(patches) = patches { - vortex_ensure_eq!(patches.array_len(), encoded.len()); + vortex_ensure_eq!(patches.array_len(), encoded.len(), InvalidArgument); // Verify that the patches DType are of the proper DType. } @@ -319,7 +319,9 @@ impl ALPData { DType::Primitive(PType::I64, nullability) => { Ok(DType::Primitive(PType::F64, *nullability)) } - _ => vortex_bail!("ALP encoded ints have invalid DType {}", encoded.dtype(),), + _ => { + vortex_bail!(MismatchedTypes: "ALP encoded ints have invalid DType {}", encoded.dtype(),) + } } } @@ -328,10 +330,10 @@ impl ALPData { patches: &Patches, encoded: &ArrayRef, ) -> VortexResult<()> { - vortex_ensure_eq!(patches.array_len(), encoded.len()); + vortex_ensure_eq!(patches.array_len(), encoded.len(), InvalidArgument); let expected_type = DType::Primitive(T::PTYPE, encoded.dtype().nullability()); - vortex_ensure_eq!(patches.dtype(), &expected_type); + vortex_ensure_eq!(patches.dtype(), &expected_type, MismatchedTypes); Ok(()) } @@ -445,11 +447,11 @@ fn validate_parts( ) -> VortexResult<()> { let logical_dtype = ALPData::logical_dtype(encoded)?; ALPData::validate_components(encoded, exponents, patches.as_ref())?; - vortex_ensure_eq!(encoded.len(), len, "ALP encoded len must match outer len"); + vortex_ensure_eq!(encoded.len(), len, InvalidArgument: "ALP encoded len must match outer len"); vortex_ensure_eq!( &logical_dtype, dtype, - "ALP dtype does not match encoded logical dtype" + MismatchedTypes: "ALP dtype does not match encoded logical dtype" ); Ok(()) } diff --git a/encodings/alp/src/alp/compress.rs b/encodings/alp/src/alp/compress.rs index 024c95f82e3..5d510159ed7 100644 --- a/encodings/alp/src/alp/compress.rs +++ b/encodings/alp/src/alp/compress.rs @@ -39,7 +39,7 @@ macro_rules! match_each_alp_float_ptype { type $enc = f64; $body } - _ => vortex_panic!("ALP can only encode f32 and f64, got {}", ptype), + _ => vortex_panic!(MismatchedTypes: "ALP can only encode f32 and f64, got {}", ptype), } }}; } @@ -52,7 +52,7 @@ pub fn alp_encode( let (exponents, encoded, patches) = match parray.ptype() { PType::F32 => alp_encode_components_typed::(parray, exponents, ctx)?, PType::F64 => alp_encode_components_typed::(parray, exponents, ctx)?, - _ => vortex_bail!("ALP can only encode f32 and f64"), + _ => vortex_bail!(MismatchedTypes: "ALP can only encode f32 and f64"), }; // SAFETY: alp_encode_components_typed must return well-formed components diff --git a/encodings/alp/src/alp/compute/compare.rs b/encodings/alp/src/alp/compute/compare.rs index 457aacee172..9921cf731c2 100644 --- a/encodings/alp/src/alp/compute/compare.rs +++ b/encodings/alp/src/alp/compute/compare.rs @@ -45,7 +45,7 @@ impl CompareKernel for ALP { if let Some(const_scalar) = rhs.as_constant() { let pscalar = const_scalar.as_primitive_opt().ok_or_else(|| { vortex_err!( - "ALP Compare RHS had the wrong type {}, expected {}", + InvalidArgument: "ALP Compare RHS had the wrong type {}, expected {}", const_scalar, const_scalar.dtype() ) @@ -55,7 +55,7 @@ impl CompareKernel for ALP { match pscalar.typed_value::() { Some(value) => return alp_scalar_compare(lhs, value, operator), None => vortex_bail!( - "Failed to convert scalar {:?} to ALP type {:?}", + InvalidArgument: "Failed to convert scalar {:?} to ALP type {:?}", pscalar, pscalar.ptype() ), diff --git a/encodings/alp/src/alp/ops.rs b/encodings/alp/src/alp/ops.rs index db6f89ecf91..b374a052ff4 100644 --- a/encodings/alp/src/alp/ops.rs +++ b/encodings/alp/src/alp/ops.rs @@ -36,7 +36,7 @@ impl OperationsVTable for ALP { let encoded_val = state .slot(ALPSlots::ENCODED)? - .ok_or_else(|| vortex_err!("ALP encoded slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "ALP encoded slot is missing"))? .execute_scalar(index, ctx)?; Ok(match_each_alp_float_ptype!(array.dtype().as_ptype(), |T| { diff --git a/encodings/alp/src/alp/plugin.rs b/encodings/alp/src/alp/plugin.rs index b72893efb32..738bec6f919 100644 --- a/encodings/alp/src/alp/plugin.rs +++ b/encodings/alp/src/alp/plugin.rs @@ -55,7 +55,7 @@ impl ArrayPlugin for ALPPatchedPlugin { vortex_ensure_eq!( parts.serialized_id, self.id(), - "ALP plugin does not recognize serialized ID" + Serde: "ALP plugin does not recognize serialized ID" ); let alp_array = Array::::try_from_parts(ArrayVTable::deserialize( &ALP, @@ -66,7 +66,7 @@ impl ArrayPlugin for ALPPatchedPlugin { parts.children, session, )?) - .map_err(|_| vortex_err!("ALP plugin should only deserialize vortex.alp"))?; + .map_err(|_| vortex_err!(Serde: "ALP plugin should only deserialize vortex.alp"))?; // Check if there are interior patches to externalize. let Some(patches) = alp_array.patches() else { @@ -164,15 +164,13 @@ mod tests { assert_arrays_eq!(deserialized, parray, &mut SESSION.create_execution_ctx()); - let patched: PatchedArray = deserialized - .try_downcast() - .map_err(|a| vortex_err!("Expected Patched, got {}", a.encoding_id()))?; + let patched: PatchedArray = deserialized.try_downcast().map_err( + |a| vortex_err!(MismatchedTypes: "Expected Patched, got {}", a.encoding_id()), + )?; - let inner_alp: ALPArray = patched - .inner() - .clone() - .try_downcast() - .map_err(|a| vortex_err!("Expected inner ALP, got {}", a.encoding_id()))?; + let inner_alp: ALPArray = patched.inner().clone().try_downcast().map_err( + |a| vortex_err!(MismatchedTypes: "Expected inner ALP, got {}", a.encoding_id()), + )?; assert!( inner_alp.patches().is_none(), @@ -218,9 +216,9 @@ mod tests { assert_arrays_eq!(deserialized, parray, &mut SESSION.create_execution_ctx()); - let result = deserialized - .try_downcast::() - .map_err(|a| vortex_err!("Expected deserialized ALP, got {}", a.encoding_id()))?; + let result = deserialized.try_downcast::().map_err( + |a| vortex_err!(Serde: "Expected deserialized ALP, got {}", a.encoding_id()), + )?; assert!(result.patches().is_none(), "Result should not have patches"); diff --git a/encodings/alp/src/alp_rd/array.rs b/encodings/alp/src/alp_rd/array.rs index 71a450585a6..fe5c0b8d340 100644 --- a/encodings/alp/src/alp_rd/array.rs +++ b/encodings/alp/src/alp_rd/array.rs @@ -122,7 +122,7 @@ impl VTable for ALPRD { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ALPRDArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ALPRDArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -174,7 +174,7 @@ impl VTable for ALPRD { let metadata = ALPRDMetadata::decode(metadata)?; if children.len() < 2 { vortex_bail!( - "Expected at least 2 children for ALPRD encoding, found {}", + InvalidArgument: "Expected at least 2 children for ALPRD encoding, found {}", children.len() ); } @@ -185,8 +185,9 @@ impl VTable for ALPRD { [0..metadata.dict_len as usize] .iter() .map(|&i| { - u16::try_from(i) - .map_err(|_| vortex_err!("left_parts_dictionary code {i} does not fit in u16")) + u16::try_from(i).map_err( + |_| vortex_err!(Overflow: "left_parts_dictionary code {i} does not fit in u16"), + ) }) .try_collect()?; @@ -197,7 +198,7 @@ impl VTable for ALPRD { DType::Primitive(PType::F64, _) => { DType::Primitive(PType::U64, Nullability::NonNullable) } - _ => vortex_bail!("Expected f32 or f64 dtype, got {:?}", dtype), + _ => vortex_bail!(MismatchedTypes: "Expected f32 or f64 dtype, got {:?}", dtype), }; let right_parts = children.get(1, &right_parts_dtype, len)?; @@ -223,7 +224,7 @@ impl VTable for ALPRD { left_parts_dictionary, u8::try_from(metadata.right_bit_width).map_err(|_| { vortex_err!( - "right_bit_width {} out of u8 range", + Overflow: "right_bit_width {} out of u8 range", metadata.right_bit_width ) })?, @@ -477,18 +478,18 @@ fn validate_parts( left_parts_patches: Option<&Patches>, ) -> VortexResult<()> { if !dtype.is_float() { - vortex_bail!("ALPRDArray given invalid DType ({dtype})"); + vortex_bail!(InvalidArgument: "ALPRDArray given invalid DType ({dtype})"); } - vortex_ensure_eq!(left_parts.len(), len); - vortex_ensure_eq!(right_parts.len(), len); + vortex_ensure_eq!(left_parts.len(), len, InvalidArgument); + vortex_ensure_eq!(right_parts.len(), len, InvalidArgument); if !left_parts.dtype().is_unsigned_int() { - vortex_bail!("left_parts dtype must be uint"); + vortex_bail!(InvalidArgument: "left_parts dtype must be uint"); } if dtype.is_nullable() != left_parts.dtype().is_nullable() { vortex_bail!( - "ALPRDArray dtype nullability ({}) must match left_parts dtype nullability ({})", + InvalidArgument: "ALPRDArray dtype nullability ({}) must match left_parts dtype nullability ({})", dtype, left_parts.dtype() ); @@ -497,12 +498,16 @@ fn validate_parts( let expected_right_parts_dtype = match dtype { DType::Primitive(PType::F32, _) => DType::Primitive(PType::U32, Nullability::NonNullable), DType::Primitive(PType::F64, _) => DType::Primitive(PType::U64, Nullability::NonNullable), - _ => vortex_bail!("Expected f32 or f64 dtype, got {:?}", dtype), + _ => vortex_bail!(MismatchedTypes: "Expected f32 or f64 dtype, got {:?}", dtype), }; - vortex_ensure_eq!(right_parts.dtype(), &expected_right_parts_dtype); + vortex_ensure_eq!( + right_parts.dtype(), + &expected_right_parts_dtype, + MismatchedTypes + ); if let Some(patches) = left_parts_patches { - vortex_ensure_eq!(patches.array_len(), len); + vortex_ensure_eq!(patches.array_len(), len, InvalidArgument); // Left-parts exceptions are always all-valid and are stored as the non-nullable left-parts // dtype. Requiring that exact dtype (rather than ignoring nullability) means each // construction path must produce correct patches, removing the need to normalize them. @@ -511,7 +516,7 @@ fn validate_parts( vortex_ensure_eq!( patches.dtype(), &expected, - "patches dtype must be the non-nullable left_parts dtype" + MismatchedTypes: "patches dtype must be the non-nullable left_parts dtype" ); } diff --git a/encodings/alp/src/alp_rd/mod.rs b/encodings/alp/src/alp_rd/mod.rs index 8b0cd8f2f39..ec663339f38 100644 --- a/encodings/alp/src/alp_rd/mod.rs +++ b/encodings/alp/src/alp_rd/mod.rs @@ -150,7 +150,7 @@ where T::UINT: NativePType, { if left_parts.len() != right_parts.len() { - vortex_panic!("alp_rd_decode: left_parts.len != right_parts.len"); + vortex_panic!(AssertionFailed: "alp_rd_decode: left_parts.len != right_parts.len"); } if let Some(patches) = left_parts_patches { diff --git a/encodings/bytebool/src/array.rs b/encodings/bytebool/src/array.rs index 9413cbaa8b4..14a052fbe6e 100644 --- a/encodings/bytebool/src/array.rs +++ b/encodings/bytebool/src/array.rs @@ -85,14 +85,14 @@ impl VTable for ByteBool { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.buffer().clone(), - _ => vortex_panic!("ByteBoolArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "ByteBoolArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("values".to_string()), - _ => vortex_panic!("ByteBoolArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "ByteBoolArray buffer_name index {idx} out of bounds"), } } @@ -101,7 +101,7 @@ impl VTable for ByteBool { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1); + vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); let data = ByteBoolData::new(buffers[0].clone()); Ok(ArrayParts::new( self.clone(), @@ -130,7 +130,7 @@ impl VTable for ByteBool { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "ByteBoolArray expects empty metadata, got {} bytes", + InvalidArgument: "ByteBoolArray expects empty metadata, got {} bytes", metadata.len() ); } @@ -140,11 +140,11 @@ impl VTable for ByteBool { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("Expected 0 or 1 child, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 0 or 1 child, got {}", children.len()); }; if buffers.len() != 1 { - vortex_bail!("Expected 1 buffer, got {}", buffers.len()); + vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); } let buffer = buffers[0].clone(); @@ -261,10 +261,10 @@ impl ByteBoolData { len: usize, ) -> VortexResult<()> { let expected_dtype = DType::Bool(validity.nullability()); - vortex_ensure_eq!(dtype, &expected_dtype); - vortex_ensure_eq!(buffer.len(), len); + vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes); + vortex_ensure_eq!(buffer.len(), len, InvalidArgument); if let Some(vlen) = validity.maybe_len() { - vortex_ensure_eq!(vlen, len); + vortex_ensure_eq!(vlen, len, InvalidArgument); } Ok(()) } diff --git a/encodings/bytebool/src/compute.rs b/encodings/bytebool/src/compute.rs index 6a92a039ec8..9b8fb0ce979 100644 --- a/encodings/bytebool/src/compute.rs +++ b/encodings/bytebool/src/compute.rs @@ -129,7 +129,7 @@ impl BooleanKernel for ByteBool { let rhs = rhs .scalar() .as_bool_opt() - .ok_or_else(|| vortex_err!("expected boolean scalar"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))?; return kleene_boolean_buffer_scalar( lhs_values, lhs.validity()?, @@ -280,7 +280,9 @@ mod tests { let and_result = ::boolean(lhs.as_view(), &rhs, Operator::And, &mut ctx)? - .ok_or_else(|| vortex_err!("ByteBool should handle ByteBool boolean AND"))?; + .ok_or_else( + || vortex_err!(AssertionFailed: "ByteBool should handle ByteBool boolean AND"), + )?; assert_arrays_eq!( and_result, BoolArray::from_iter([Some(false), None, None, Some(false), None]), @@ -289,7 +291,9 @@ mod tests { let or_result = ::boolean(lhs.as_view(), &rhs, Operator::Or, &mut ctx)? - .ok_or_else(|| vortex_err!("ByteBool should handle ByteBool boolean OR"))?; + .ok_or_else( + || vortex_err!(AssertionFailed: "ByteBool should handle ByteBool boolean OR"), + )?; assert_arrays_eq!( or_result, BoolArray::from_iter([None, Some(true), Some(true), Some(false), None]), diff --git a/encodings/datetime-parts/src/array.rs b/encodings/datetime-parts/src/array.rs index 8fd621bdb0d..429bd602e8c 100644 --- a/encodings/datetime-parts/src/array.rs +++ b/encodings/datetime-parts/src/array.rs @@ -74,17 +74,17 @@ pub struct DateTimePartsMetadata { impl DateTimePartsMetadata { pub fn get_days_ptype(&self) -> VortexResult { PType::try_from(self.days_ptype) - .map_err(|_| vortex_err!("Invalid PType {}", self.days_ptype)) + .map_err(|_| vortex_err!(InvalidArgument: "Invalid PType {}", self.days_ptype)) } pub fn get_seconds_ptype(&self) -> VortexResult { PType::try_from(self.seconds_ptype) - .map_err(|_| vortex_err!("Invalid PType {}", self.seconds_ptype)) + .map_err(|_| vortex_err!(InvalidArgument: "Invalid PType {}", self.seconds_ptype)) } pub fn get_subseconds_ptype(&self) -> VortexResult { PType::try_from(self.subseconds_ptype) - .map_err(|_| vortex_err!("Invalid PType {}", self.subseconds_ptype)) + .map_err(|_| vortex_err!(InvalidArgument: "Invalid PType {}", self.subseconds_ptype)) } } @@ -115,11 +115,11 @@ impl VTable for DateTimeParts { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("DateTimePartsArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "DateTimePartsArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("DateTimePartsArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "DateTimePartsArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -156,7 +156,7 @@ impl VTable for DateTimeParts { let metadata = DateTimePartsMetadata::decode(metadata)?; if children.len() != 3 { vortex_bail!( - "Expected 3 children for datetime-parts encoding, found {}", + InvalidArgument: "Expected 3 children for datetime-parts encoding, found {}", children.len() ) } @@ -313,25 +313,25 @@ impl DateTimePartsData { subseconds: &ArrayRef, len: usize, ) -> VortexResult<()> { - vortex_ensure_eq!(days.len(), len); + vortex_ensure_eq!(days.len(), len, InvalidArgument); if !days.dtype().is_int() || (dtype.is_nullable() != days.dtype().is_nullable()) { vortex_bail!( - "Expected integer with nullability {}, got {}", + MismatchedTypes: "Expected integer with nullability {}, got {}", dtype.is_nullable(), days.dtype() ); } if !seconds.dtype().is_int() || seconds.dtype().is_nullable() { - vortex_bail!(MismatchedTypes: "non-nullable integer", seconds.dtype()); + vortex_bail!(MismatchedTypes: "expected type: non-nullable integer but instead got {}", seconds.dtype()); } if !subseconds.dtype().is_int() || subseconds.dtype().is_nullable() { - vortex_bail!(MismatchedTypes: "non-nullable integer", subseconds.dtype()); + vortex_bail!(MismatchedTypes: "expected type: non-nullable integer but instead got {}", subseconds.dtype()); } if len != seconds.len() || len != subseconds.len() { vortex_bail!( - "Mismatched lengths {} {} {}", + MismatchedTypes: "Mismatched lengths {} {} {}", days.len(), seconds.len(), subseconds.len() diff --git a/encodings/datetime-parts/src/canonical.rs b/encodings/datetime-parts/src/canonical.rs index 0b375d84b2d..2f854ffa6a2 100644 --- a/encodings/datetime-parts/src/canonical.rs +++ b/encodings/datetime-parts/src/canonical.rs @@ -41,11 +41,11 @@ pub fn decode_to_temporal( ctx: &mut ExecutionCtx, ) -> VortexResult { let DType::Extension(ext) = dtype else { - vortex_panic!(Compute: "expected dtype to be DType::Extension variant") + vortex_panic!(MismatchedTypes: "expected dtype to be DType::Extension variant") }; let Some(options) = ext.metadata_opt::() else { - vortex_panic!(Compute: "must decode TemporalMetadata from extension metadata"); + vortex_panic!(Serde: "must decode TemporalMetadata from extension metadata"); }; let divisor = match options.unit { diff --git a/encodings/datetime-parts/src/compress.rs b/encodings/datetime-parts/src/compress.rs index d84f4b6be91..8c5b7410368 100644 --- a/encodings/datetime-parts/src/compress.rs +++ b/encodings/datetime-parts/src/compress.rs @@ -34,7 +34,7 @@ pub struct TemporalParts { pub fn split_temporal(array: TemporalArray, ctx: &mut ExecutionCtx) -> VortexResult { let time_unit = array.temporal_metadata().time_unit(); if matches!(time_unit, TimeUnit::Days) { - vortex_bail!("Cannot handle day-level data"); + vortex_bail!(NotImplemented: "Cannot handle day-level data"); } let temporal_values = array diff --git a/encodings/datetime-parts/src/compute/take.rs b/encodings/datetime-parts/src/compute/take.rs index 7ca56f55b97..23deaa616da 100644 --- a/encodings/datetime-parts/src/compute/take.rs +++ b/encodings/datetime-parts/src/compute/take.rs @@ -49,16 +49,16 @@ fn take_datetime_parts( // If they became nullable due to nullable indices, we need to fill nulls. // But first, we need to check that the types are consistent. if !taken_days.dtype().is_nullable() { - vortex_panic!("Mismatched types: days is not nullable, seconds is nullable"); + vortex_panic!(MismatchedTypes: "Mismatched types: days is not nullable, seconds is nullable"); } if !taken_seconds.dtype().is_nullable() { - vortex_panic!("Mismatched types: seconds is not nullable, days is nullable"); + vortex_panic!(MismatchedTypes: "Mismatched types: seconds is not nullable, days is nullable"); } if !taken_subseconds.dtype().is_nullable() { - vortex_panic!("Mismatched types: subseconds is not nullable, days & seconds are nullable"); + vortex_panic!(MismatchedTypes: "Mismatched types: subseconds is not nullable, days & seconds are nullable"); } if !indices.dtype().is_nullable() { - vortex_panic!("Mismatched types: indices are not nullable, days & seconds are nullable"); + vortex_panic!(MismatchedTypes: "Mismatched types: indices are not nullable, days & seconds are nullable"); } let seconds_fill = array diff --git a/encodings/datetime-parts/src/ops.rs b/encodings/datetime-parts/src/ops.rs index 4fc0c0e3638..ad1aa48606e 100644 --- a/encodings/datetime-parts/src/ops.rs +++ b/encodings/datetime-parts/src/ops.rs @@ -29,13 +29,13 @@ impl OperationsVTable for DateTimeParts { let array = state.array(); let DType::Extension(ext) = array.dtype().clone() else { vortex_panic!( - "DateTimePartsArray must have extension dtype, found {}", + MismatchedTypes: "DateTimePartsArray must have extension dtype, found {}", array.dtype() ); }; let Some(options) = ext.metadata_opt::() else { - vortex_panic!(Compute: "must decode TemporalMetadata from extension metadata"); + vortex_panic!(Serde: "must decode TemporalMetadata from extension metadata"); }; if !state.is_valid(index, ctx)? { @@ -87,7 +87,7 @@ fn part_at( ) -> VortexResult { Ok(state .slot(slot)? - .ok_or_else(|| vortex_err!("DateTimeParts {name} slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "DateTimeParts {name} slot is missing"))? .execute_scalar(index, ctx)? .as_primitive() .as_::() diff --git a/encodings/datetime-parts/src/timestamp.rs b/encodings/datetime-parts/src/timestamp.rs index a9e9bcc3322..07a9888fb21 100644 --- a/encodings/datetime-parts/src/timestamp.rs +++ b/encodings/datetime-parts/src/timestamp.rs @@ -37,7 +37,7 @@ pub fn split(timestamp: i64, time_unit: TimeUnit) -> VortexResult split_with_divisor::<1_000_000>(timestamp), TimeUnit::Milliseconds => split_with_divisor::<1_000>(timestamp), TimeUnit::Seconds => split_with_divisor::<1>(timestamp), - TimeUnit::Days => vortex_bail!("Cannot handle day-level data"), + TimeUnit::Days => vortex_bail!(NotImplemented: "Cannot handle day-level data"), }) } @@ -71,7 +71,7 @@ pub fn combine(ts_parts: TimestampParts, time_unit: TimeUnit) -> i64 { TimeUnit::Microseconds => 1_000_000, TimeUnit::Milliseconds => 1_000, TimeUnit::Seconds => 1, - TimeUnit::Days => vortex_panic!("Cannot handle day-level data"), + TimeUnit::Days => vortex_panic!(NotImplemented: "Cannot handle day-level data"), }; ts_parts.days as i64 * SECONDS_PER_DAY * divisor diff --git a/encodings/decimal-byte-parts/benches/common/mod.rs b/encodings/decimal-byte-parts/benches/common/mod.rs index 197c518b722..dc8044702d4 100644 --- a/encodings/decimal-byte-parts/benches/common/mod.rs +++ b/encodings/decimal-byte-parts/benches/common/mod.rs @@ -85,7 +85,7 @@ pub(super) mod arrays { DecimalType::I256 => { DecimalArray::new(i256_values(len), DecimalDType::new(76, 2), validity) } - _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), } } } diff --git a/encodings/decimal-byte-parts/benches/dbp_assemble.rs b/encodings/decimal-byte-parts/benches/dbp_assemble.rs index 33ab5efbf2a..ee2dcf1cdc8 100644 --- a/encodings/decimal-byte-parts/benches/dbp_assemble.rs +++ b/encodings/decimal-byte-parts/benches/dbp_assemble.rs @@ -62,7 +62,7 @@ fn dbp_assemble_kernel(bencher: Bencher, (values_type, len): (DecimalType, usize ) }); } - _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), } } @@ -96,7 +96,7 @@ fn dbp_assemble_kernel_narrow_msp(bencher: Bencher, (values_type, len): (Decimal ) }); } - _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), } } @@ -154,7 +154,7 @@ mod arrays { buffer![u32::MAX; len].into_array(), ], ), - _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), }; bench_parts( bencher, diff --git a/encodings/decimal-byte-parts/benches/dbp_split.rs b/encodings/decimal-byte-parts/benches/dbp_split.rs index 933eb31a519..3bdf5dddd23 100644 --- a/encodings/decimal-byte-parts/benches/dbp_split.rs +++ b/encodings/decimal-byte-parts/benches/dbp_split.rs @@ -68,7 +68,7 @@ fn bench_split(bencher: Bencher, values_type: DecimalType, len: usize, validity: ) }); } - _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), } } diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs index 7b60b349023..212306d8a69 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs @@ -95,26 +95,26 @@ impl DecimalBytePartsData { len: usize, ) -> VortexResult<()> { if !msp.dtype().is_signed_int() { - vortex_bail!("msp must be a signed integer array") + vortex_bail!(InvalidArgument: "msp must be a signed integer array") } let expected_dtype = DType::Decimal(decimal_dtype, msp.dtype().nullability()); - vortex_ensure_eq!(dtype, &expected_dtype); - vortex_ensure_eq!(msp.len(), len); + vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes); + vortex_ensure_eq!(msp.len(), len, InvalidArgument); let lower_part_count = lower_parts.len(); vortex_ensure!( lower_part_count <= MAX_LOWER_PARTS, - "at most {MAX_LOWER_PARTS} lower parts are supported, got {lower_part_count}" + InvalidArgument: "at most {MAX_LOWER_PARTS} lower parts are supported, got {lower_part_count}" ); for (idx, part) in lower_parts.enumerate() { vortex_ensure!( part.dtype().is_unsigned_int() && !part.dtype().is_nullable(), - "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", + MismatchedTypes: "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", part.dtype() ); - vortex_ensure_eq!(part.len(), len, "lower part {idx} length mismatch"); + vortex_ensure_eq!(part.len(), len, InvalidArgument: "lower part {idx} length mismatch"); } Ok(()) } @@ -211,18 +211,18 @@ impl VTable for DecimalByteParts { slots: &[Option], ) -> VortexResult<()> { let Some(decimal_dtype) = dtype.as_decimal_opt() else { - vortex_bail!("expected decimal dtype, got {}", dtype) + vortex_bail!(MismatchedTypes: "expected decimal dtype, got {}", dtype) }; let min_slots = DecimalBytePartsSlots::FIXED_COUNT; let max_slots = min_slots + MAX_LOWER_PARTS; vortex_ensure!( (min_slots..=max_slots).contains(&slots.len()), - "expected {min_slots}..={max_slots} slots, got {}", + InvalidArgument: "expected {min_slots}..={max_slots} slots, got {}", slots.len() ); for (idx, slot) in slots.iter().enumerate() { - vortex_ensure!(slot.is_some(), "missing required slot {idx}"); + vortex_ensure!(slot.is_some(), InvalidArgument: "missing required slot {idx}"); } let slots = DecimalBytePartsSlotsView::from_slots(slots); @@ -240,11 +240,11 @@ impl VTable for DecimalByteParts { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("DecimalBytePartsArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "DecimalBytePartsArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("DecimalBytePartsArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "DecimalBytePartsArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -259,7 +259,7 @@ impl VTable for DecimalByteParts { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!("DecimalByteParts serialization requires DecimalBytePartsPlugin") + vortex_bail!(Serde: "DecimalByteParts serialization requires DecimalBytePartsPlugin") } fn deserialize( @@ -271,7 +271,7 @@ impl VTable for DecimalByteParts { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("DecimalByteParts deserialization requires DecimalBytePartsPlugin") + vortex_bail!(Serde: "DecimalByteParts deserialization requires DecimalBytePartsPlugin") } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { @@ -392,7 +392,7 @@ impl OperationsVTable for DecimalByteParts { DecimalValue::I256(assemble_wide_decimal_value(msp, [*first, *second, *third])) } _ => vortex_bail!( - "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", + InvalidArgument: "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", lower_parts.len() ), }; diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs index df222241964..54982f7b252 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs @@ -52,7 +52,7 @@ pub fn assemble_decimal( ) -> VortexResult { vortex_ensure!( msp.dtype().is_signed_int(), - "MSP must have a signed integer dtype" + MismatchedTypes: "MSP must have a signed integer dtype" ); let validity = msp.validity()?; @@ -63,17 +63,17 @@ pub fn assemble_decimal( vortex_ensure!( lower_parts.len() <= MAX_LOWER_PARTS, - "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", + InvalidArgument: "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", lower_parts.len() ); let len = msp.len(); for (idx, part) in lower_parts.iter().enumerate() { vortex_ensure!( part.dtype().is_unsigned_int() && !part.dtype().is_nullable(), - "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", + MismatchedTypes: "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", part.dtype() ); - vortex_ensure_eq!(part.len(), len, "lower part {idx} length mismatch"); + vortex_ensure_eq!(part.len(), len, InvalidArgument: "lower part {idx} length mismatch"); } assemble_wide_decimal_from_arrays(msp, lower_parts, validity, decimal_dtype, exec_ctx) @@ -154,7 +154,9 @@ fn assemble_wide_decimal_from_arrays( validity, ) .into_array(), - _ => vortex_bail!("expected between one and {MAX_LOWER_PARTS} lower parts"), + _ => { + vortex_bail!(InvalidArgument: "expected between one and {MAX_LOWER_PARTS} lower parts") + } } })) } diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs index 3896cd51c96..e5e243546ce 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs @@ -66,7 +66,7 @@ impl ArrayPlugin for DecimalBytePartsPlugin { ) -> VortexResult> { let view = array.as_opt::().ok_or_else(|| { vortex_err!( - "DecimalByteParts plugin cannot serialize {}", + Serde: "DecimalByteParts plugin cannot serialize {}", array.encoding_id() ) })?; @@ -89,7 +89,7 @@ impl ArrayPlugin for DecimalBytePartsPlugin { v2::deserialize(parts)? } else { vortex_bail!( - "DecimalByteParts plugin does not recognize serialized ID {}", + Serde: "DecimalByteParts plugin does not recognize serialized ID {}", parts.serialized_id ) }; diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs index 99f3614e2a4..9bca0ca88c7 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs @@ -35,7 +35,7 @@ pub(super) fn serialize( ) -> VortexResult { vortex_ensure!( array.lower_parts().is_empty(), - "v1 must not carry lower parts" + Serde: "v1 must not carry lower parts" ); let msp = array.msp(); let metadata = DecimalBytePartsMetadata { @@ -55,23 +55,23 @@ pub(super) fn deserialize(parts: ArrayDeserialization<'_>) -> VortexResult) -> VortexResult>(len: usize, child: Child) -> Array } }; let FoRReferences::Blocked(references) = for_array.references() else { - vortex_panic!("every chunk has its own reference"); + vortex_panic!(AssertionFailed: "every chunk has its own reference"); }; FoR::try_new_chunked(packed.into_array(), references.clone(), 0) .unwrap() diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs index 4fbe91fedb9..77e503d70ea 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs @@ -343,7 +343,7 @@ mod tests { use vortex_array::assert_arrays_eq; use vortex_array::validity::Validity; use vortex_buffer::Buffer; - use vortex_error::VortexError; + use vortex_error::VortexErrorKind; use vortex_error::vortex_bail; use vortex_error::vortex_err; use vortex_session::VortexSession; @@ -366,7 +366,7 @@ mod tests { ctx: &mut ExecutionCtx, ) -> VortexResult { let BitWidthsView::Blocked(offsets) = array.bit_widths() else { - vortex_bail!("expected block offsets"); + vortex_bail!(AssertionFailed: "expected block offsets"); }; offsets.clone().execute::(ctx) } @@ -445,7 +445,7 @@ mod tests { let patches = array .patches() - .ok_or_else(|| vortex_err!("expected patches"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; assert_arrays_eq!( patches.indices().clone(), PrimitiveArray::from_iter([10u16, 20, 1029]), @@ -459,7 +459,7 @@ mod tests { let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!("expected chunk offsets"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? .clone(); assert_arrays_eq!( chunk_offsets, @@ -482,7 +482,7 @@ mod tests { assert_eq!(array.packed().len(), 0); let patches = array .patches() - .ok_or_else(|| vortex_err!("expected patches"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; assert_eq!(patches.num_patches(), 10); Ok(()) } @@ -496,7 +496,7 @@ mod tests { )?; let BitWidthsView::Blocked(offsets) = array.bit_widths() else { - vortex_bail!("expected block offsets"); + vortex_bail!(AssertionFailed: "expected block offsets"); }; assert!(offsets.is::()); assert_arrays_eq!( @@ -546,14 +546,18 @@ mod tests { #[case::float(PrimitiveArray::from_iter([1.0f32, 2.0]))] fn encode_blocked_rejects_invalid_values(#[case] array: PrimitiveArray) { let mut ctx = SESSION.create_execution_ctx(); - assert!(matches!( - bitpack_blocked_to_best_bit_widths(&array, &mut ctx).unwrap_err(), - VortexError::InvalidArgument(_, _) - )); - assert!(matches!( - BitPackedData::encode_blocked(&array.into_array(), &[1], &mut ctx).unwrap_err(), - VortexError::InvalidArgument(_, _) - )); + assert_eq!( + bitpack_blocked_to_best_bit_widths(&array, &mut ctx) + .unwrap_err() + .kind(), + VortexErrorKind::InvalidArgument + ); + assert_eq!( + BitPackedData::encode_blocked(&array.into_array(), &[1], &mut ctx) + .unwrap_err() + .kind(), + VortexErrorKind::InvalidArgument + ); } #[rstest] @@ -568,7 +572,7 @@ mod tests { &mut SESSION.create_execution_ctx(), ) .unwrap_err(); - assert!(matches!(err, VortexError::InvalidArgument(_, _))); + assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); } #[test] diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs index 53f16a0e06a..b3058f1122e 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs @@ -353,7 +353,7 @@ pub fn find_best_bit_width(ptype: PType, bit_width_freq: &[usize]) -> VortexResu )] fn best_bit_width(bit_width_freq: &[usize], bytes_per_exception: usize) -> VortexResult { if bit_width_freq.len() > u8::MAX as usize { - vortex_bail!("Too many bit widths"); + vortex_bail!(Overflow: "Too many bit widths"); } let len: usize = bit_width_freq.iter().sum(); @@ -434,7 +434,7 @@ mod test { use vortex_array::builders::ArrayBuilder; use vortex_array::builders::PrimitiveBuilder; use vortex_buffer::Buffer; - use vortex_error::VortexError; + use vortex_error::VortexErrorKind; use vortex_error::vortex_err; use vortex_session::VortexSession; @@ -494,7 +494,7 @@ mod test { let err = BitPackedData::encode(&array.into_array(), 1024u32.ilog2() as u8, &mut ctx) .unwrap_err(); - assert!(matches!(err, VortexError::InvalidArgument(_, _))); + assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); } #[test] @@ -536,11 +536,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!("expected patches"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!("expected chunk offsets"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? .clone(); // chunk 0 (0-1023): patches at 100, 200 -> starts at patch index 0 @@ -571,11 +571,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!("expected patches"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!("expected chunk offsets"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? .clone(); assert_arrays_eq!( @@ -602,11 +602,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!("expected patches"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!("expected chunk offsets"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? .clone(); // chunk 0 (0-1023): patches at 100, 200 -> starts at patch index 0 @@ -638,11 +638,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!("expected patches"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!("expected chunk offsets"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? .clone(); // Single chunk starting at patch index 0. diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs index 6dcb3177928..792ee5aa1f3 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs @@ -118,7 +118,7 @@ pub(crate) fn execute_block_offsets( let num_blocks = (array.len() + usize::from(array.offset())).div_ceil(FL_CHUNK_SIZE); vortex_ensure!( offsets.len() == num_blocks + 1, - "Expected {} block boundaries, got {}", + InvalidArgument: "Expected {} block boundaries, got {}", num_blocks + 1, offsets.len() ); @@ -221,7 +221,7 @@ pub fn unpack_single_blocked( let block = index_in_encoded / FL_CHUNK_SIZE; vortex_ensure!( block + 1 < offsets.len(), - "BitPacked index {index} has no block boundaries" + OutOfBounds: "BitPacked index {index} has no block boundaries" ); let (base, start, end) = if let Some(primitive) = offsets.as_opt::() && primitive.buffer_handle().is_on_host() @@ -457,7 +457,7 @@ mod tests { &mut ctx, )?; let BitWidthsView::Blocked(block_offsets) = array.bit_widths() else { - vortex_bail!("expected block offsets"); + vortex_bail!(AssertionFailed: "expected block offsets"); }; let array = BitPacked::try_new_with_block_offsets( array.packed().clone(), diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs index 3cdf080edec..685b3eaf80e 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs @@ -168,7 +168,7 @@ pub(crate) fn apply_patches_to_uninit_range, index: usize) -> VortexResult { let BitWidthsView::Global(bit_width) = array.bit_widths() else { - vortex_bail!("BitPacked array has per-block bit widths"); + vortex_bail!(NotImplemented: "BitPacked array has per-block bit widths"); }; let bit_width = bit_width as usize; let ptype = array.dtype().as_ptype(); diff --git a/encodings/fastlanes/src/bitpacking/array/mod.rs b/encodings/fastlanes/src/bitpacking/array/mod.rs index 323bee8c7d8..08c7cefb526 100644 --- a/encodings/fastlanes/src/bitpacking/array/mod.rs +++ b/encodings/fastlanes/src/bitpacking/array/mod.rs @@ -84,12 +84,12 @@ pub(crate) fn validate_block_offsets( ) -> VortexResult<()> { vortex_ensure!( offsets.dtype().is_unsigned_int() && !offsets.dtype().is_nullable(), - "Expected non-nullable unsigned integer block offsets, got {}", + MismatchedTypes: "Expected non-nullable unsigned integer block offsets, got {}", offsets.dtype() ); vortex_ensure!( offsets.len() == num_blocks + 1, - "Expected {} block boundaries, got {}", + InvalidArgument: "Expected {} block boundaries, got {}", num_blocks + 1, offsets.len() ); @@ -132,7 +132,7 @@ where }; vortex_ensure!( span == packed_len as u64, - "Block offsets span {span} bytes, but the packed buffer has {packed_len}" + InvalidArgument: "Block offsets span {span} bytes, but the packed buffer has {packed_len}" ); Ok(()) } @@ -151,22 +151,22 @@ fn block_range( ) -> VortexResult> { vortex_ensure!( base <= start, - "Block boundary {start} is below the first boundary {base}" + InvalidArgument: "Block boundary {start} is below the first boundary {base}" ); vortex_ensure!( start <= end, - "Block boundaries {start} and {end} are decreasing" + InvalidArgument: "Block boundaries {start} and {end} are decreasing" ); vortex_ensure!( end - base <= packed_len as u64, - "Block boundaries {start} and {end} are outside the packed buffer (base {base})" + InvalidArgument: "Block boundaries {start} and {end} are outside the packed buffer (base {base})" ); let size = end - start; vortex_ensure!( (start - base).is_multiple_of(128) && size.is_multiple_of(128) && size / 128 <= max_bit_width, - "Block boundaries {start} and {end} do not hold a supported bit width (at most {max_bit_width} bits)" + InvalidArgument: "Block boundaries {start} and {end} do not hold a supported bit width (at most {max_bit_width} bits)" ); // Both differences are at most `packed_len`, so they fit in `usize`. Ok((start - base) as usize..(end - base) as usize) @@ -288,10 +288,10 @@ impl BitPackedData { bit_width: u8, offset: u16, ) -> VortexResult { - vortex_ensure!(bit_width <= 64, "Unsupported bit width {bit_width}"); + vortex_ensure!(bit_width <= 64, InvalidArgument: "Unsupported bit width {bit_width}"); vortex_ensure!( offset < 1024, - "Offset must be less than the full block i.e., 1024, got {offset}" + InvalidArgument: "Offset must be less than the full block i.e., 1024, got {offset}" ); Ok(Self { @@ -310,7 +310,7 @@ impl BitPackedData { ) -> VortexResult { vortex_ensure!( offset < 1024, - "Offset must be less than the full block i.e., 1024, got {offset}" + InvalidArgument: "Offset must be less than the full block i.e., 1024, got {offset}" ); Ok(Self { @@ -330,13 +330,17 @@ impl BitPackedData { length: usize, offset: u16, ) -> VortexResult<()> { - vortex_ensure!(ptype.is_int(), MismatchedTypes: "integer", ptype); + vortex_ensure!( + ptype.is_int(), + MismatchedTypes: "expected type: integer but instead got {}", + ptype + ); if let Some(validity_len) = validity.maybe_len() { vortex_ensure_eq!( validity_len, length, - "BitPackedArray validity length must match array length" + InvalidArgument: "BitPackedArray validity length must match array length" ); } @@ -349,11 +353,11 @@ impl BitPackedData { if let Some(bit_width) = bit_width { vortex_ensure!( usize::from(bit_width) <= ptype.bit_width(), - "Unsupported bit width {bit_width} for {ptype}" + InvalidArgument: "Unsupported bit width {bit_width} for {ptype}" ); let expected_packed_len = (length + offset as usize).div_ceil(1024) * (128 * bit_width as usize); - vortex_ensure_eq!(packed.len(), expected_packed_len); + vortex_ensure_eq!(packed.len(), expected_packed_len, InvalidArgument); } Ok(()) @@ -363,7 +367,7 @@ impl BitPackedData { // Ensure that array and patches have same ptype vortex_ensure!( patches.dtype().eq_ignore_nullability(ptype.into()), - "Patches DType {} does not match BitPackedArray dtype {}", + MismatchedTypes: "Patches DType {} does not match BitPackedArray dtype {}", patches.dtype().as_nonnullable(), ptype ); @@ -371,7 +375,7 @@ impl BitPackedData { vortex_ensure_eq!( patches.array_len(), len, - "BitPackedArray patches length mismatch" + InvalidArgument: "BitPackedArray patches length mismatch" ); Ok(()) @@ -482,7 +486,7 @@ pub trait BitPackedArrayExt: BitPackedArraySlotsExt { (Some(bit_width), None) => BitWidthsView::Global(bit_width), (None, Some(block_offsets)) => BitWidthsView::Blocked(block_offsets), _ => vortex_panic!( - "BitPacked must have exactly one of a global bit width and block offsets" + AssertionFailed: "BitPacked must have exactly one of a global bit width and block offsets" ), } } diff --git a/encodings/fastlanes/src/bitpacking/array/tests.rs b/encodings/fastlanes/src/bitpacking/array/tests.rs index 94a29adff73..2a9d28ba8cb 100644 --- a/encodings/fastlanes/src/bitpacking/array/tests.rs +++ b/encodings/fastlanes/src/bitpacking/array/tests.rs @@ -374,7 +374,7 @@ fn into_parts_preserves_block_offsets(#[case] offsets: ArrayRef) -> VortexResult )?; let parts = BitPacked::into_parts(array); let BitWidths::Blocked(block_offsets) = parts.bit_widths else { - vortex_bail!("expected block offsets"); + vortex_bail!(AssertionFailed: "expected block offsets"); }; assert!(ArrayRef::ptr_eq(&offsets, &block_offsets)); let rebuilt = BitPacked::try_new_with_block_offsets( diff --git a/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs b/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs index e6993e83a62..e5e8f095ac7 100644 --- a/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs +++ b/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs @@ -110,7 +110,7 @@ impl<'a, T: BitPacked> BitUnpackedChunks<'a, T> { scratch: &'a mut [MaybeUninit; CHUNK_SIZE], ) -> VortexResult { let Some(bit_width) = array.global_bit_width else { - vortex_bail!("BitPacked array has per-block bit widths"); + vortex_bail!(NotImplemented: "BitPacked array has per-block bit widths"); }; Self::try_new_with_strategy( BitPackingStrategy, @@ -350,11 +350,11 @@ fn validate_packed( ) -> VortexResult<(usize, usize)> { vortex_ensure!( offset < CHUNK_SIZE, - "Invalid bit-packed offset {offset}, expected < {CHUNK_SIZE}" + InvalidArgument: "Invalid bit-packed offset {offset}, expected < {CHUNK_SIZE}" ); let elems_per_chunk = 128 * bit_width / size_of::(); let num_chunks = (offset + len).div_ceil(CHUNK_SIZE); - vortex_ensure_eq!(packed_len, num_chunks * elems_per_chunk); + vortex_ensure_eq!(packed_len, num_chunks * elems_per_chunk, InvalidArgument); Ok((num_chunks, (offset + len) % CHUNK_SIZE)) } diff --git a/encodings/fastlanes/src/bitpacking/compute/take.rs b/encodings/fastlanes/src/bitpacking/compute/take.rs index 345cbef80da..2ba7fdd33f6 100644 --- a/encodings/fastlanes/src/bitpacking/compute/take.rs +++ b/encodings/fastlanes/src/bitpacking/compute/take.rs @@ -184,14 +184,14 @@ fn collect_ranges( let length = usize::try_from(length)?; let end = start .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"))?; vortex_ensure!( end <= array_len, - "PiecewiseSequenceArray range exceeds array length" + OutOfBounds: "PiecewiseSequenceArray range exceeds array length" ); - total_len = total_len - .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + total_len = total_len.checked_add(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; ranges.push(start..end); } vortex_ensure_eq!(total_len, output_len); diff --git a/encodings/fastlanes/src/bitpacking/plugin/mod.rs b/encodings/fastlanes/src/bitpacking/plugin/mod.rs index 31b1f06ec90..648282d6f13 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/mod.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/mod.rs @@ -73,9 +73,9 @@ impl ArrayPlugin for BitPackedPlugin { array: &ArrayRef, _session: &VortexSession, ) -> VortexResult> { - let view = array.as_opt::().ok_or_else(|| { - vortex_err!("BitPacked plugin cannot serialize {}", array.encoding_id()) - })?; + let view = array.as_opt::().ok_or_else( + || vortex_err!(Serde: "BitPacked plugin cannot serialize {}", array.encoding_id()), + )?; let serialization = match view.bit_widths() { BitWidthsView::Global(bit_width) => v1::serialize(array, view, bit_width)?, BitWidthsView::Blocked(block_offsets) => v2::serialize(array, view, block_offsets)?, @@ -94,7 +94,7 @@ impl ArrayPlugin for BitPackedPlugin { v2::deserialize(parts, session) } else { vortex_bail!( - "BitPacked plugin does not recognize serialized ID {}", + Serde: "BitPacked plugin does not recognize serialized ID {}", parts.serialized_id ) } @@ -134,14 +134,14 @@ impl ArrayPlugin for BitPackedPatchedPlugin { ) -> VortexResult { vortex_ensure!( self.serialized_ids().contains(&parts.serialized_id), - "BitPacked plugin does not recognize serialized ID {}", + Serde: "BitPacked plugin does not recognize serialized ID {}", parts.serialized_id, ); let bitpacked: BitPackedArray = BitPackedPlugin .deserialize(parts, session)? .try_downcast() .map_err(|_| { - vortex_err!("BitPacked plugin should only deserialize fastlanes.bitpacked") + vortex_err!(Serde: "BitPacked plugin should only deserialize fastlanes.bitpacked") })?; // Create a new BitPackedArray without the interior patches installed. diff --git a/encodings/fastlanes/src/bitpacking/plugin/tests.rs b/encodings/fastlanes/src/bitpacking/plugin/tests.rs index 127695c6d26..d42840cd6a0 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/tests.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/tests.rs @@ -92,13 +92,11 @@ fn test_decode_bitpacked_patches() -> VortexResult<()> { let patched: PatchedArray = deserialized .try_downcast() - .map_err(|a| vortex_err!("Expected Patched, got {}", a.encoding_id()))?; + .map_err(|a| vortex_err!(MismatchedTypes: "Expected Patched, got {}", a.encoding_id()))?; - let inner_bitpacked: BitPackedArray = patched - .inner() - .clone() - .try_downcast() - .map_err(|a| vortex_err!("Expected inner BitPacked, got {}", a.encoding_id()))?; + let inner_bitpacked: BitPackedArray = patched.inner().clone().try_downcast().map_err( + |a| vortex_err!(MismatchedTypes: "Expected inner BitPacked, got {}", a.encoding_id()), + )?; assert!( inner_bitpacked.patches().is_none(), @@ -145,9 +143,9 @@ fn bitpacked_without_patches_stays_bitpacked() -> VortexResult<()> { assert_arrays_eq!(deserialized, parray, &mut ctx); - let result = deserialized - .try_downcast::() - .map_err(|a| vortex_err!("Expected deserialize BitPacked, got {}", a.encoding_id()))?; + let result = deserialized.try_downcast::().map_err( + |a| vortex_err!(Serde: "Expected deserialize BitPacked, got {}", a.encoding_id()), + )?; assert!(result.patches().is_none(), "Result should not have patches"); @@ -228,7 +226,7 @@ fn serde_roundtrip( let view = array.as_::(); let serialization = PLUGIN_SESSION .array_serialize(&array)? - .ok_or_else(|| vortex_err!("BitPacked must serialize"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "BitPacked must serialize"))?; assert_eq!(serialization.serialized_id, bitpacked_v1_id()); let metadata = BitPackedMetadata::decode(serialization.metadata.as_slice())?; assert_eq!(metadata.bit_width, u32::from(bit_width)); @@ -275,11 +273,11 @@ fn v2_roundtrip( None => bitpack_blocked_to_best_bit_widths(&values, &mut ctx)?, }; let BitWidthsView::Blocked(block_offsets) = array.bit_widths() else { - vortex_bail!("expected block offsets"); + vortex_bail!(AssertionFailed: "expected block offsets"); }; let serialization = PLUGIN_SESSION .array_serialize(array.as_array())? - .ok_or_else(|| vortex_err!("BitPacked must serialize"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "BitPacked must serialize"))?; assert_eq!(serialization.serialized_id, bitpacked_v2_id()); let metadata = BitPackedV2Metadata::decode(serialization.metadata.as_slice())?; assert_eq!(metadata.offset, 0); @@ -302,7 +300,7 @@ fn v2_roundtrip_offset_and_nonzero_base() -> VortexResult<()> { let values = drifting(); let encoded = bitpack_blocked_to_best_bit_widths(&values, &mut ctx)?; let BitWidthsView::Blocked(block_offsets) = encoded.bit_widths() else { - vortex_bail!("expected block offsets"); + vortex_bail!(AssertionFailed: "expected block offsets"); }; let block_offsets = block_offsets .cast(DType::Primitive(PType::U64, Nullability::NonNullable))? @@ -322,7 +320,7 @@ fn v2_roundtrip_offset_and_nonzero_base() -> VortexResult<()> { let serialization = PLUGIN_SESSION .array_serialize(&array)? - .ok_or_else(|| vortex_err!("BitPacked must serialize"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "BitPacked must serialize"))?; assert_eq!( BitPackedV2Metadata::decode(serialization.metadata.as_slice())?.offset, 17 @@ -342,7 +340,7 @@ fn v2_rejects_malformed_parts() -> VortexResult<()> { &mut PLUGIN_SESSION.create_execution_ctx(), )?; let BitWidthsView::Blocked(block_offsets) = array.bit_widths() else { - vortex_bail!("expected block offsets"); + vortex_bail!(AssertionFailed: "expected block offsets"); }; let metadata = BitPackedV2Metadata { offset: 0, @@ -412,12 +410,10 @@ fn test_decode_blocked_bitpacked_patches() -> VortexResult<()> { let patched: PatchedArray = deserialized .try_downcast() - .map_err(|a| vortex_err!("Expected Patched, got {}", a.encoding_id()))?; - let inner_bitpacked: BitPackedArray = patched - .inner() - .clone() - .try_downcast() - .map_err(|a| vortex_err!("Expected inner BitPacked, got {}", a.encoding_id()))?; + .map_err(|a| vortex_err!(MismatchedTypes: "Expected Patched, got {}", a.encoding_id()))?; + let inner_bitpacked: BitPackedArray = patched.inner().clone().try_downcast().map_err( + |a| vortex_err!(MismatchedTypes: "Expected inner BitPacked, got {}", a.encoding_id()), + )?; assert!(inner_bitpacked.patches().is_none()); assert!(!inner_bitpacked.bit_widths().is_global()); assert_arrays_eq!(patched, values, &mut ctx); diff --git a/encodings/fastlanes/src/bitpacking/plugin/v1.rs b/encodings/fastlanes/src/bitpacking/plugin/v1.rs index 78da347f2c5..2ed8229e2cb 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/v1.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/v1.rs @@ -75,7 +75,7 @@ pub(super) fn deserialize( let metadata = BitPackedMetadata::decode(metadata)?; if buffers.len() != 1 { - vortex_bail!("Expected 1 buffer, got {}", buffers.len()); + vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); } let packed = buffers[0].clone(); @@ -87,7 +87,7 @@ pub(super) fn deserialize( Ok(Validity::Array(validity)) } else { vortex_bail!( - "Expected {} or {} children, got {}", + InvalidArgument: "Expected {} or {} children, got {}", child_idx, child_idx + 1, children.len() @@ -136,13 +136,13 @@ pub(super) fn deserialize( patches, u8::try_from(metadata.bit_width).map_err(|_| { vortex_err!( - "BitPackedMetadata bit_width {} does not fit in u8", + Overflow: "BitPackedMetadata bit_width {} does not fit in u8", metadata.bit_width ) })?, u16::try_from(metadata.offset).map_err(|_| { vortex_err!( - "BitPackedMetadata offset {} does not fit in u16", + Overflow: "BitPackedMetadata offset {} does not fit in u16", metadata.offset ) })?, diff --git a/encodings/fastlanes/src/bitpacking/plugin/v2.rs b/encodings/fastlanes/src/bitpacking/plugin/v2.rs index 388e4b1241f..46702fd8273 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/v2.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/v2.rs @@ -86,12 +86,12 @@ pub(super) fn deserialize( let metadata = BitPackedV2Metadata::decode(metadata)?; vortex_ensure!( buffers.len() == 1, - "Expected 1 buffer, got {}", + InvalidArgument: "Expected 1 buffer, got {}", buffers.len() ); vortex_ensure!( usize::try_from(metadata.offset).is_ok_and(|offset| offset < FL_CHUNK_SIZE), - "BitPacked offset must be less than {FL_CHUNK_SIZE}, got {}", + InvalidArgument: "BitPacked offset must be less than {FL_CHUNK_SIZE}, got {}", metadata.offset ); let offset = u16::try_from(metadata.offset)?; @@ -108,7 +108,7 @@ pub(super) fn deserialize( Validity::Array(children.get(num_patch_children, &Validity::DTYPE, len)?) } else { vortex_bail!( - "Expected {} or {} children, got {}", + InvalidArgument: "Expected {} or {} children, got {}", num_patch_children + 1, num_patch_children + 2, children.len() diff --git a/encodings/fastlanes/src/bitpacking/vtable/mod.rs b/encodings/fastlanes/src/bitpacking/vtable/mod.rs index e92b1d040a2..72493720543 100644 --- a/encodings/fastlanes/src/bitpacking/vtable/mod.rs +++ b/encodings/fastlanes/src/bitpacking/vtable/mod.rs @@ -113,7 +113,7 @@ impl VTable for BitPacked { data.packed.len(), )?, _ => { - vortex_bail!("BitPacked needs exactly one of a global bit width and block offsets") + vortex_bail!(InvalidArgument: "BitPacked needs exactly one of a global bit width and block offsets") } } @@ -138,7 +138,7 @@ impl VTable for BitPacked { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.packed().clone(), - _ => vortex_panic!("BitPackedArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "BitPackedArray buffer index {idx} out of bounds"), } } @@ -154,7 +154,7 @@ impl VTable for BitPacked { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1); + vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); let mut data = array.data().clone(); data.packed = buffers[0].clone(); Ok(ArrayParts::new( @@ -170,7 +170,7 @@ impl VTable for BitPacked { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!("BitPacked serialization requires BitPackedPlugin") + vortex_bail!(Serde: "BitPacked serialization requires BitPackedPlugin") } fn deserialize( @@ -182,7 +182,7 @@ impl VTable for BitPacked { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("BitPacked deserialization requires BitPackedPlugin") + vortex_bail!(Serde: "BitPacked deserialization requires BitPackedPlugin") } fn append_to_builder( diff --git a/encodings/fastlanes/src/delta/array/mod.rs b/encodings/fastlanes/src/delta/array/mod.rs index 271a74d5343..09377d81288 100644 --- a/encodings/fastlanes/src/delta/array/mod.rs +++ b/encodings/fastlanes/src/delta/array/mod.rs @@ -109,7 +109,7 @@ impl> DeltaArrayExt for T {} impl DeltaData { pub fn try_new(offset: usize) -> VortexResult { - vortex_ensure!(offset < 1024, "offset must be less than 1024: {offset}"); + vortex_ensure!(offset < 1024, InvalidArgument: "offset must be less than 1024: {offset}"); Ok(Self { offset }) } } diff --git a/encodings/fastlanes/src/delta/compute/cast.rs b/encodings/fastlanes/src/delta/compute/cast.rs index 4342fd883bd..d24d97fa017 100644 --- a/encodings/fastlanes/src/delta/compute/cast.rs +++ b/encodings/fastlanes/src/delta/compute/cast.rs @@ -135,9 +135,9 @@ mod tests { casted.dtype(), &DType::Primitive(PType::U32, Nullability::Nullable) ); - let reduced = casted - .as_opt::() - .ok_or_else(|| vortex_err!("expected nullability cast to preserve Delta"))?; + let reduced = casted.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "expected nullability cast to preserve Delta"), + )?; assert!(!reduced.deltas().dtype().is_nullable()); assert!(!reduced.bases().dtype().is_nullable()); assert_arrays_eq!( diff --git a/encodings/fastlanes/src/delta/tests.rs b/encodings/fastlanes/src/delta/tests.rs index 37bc80e8e00..563aeea92be 100644 --- a/encodings/fastlanes/src/delta/tests.rs +++ b/encodings/fastlanes/src/delta/tests.rs @@ -135,7 +135,7 @@ fn delta_null_patterns(#[case] pattern: usize) -> VortexResult<()> { )?; let restored_delta = restored .as_opt::() - .ok_or_else(|| vortex_err!("expected deserialized Delta"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "expected deserialized Delta"))?; assert!(!restored_delta.deltas().dtype().is_nullable()); assert_arrays_eq!(restored, source, &mut ctx); } diff --git a/encodings/fastlanes/src/delta/vtable/mod.rs b/encodings/fastlanes/src/delta/vtable/mod.rs index cdd4cef18c4..32eb7d11b5c 100644 --- a/encodings/fastlanes/src/delta/vtable/mod.rs +++ b/encodings/fastlanes/src/delta/vtable/mod.rs @@ -105,7 +105,7 @@ impl VTable for Delta { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("DeltaArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "DeltaArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -156,23 +156,24 @@ impl VTable for Delta { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - "DeltaArray expects 0 buffers, got {}", + InvalidArgument: "DeltaArray expects 0 buffers, got {}", buffers.len() ); vortex_ensure!( children.len() == 2 || children.len() == 3, - "DeltaArray expects 2 or 3 children, got {}", + InvalidArgument: "DeltaArray expects 2 or 3 children, got {}", children.len() ); let metadata = DeltaMetadata::decode(metadata)?; let ptype = PType::try_from(dtype)?; let lanes = lane_count(ptype); - let deltas_len = usize::try_from(metadata.deltas_len) - .map_err(|_| vortex_err!("deltas_len {} overflowed usize", metadata.deltas_len))?; + let deltas_len = usize::try_from(metadata.deltas_len).map_err( + |_| vortex_err!(Overflow: "deltas_len {} overflowed usize", metadata.deltas_len), + )?; vortex_ensure!( deltas_len.is_multiple_of(FL_CHUNK_SIZE), - "deltas length must be a multiple of {FL_CHUNK_SIZE}" + Serde: "deltas length must be a multiple of {FL_CHUNK_SIZE}" ); let bases_len = deltas_len / FL_CHUNK_SIZE * lanes; @@ -257,42 +258,42 @@ fn validate_parts( ) -> VortexResult<()> { vortex_ensure!( offset <= deltas.len() && len <= deltas.len() - offset, - "offset + len, {offset} + {len}, must be less than or equal to the size of deltas: {}", + InvalidArgument: "offset + len, {offset} + {len}, must be less than or equal to the size of deltas: {}", deltas.len() ); vortex_ensure!( !bases.dtype().is_nullable() && !deltas.dtype().is_nullable(), - "DeltaArray: bases and deltas must be nonnullable" + MismatchedTypes: "DeltaArray: bases and deltas must be nonnullable" ); vortex_ensure!( bases.dtype() == deltas.dtype(), - "DeltaArray: bases and deltas must have the same dtype, got {} and {}", + MismatchedTypes: "DeltaArray: bases and deltas must have the same dtype, got {} and {}", bases.dtype(), deltas.dtype() ); vortex_ensure!( bases.dtype().is_int(), - "DeltaArray: dtype must be an integer, got {}", + MismatchedTypes: "DeltaArray: dtype must be an integer, got {}", bases.dtype() ); let expected_dtype = bases.dtype().with_nullability(dtype.nullability()); - vortex_ensure_eq!(dtype, &expected_dtype, "DeltaArray dtype mismatch"); + vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes: "DeltaArray dtype mismatch"); if let Some(validity) = validity_child { vortex_ensure!( dtype.is_nullable(), - "DeltaArray: validity requires a nullable dtype" + MismatchedTypes: "DeltaArray: validity requires a nullable dtype" ); vortex_ensure_eq!( validity.dtype(), &Validity::DTYPE, - "DeltaArray: validity must be nonnullable bool" + MismatchedTypes: "DeltaArray: validity must be nonnullable bool" ); vortex_ensure_eq!( validity.len(), len, - "DeltaArray: validity length must equal logical length" + InvalidArgument: "DeltaArray: validity length must equal logical length" ); } @@ -300,12 +301,12 @@ fn validate_parts( vortex_ensure!( deltas.len().is_multiple_of(1024), - "deltas length ({}) must be a multiple of 1024", + InvalidArgument: "deltas length ({}) must be a multiple of 1024", deltas.len(), ); vortex_ensure!( bases.len() == deltas.len() / FL_CHUNK_SIZE * lanes, - "bases length ({}) must equal the number of chunks times LANES ({lanes})", + InvalidArgument: "bases length ({}) must equal the number of chunks times LANES ({lanes})", bases.len(), ); Ok(()) diff --git a/encodings/fastlanes/src/delta/vtable/validity.rs b/encodings/fastlanes/src/delta/vtable/validity.rs index 3133e07cdf2..b56b14ec35c 100644 --- a/encodings/fastlanes/src/delta/vtable/validity.rs +++ b/encodings/fastlanes/src/delta/vtable/validity.rs @@ -87,7 +87,7 @@ mod tests { let sliced = delta.slice(range.clone())?; let Validity::Array(validity) = sliced.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(range.clone()), &mut ctx); assert_arrays_eq!(sliced, primitive.slice(range)?, &mut ctx); @@ -102,7 +102,7 @@ mod tests { let sliced = delta.slice(100..2400)?.slice(900..1500)?; let Validity::Array(validity) = sliced.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(1000..1600), &mut ctx); assert_arrays_eq!(sliced, primitive.slice(1000..1600)?, &mut ctx); @@ -118,7 +118,7 @@ mod tests { let (bases, deltas) = delta_compress(&primitive, &mut ctx)?; let Validity::Array(validity) = primitive.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; let lazy_validity = SliceArray::try_new(validity, 0..primitive.len())?.into_array(); let delta = Delta::try_new( @@ -130,7 +130,7 @@ mod tests { )?; let Validity::Array(validity) = delta.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; assert_arrays_eq!( validity, @@ -148,7 +148,7 @@ mod tests { let (bases, deltas) = delta_compress(&primitive, &mut ctx)?; let Validity::Array(validity) = primitive.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; let bits = validity.execute::(&mut ctx)?.into_bit_buffer(); let unaligned = BoolArray::new(misalign_bits(bits), Validity::NonNullable).into_array(); @@ -161,14 +161,14 @@ mod tests { )?; let Validity::Array(validity) = delta.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(0..LEN), &mut ctx); assert_arrays_eq!(delta, primitive, &mut ctx); let sliced = delta.slice(1000..1050)?; let Validity::Array(sliced_validity) = sliced.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; assert_arrays_eq!(sliced_validity, expected_validity(1000..1050), &mut ctx); Ok(()) @@ -185,7 +185,7 @@ mod tests { let delta = Delta::try_from_primitive_array(&primitive, &mut ctx)?; let Validity::Array(validity) = delta.validity()? else { - vortex_bail!("expected array-backed validity") + vortex_bail!(MismatchedTypes: "expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(0..len as usize), &mut ctx); assert_arrays_eq!(delta, primitive, &mut ctx); diff --git a/encodings/fastlanes/src/for_/array/for_compress.rs b/encodings/fastlanes/src/for_/array/for_compress.rs index cd854bab5fa..a8f26f2fdc5 100644 --- a/encodings/fastlanes/src/for_/array/for_compress.rs +++ b/encodings/fastlanes/src/for_/array/for_compress.rs @@ -39,7 +39,7 @@ impl FoRData { let min = array_ref .statistics() .compute_stat(Stat::Min, ctx)? - .ok_or_else(|| vortex_err!("Min stat not found"))?; + .ok_or_else(|| vortex_err!(NotFound: "Min stat not found"))?; let encoded = match_each_integer_ptype!(array.ptype(), |T| { encode_primitive::(array, T::try_from(&min)?, ctx)?.into_array() diff --git a/encodings/fastlanes/src/for_/array/for_decompress.rs b/encodings/fastlanes/src/for_/array/for_decompress.rs index 30aed5808b9..7a41f0457a3 100644 --- a/encodings/fastlanes/src/for_/array/for_decompress.rs +++ b/encodings/fastlanes/src/for_/array/for_decompress.rs @@ -86,7 +86,7 @@ fn fused_decompress_typed< ctx: &mut ExecutionCtx, ) -> VortexResult { let FoRReferences::Global(reference) = for_.references() else { - vortex_bail!("fused FoR decompression requires a global reference"); + vortex_bail!(NotImplemented: "fused FoR decompression requires a global reference"); }; let ref_ = reference .as_primitive() diff --git a/encodings/fastlanes/src/for_/array/mod.rs b/encodings/fastlanes/src/for_/array/mod.rs index 4d99943ae9a..f2f30fadbf2 100644 --- a/encodings/fastlanes/src/for_/array/mod.rs +++ b/encodings/fastlanes/src/for_/array/mod.rs @@ -67,7 +67,9 @@ pub trait FoRArrayExt: FoRArraySlotsExt { match (&self.global_reference, self.blocked_references()) { (Some(reference), None) => FoRReferences::Global(reference), (None, Some(references)) => FoRReferences::Blocked(references), - _ => vortex_panic!("FoR array must have either a global or blocked references"), + _ => { + vortex_panic!(AssertionFailed: "FoR array must have either a global or blocked references") + } } } @@ -98,11 +100,11 @@ impl FoRData { pub(crate) fn try_new(offset: u16, global_reference: Option) -> VortexResult { vortex_ensure!( usize::from(offset) < FL_CHUNK_SIZE, - "FoR offset must be less than {FL_CHUNK_SIZE}, got {offset}" + InvalidArgument: "FoR offset must be less than {FL_CHUNK_SIZE}, got {offset}" ); vortex_ensure!( offset == 0 || global_reference.is_none(), - "FoR with a global reference must have offset 0, got {offset}" + InvalidArgument: "FoR with a global reference must have offset 0, got {offset}" ); Ok(Self { offset, diff --git a/encodings/fastlanes/src/for_/plugin/mod.rs b/encodings/fastlanes/src/for_/plugin/mod.rs index a5478428072..7ab1d13cadc 100644 --- a/encodings/fastlanes/src/for_/plugin/mod.rs +++ b/encodings/fastlanes/src/for_/plugin/mod.rs @@ -61,9 +61,9 @@ impl ArrayPlugin for FoRPlugin { array: &ArrayRef, _session: &VortexSession, ) -> VortexResult> { - let view = array - .as_opt::() - .ok_or_else(|| vortex_err!("FoR plugin cannot serialize {}", array.encoding_id()))?; + let view = array.as_opt::().ok_or_else( + || vortex_err!(Serde: "FoR plugin cannot serialize {}", array.encoding_id()), + )?; Ok(Some(match view.references() { FoRReferences::Global(reference) => v1::serialize(view, reference), FoRReferences::Blocked(references) => v2::serialize(view, references), @@ -81,7 +81,7 @@ impl ArrayPlugin for FoRPlugin { v2::deserialize(parts) } else { vortex_bail!( - "FoR plugin does not recognize serialized ID {}", + Serde: "FoR plugin does not recognize serialized ID {}", parts.serialized_id ) } diff --git a/encodings/fastlanes/src/for_/plugin/tests.rs b/encodings/fastlanes/src/for_/plugin/tests.rs index 16278e070df..5d98fd5fcca 100644 --- a/encodings/fastlanes/src/for_/plugin/tests.rs +++ b/encodings/fastlanes/src/for_/plugin/tests.rs @@ -55,7 +55,7 @@ fn serde_roundtrip(#[case] array: VortexResult) -> VortexResult<()> { let array = array?; let serialization = SESSION .array_serialize(array.as_array())? - .ok_or_else(|| vortex_err!("FoR must serialize"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "FoR must serialize"))?; assert_eq!(serialization.serialized_id, for_v1_id()); assert_eq!( serialization.metadata, @@ -84,7 +84,7 @@ fn v2_roundtrip(#[case] range: std::ops::Range) -> VortexResult<()> { let array = chunked()?.into_array().slice(range.clone())?; let serialization = SESSION .array_serialize(&array)? - .ok_or_else(|| vortex_err!("FoR must serialize"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "FoR must serialize"))?; assert_eq!(serialization.serialized_id, for_v2_id()); assert_eq!( v2::FoRV2Metadata::decode(serialization.metadata.as_slice())?.offset, diff --git a/encodings/fastlanes/src/for_/plugin/v1.rs b/encodings/fastlanes/src/for_/plugin/v1.rs index 11a862cfc33..9dfdf7acb02 100644 --- a/encodings/fastlanes/src/for_/plugin/v1.rs +++ b/encodings/fastlanes/src/for_/plugin/v1.rs @@ -31,12 +31,12 @@ pub(super) fn deserialize( ) -> VortexResult { vortex_ensure!( parts.buffers.is_empty(), - "FoRArray expects 0 buffers, got {}", + InvalidArgument: "FoRArray expects 0 buffers, got {}", parts.buffers.len() ); if parts.children.len() != 1 { vortex_bail!( - "Expected 1 child for FoR encoding, found {}", + InvalidArgument: "Expected 1 child for FoR encoding, found {}", parts.children.len() ) } diff --git a/encodings/fastlanes/src/for_/plugin/v2.rs b/encodings/fastlanes/src/for_/plugin/v2.rs index 04cce287eab..c0d911eb54d 100644 --- a/encodings/fastlanes/src/for_/plugin/v2.rs +++ b/encodings/fastlanes/src/for_/plugin/v2.rs @@ -43,19 +43,19 @@ pub(super) fn serialize(array: ArrayView<'_, FoR>, references: &ArrayRef) -> Arr pub(super) fn deserialize(parts: ArrayDeserialization<'_>) -> VortexResult { vortex_ensure!( parts.buffers.is_empty(), - "FoRArray expects 0 buffers, got {}", + InvalidArgument: "FoRArray expects 0 buffers, got {}", parts.buffers.len() ); vortex_ensure_eq!( parts.children.len(), 2, - "Expected 2 children for {}", + Serde: "Expected 2 children for {}", for_v2_id() ); let metadata = FoRV2Metadata::decode(parts.metadata)?; vortex_ensure!( usize::try_from(metadata.offset).is_ok_and(|offset| offset < FL_CHUNK_SIZE), - "FoR offset must be less than {FL_CHUNK_SIZE}, got {}", + Serde: "FoR offset must be less than {FL_CHUNK_SIZE}, got {}", metadata.offset ); let offset = u16::try_from(metadata.offset)?; diff --git a/encodings/fastlanes/src/for_/tests.rs b/encodings/fastlanes/src/for_/tests.rs index 63116924f5e..8e6704e149d 100644 --- a/encodings/fastlanes/src/for_/tests.rs +++ b/encodings/fastlanes/src/for_/tests.rs @@ -48,14 +48,14 @@ static SESSION: LazyLock = LazyLock::new(|| { pub(crate) fn global(array: &FoRArray) -> VortexResult { match array.references() { FoRReferences::Global(reference) => Ok(reference.clone()), - FoRReferences::Blocked(_) => vortex_bail!("expected a global reference"), + FoRReferences::Blocked(_) => vortex_bail!(AssertionFailed: "expected a global reference"), } } /// The blocked references of `array`. pub(crate) fn blocked(array: &FoRArray) -> VortexResult { match array.references() { - FoRReferences::Global(_) => vortex_bail!("expected blocked references"), + FoRReferences::Global(_) => vortex_bail!(AssertionFailed: "expected blocked references"), FoRReferences::Blocked(references) => Ok(references.clone()), } } diff --git a/encodings/fastlanes/src/for_/vtable/mod.rs b/encodings/fastlanes/src/for_/vtable/mod.rs index ba2c353dec2..1b3610c635a 100644 --- a/encodings/fastlanes/src/for_/vtable/mod.rs +++ b/encodings/fastlanes/src/for_/vtable/mod.rs @@ -95,10 +95,10 @@ impl VTable for FoR { (Some(reference), None) => FoRReferences::Global(reference), (None, Some(references)) => FoRReferences::Blocked(references), (Some(_), Some(_)) => { - vortex_bail!("FoR cannot have both a global reference and blocked references") + vortex_bail!(InvalidArgument: "FoR cannot have both a global reference and blocked references") } (None, None) => { - vortex_bail!("FoR needs either a global reference or blocked references") + vortex_bail!(InvalidArgument: "FoR needs either a global reference or blocked references") } }; validate_parts(slots.encoded, references, data.offset, dtype, len) @@ -109,7 +109,7 @@ impl VTable for FoR { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("FoRArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "FoRArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -132,7 +132,7 @@ impl VTable for FoR { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!("FoR serialization requires FoRPlugin") + vortex_bail!(Serde: "FoR serialization requires FoRPlugin") } fn deserialize( @@ -144,7 +144,7 @@ impl VTable for FoR { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("FoR deserialization requires FoRPlugin") + vortex_bail!(Serde: "FoR deserialization requires FoRPlugin") } fn reduce_parent( @@ -182,7 +182,7 @@ pub struct FoR; impl FoR { /// Construct a FoR array with one global reference. pub fn try_new(encoded: ArrayRef, reference: Scalar) -> VortexResult { - vortex_ensure!(!reference.is_null(), "Reference value cannot be null"); + vortex_ensure!(!reference.is_null(), InvalidArgument: "Reference value cannot be null"); let dtype = reference .dtype() .with_nullability(encoded.dtype().nullability()); @@ -204,7 +204,7 @@ impl FoR { vortex_ensure_eq!( references.len(), num_chunks(offset, encoded.len()), - "FoR expects one reference per chunk" + InvalidArgument: "FoR expects one reference per chunk" ); return Self::try_new(encoded, reference); } @@ -242,29 +242,29 @@ fn validate_parts( dtype: &DType, len: usize, ) -> VortexResult<()> { - vortex_ensure!(dtype.is_int(), "FoR requires an integer dtype, got {dtype}"); - vortex_ensure_eq!(encoded.dtype(), dtype, "FoR encoded dtype mismatch"); - vortex_ensure_eq!(encoded.len(), len, "FoR encoded length mismatch"); + vortex_ensure!(dtype.is_int(), MismatchedTypes: "FoR requires an integer dtype, got {dtype}"); + vortex_ensure_eq!(encoded.dtype(), dtype, MismatchedTypes: "FoR encoded dtype mismatch"); + vortex_ensure_eq!(encoded.len(), len, InvalidArgument: "FoR encoded length mismatch"); let references_dtype = dtype.as_nonnullable(); match references { FoRReferences::Global(reference) => { - vortex_ensure!(!reference.is_null(), "FoR global reference cannot be null"); + vortex_ensure!(!reference.is_null(), InvalidArgument: "FoR global reference cannot be null"); vortex_ensure_eq!( reference.dtype(), &references_dtype, - "FoR global reference dtype mismatch" + MismatchedTypes: "FoR global reference dtype mismatch" ); } FoRReferences::Blocked(references) => { vortex_ensure_eq!( references.dtype(), &references_dtype, - "FoR references dtype mismatch" + MismatchedTypes: "FoR references dtype mismatch" ); vortex_ensure_eq!( references.len(), num_chunks(offset, len), - "FoR expects one reference per chunk" + InvalidArgument: "FoR expects one reference per chunk" ); } } diff --git a/encodings/fastlanes/src/for_/vtable/operations.rs b/encodings/fastlanes/src/for_/vtable/operations.rs index afe60caf930..d9f75d48ec2 100644 --- a/encodings/fastlanes/src/for_/vtable/operations.rs +++ b/encodings/fastlanes/src/for_/vtable/operations.rs @@ -27,7 +27,7 @@ impl OperationsVTable for FoR { let array = state.array(); let encoded_pvalue = state .slot(FoRSlots::ENCODED)? - .ok_or_else(|| vortex_err!("FoR encoded slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "FoR encoded slot is missing"))? .execute_scalar(index, ctx)?; let encoded_pvalue = encoded_pvalue.as_primitive(); let reference = match array.references() { @@ -36,7 +36,9 @@ impl OperationsVTable for FoR { let chunk = (usize::from(array.offset()) + index) / FL_CHUNK_SIZE; state .slot(FoRSlots::BLOCKED_REFERENCES)? - .ok_or_else(|| vortex_err!("FoR blocked references slot is missing"))? + .ok_or_else( + || vortex_err!(AssertionFailed: "FoR blocked references slot is missing"), + )? .execute_scalar(chunk, ctx)? } }; diff --git a/encodings/fastlanes/src/rle/array/mod.rs b/encodings/fastlanes/src/rle/array/mod.rs index 626d2fadd1d..0e19783314e 100644 --- a/encodings/fastlanes/src/rle/array/mod.rs +++ b/encodings/fastlanes/src/rle/array/mod.rs @@ -60,7 +60,7 @@ impl RLEData { pub fn try_new(offset: usize) -> VortexResult { vortex_ensure!( offset < 1024, - "Offset must be smaller than 1024, got {}", + InvalidArgument: "Offset must be smaller than 1024, got {}", offset ); Ok(Self { offset }) diff --git a/encodings/fastlanes/src/rle/array/rle_decompress.rs b/encodings/fastlanes/src/rle/array/rle_decompress.rs index 0c841b7cba6..065e53aea2d 100644 --- a/encodings/fastlanes/src/rle/array/rle_decompress.rs +++ b/encodings/fastlanes/src/rle/array/rle_decompress.rs @@ -43,7 +43,7 @@ pub fn rle_decompress(array: &RLEArray, ctx: &mut ExecutionCtx) -> VortexResult< PType::U8 => rle_decode_typed::(array, &values_idx_offsets, ctx), PType::U16 => rle_decode_typed::(array, &values_idx_offsets, ctx), _ => vortex_panic!( - "Unsupported index type for RLE decoding: {}", + AssertionFailed: "Unsupported index type for RLE decoding: {}", array.indices().dtype().as_ptype() ), } @@ -68,12 +68,12 @@ where // offsets must be non-decreasing and span at most `values.len()` values. vortex_ensure!( values_idx_offsets.is_sorted(), - "RLE values_idx_offsets must be non-decreasing" + InvalidArgument: "RLE values_idx_offsets must be non-decreasing" ); if let (Some(&first), Some(&last)) = (values_idx_offsets.first(), values_idx_offsets.last()) { vortex_ensure!( last - first <= values.len() as u64, - "RLE values_idx_offsets span {} values but only {} are present", + InvalidArgument: "RLE values_idx_offsets span {} values but only {} are present", last - first, values.len() ); @@ -110,7 +110,7 @@ where .vortex_expect("There can be at most 1024 values in RLE chunk"); vortex_ensure!( num_chunk_values > 0, - "RLE chunk {chunk_idx} references no values" + InvalidArgument: "RLE chunk {chunk_idx} references no values" ); // SAFETY: `MaybeUninit` and `T` have the same layout. @@ -201,7 +201,7 @@ where .unwrap_or_default(); vortex_ensure!( max_index < num_chunk_values as usize, - "RLE index {max_index} out of bounds for chunk {chunk_idx} with {num_chunk_values} values" + OutOfBounds: "RLE index {max_index} out of bounds for chunk {chunk_idx} with {num_chunk_values} values" ); // SAFETY: just checked that every index in the chunk is below `num_chunk_values`, // which the caller's offset validation bounds by `chunk_values.len()`. diff --git a/encodings/fastlanes/src/rle/probe.rs b/encodings/fastlanes/src/rle/probe.rs index 8f80aa09228..3deca8ea2cd 100644 --- a/encodings/fastlanes/src/rle/probe.rs +++ b/encodings/fastlanes/src/rle/probe.rs @@ -31,7 +31,7 @@ pub(crate) fn scalar_at( let (mut retained, mut children) = state.split(); let code = children .slot(RLESlots::INDICES)? - .ok_or_else(|| vortex_err!("RLE indices slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "RLE indices slot is missing"))? .execute_scalar(logical_index, ctx)?; let Some(code) = code.as_primitive().as_::() else { return Ok(Scalar::null(array.dtype().clone())); @@ -47,7 +47,7 @@ pub(crate) fn scalar_at( let value = read_offset( children .slot(RLESlots::VALUES_IDX_OFFSETS)? - .ok_or_else(|| vortex_err!("RLE offsets slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offsets slot is missing"))? .execute_scalar(0, ctx)?, )?; if let Some(state) = retained.as_mut() { @@ -59,18 +59,18 @@ pub(crate) fn scalar_at( read_offset( children .slot(RLESlots::VALUES_IDX_OFFSETS)? - .ok_or_else(|| vortex_err!("RLE offsets slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offsets slot is missing"))? .execute_scalar(chunk, ctx)?, )? .checked_sub(base) - .ok_or_else(|| vortex_err!("RLE offsets precede the slice base"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offsets precede the slice base"))? }; let value_index = offset .checked_add(code) - .ok_or_else(|| vortex_err!("RLE value index overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "RLE value index overflow"))?; let scalar = children .slot(RLESlots::VALUES)? - .ok_or_else(|| vortex_err!("RLE values slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "RLE values slot is missing"))? .execute_scalar(value_index, ctx)?; Scalar::try_new(array.dtype().clone(), scalar.into_value()) } @@ -79,7 +79,7 @@ fn read_offset(scalar: Scalar) -> VortexResult { scalar .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("RLE offset must be a non-null usize")) + .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offset must be a non-null usize")) } #[cfg(test)] diff --git a/encodings/fastlanes/src/rle/vtable/mod.rs b/encodings/fastlanes/src/rle/vtable/mod.rs index 9e4e11a8a12..40f4766b5f8 100644 --- a/encodings/fastlanes/src/rle/vtable/mod.rs +++ b/encodings/fastlanes/src/rle/vtable/mod.rs @@ -107,7 +107,7 @@ impl VTable for RLE { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("RLEArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "RLEArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -163,7 +163,7 @@ impl VTable for RLE { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - "RLEArray expects 0 buffers, got {}", + InvalidArgument: "RLEArray expects 0 buffers, got {}", buffers.len() ); let metadata = RLEMetadata::decode(metadata)?; @@ -277,50 +277,50 @@ fn validate_parts( values.dtype(), DType::Primitive(_, Nullability::NonNullable) ), - "RLE values must be a non-nullable primitive type, got {}", + MismatchedTypes: "RLE values must be a non-nullable primitive type, got {}", values.dtype() ); vortex_ensure!( matches!(indices.dtype().as_ptype(), PType::U8 | PType::U16), - "RLE indices must be u8 or u16, got {}", + MismatchedTypes: "RLE indices must be u8 or u16, got {}", indices.dtype() ); vortex_ensure!( values_idx_offsets.dtype().is_unsigned_int() && !values_idx_offsets.dtype().is_nullable(), - "RLE value idx offsets must be non-nullable unsigned integer, got {}", + MismatchedTypes: "RLE value idx offsets must be non-nullable unsigned integer, got {}", values_idx_offsets.dtype() ); vortex_ensure!( indices.len().is_multiple_of(crate::FL_CHUNK_SIZE), - "RLE indices length must be a multiple of {}, got {}", + InvalidArgument: "RLE indices length must be a multiple of {}, got {}", crate::FL_CHUNK_SIZE, indices.len() ); vortex_ensure!( offset + length <= indices.len(), - "RLE offset + length, {offset} + {length}, must not exceed the indices length {}", + InvalidArgument: "RLE offset + length, {offset} + {length}, must not exceed the indices length {}", indices.len() ); vortex_ensure_eq!( indices.len().div_ceil(crate::FL_CHUNK_SIZE), values_idx_offsets.len(), - "RLE must have one value idx offset per chunk" + InvalidArgument: "RLE must have one value idx offset per chunk" ); vortex_ensure!( indices.len() >= values.len(), - "RLE must have at least as many indices as values, got {} indices and {} values", + InvalidArgument: "RLE must have at least as many indices as values, got {} indices and {} values", indices.len(), values.len() ); let expected_dtype = DType::Primitive(values.dtype().as_ptype(), indices.dtype().nullability()); - vortex_ensure_eq!(dtype, &expected_dtype, "RLE dtype mismatch"); + vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes: "RLE dtype mismatch"); Ok(()) } diff --git a/encodings/fsst/src/array.rs b/encodings/fsst/src/array.rs index c8cb108adf3..ef3d723c36d 100644 --- a/encodings/fsst/src/array.rs +++ b/encodings/fsst/src/array.rs @@ -83,8 +83,9 @@ pub struct FSSTMetadata { impl FSSTMetadata { pub fn get_uncompressed_lengths_ptype(&self) -> VortexResult { - PType::try_from(self.uncompressed_lengths_ptype) - .map_err(|_| vortex_err!("Invalid PType {}", self.uncompressed_lengths_ptype)) + PType::try_from(self.uncompressed_lengths_ptype).map_err( + |_| vortex_err!(InvalidArgument: "Invalid PType {}", self.uncompressed_lengths_ptype), + ) } } @@ -156,7 +157,7 @@ impl VTable for FSST { .into_byte_buffer(), ), 2 => array.codes_bytes_handle().clone(), - _ => vortex_panic!("FSSTArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "FSSTArray buffer index {idx} out of bounds"), } } @@ -165,7 +166,7 @@ impl VTable for FSST { 0 => Some("symbols".to_string()), 1 => Some("symbol_lengths".to_string()), 2 => Some("compressed_codes".to_string()), - _ => vortex_panic!("FSSTArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "FSSTArray buffer_name index {idx} out of bounds"), } } @@ -174,7 +175,7 @@ impl VTable for FSST { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 3); + vortex_ensure_eq!(buffers.len(), 3, InvalidArgument); let symbols = Buffer::::from_byte_buffer(buffers[0].clone().try_to_host_sync()?); let symbol_lengths = Buffer::::from_byte_buffer(buffers[1].clone().try_to_host_sync()?); let data = FSSTData::try_new(symbols, symbol_lengths, buffers[2].clone(), array.len())?; @@ -279,7 +280,7 @@ impl VTable for FSST { let validity = children.get(2, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("Expected 2 or 3 children, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 2 or 3 children, got {}", children.len()); }; FSSTData::validate_parts( @@ -309,7 +310,7 @@ impl VTable for FSST { } vortex_bail!( - "InvalidArgument: Expected 2 or 3 buffers, got {}", + MismatchedTypes: "InvalidArgument: Expected 2 or 3 buffers, got {}", buffers.len() ); } @@ -349,7 +350,7 @@ impl VTable for FSST { // canonicalize-then-append fallback — it would decode to a `VarBinView` only for // `VarBinView::append_to_builder` to reject the same remainder. let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for FSST requires a variable-binary builder") + vortex_bail!(InvalidArgument: "append_to_builder for FSST requires a variable-binary builder") }; // Decompress the whole block of data into a new buffer, which the builder adopts as a @@ -673,7 +674,7 @@ impl FSST { .as_opt::() .ok_or_else(|| { vortex_err!( - "Expected VarBinArray for codes, got {}", + MismatchedTypes: "Expected VarBinArray for codes, got {}", codes.encoding_id() ) })? @@ -816,7 +817,7 @@ impl FSSTData { ) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - "FSST arrays must be Binary or Utf8, found {dtype}" + MismatchedTypes: "FSST arrays must be Binary or Utf8, found {dtype}" ); if symbols.len() > FSST_SYMBOL_TABLE_LEN { @@ -1099,7 +1100,7 @@ mod test { let sliced = fsst_array .slice(1..3)? .try_downcast::() - .map_err(|_| vortex_err!("slice must return an FSST array"))?; + .map_err(|_| vortex_err!(AssertionFailed: "slice must return an FSST array"))?; let sliced_compressor_ptr = sliced.compressor() as *const Compressor; assert_eq!(compressor_ptr, sliced_compressor_ptr); @@ -1203,7 +1204,7 @@ mod test { let padded = deserialized .clone() .try_downcast::() - .map_err(|_| vortex_err!("deserialize must return an FSST array"))?; + .map_err(|_| vortex_err!(Serde: "deserialize must return an FSST array"))?; assert_eq!(padded.padded_symbols().len(), FSST_SYMBOL_TABLE_LEN); assert_eq!(padded.n_symbols(), fsst_array.symbols().len()); diff --git a/encodings/fsst/src/canonical.rs b/encodings/fsst/src/canonical.rs index 448acdf3cc6..49cb4166c04 100644 --- a/encodings/fsst/src/canonical.rs +++ b/encodings/fsst/src/canonical.rs @@ -88,17 +88,17 @@ impl FsstDecodePlan { offsets.last().and_then(ToPrimitive::to_usize), ) }); - let (first_offset, last_offset) = first_offset.zip(last_offset).ok_or_else(|| { - vortex_err!("FSST codes offsets are missing, negative or overflow usize") - })?; + let (first_offset, last_offset) = first_offset.zip(last_offset).ok_or_else( + || vortex_err!(Overflow: "FSST codes offsets are missing, negative or overflow usize"), + )?; let codes = fsst_array.codes_bytes(); vortex_ensure!( first_offset <= last_offset, - "FSST first codes offset {first_offset} exceeds last codes offset {last_offset}" + InvalidArgument: "FSST first codes offset {first_offset} exceeds last codes offset {last_offset}" ); vortex_ensure!( last_offset <= codes.len(), - "FSST last codes offset {last_offset} exceeds codes bytes length {}", + InvalidArgument: "FSST last codes offset {last_offset} exceeds codes bytes length {}", codes.len() ); let codes = codes.slice(first_offset..last_offset); @@ -113,13 +113,15 @@ impl FsstDecodePlan { .iter() .try_fold(0usize, |acc, &x| acc.checked_add(x.to_usize()?)) }) - .ok_or_else(|| vortex_err!("FSST uncompressed lengths are negative or overflow"))?; + .ok_or_else( + || vortex_err!(Overflow: "FSST uncompressed lengths are negative or overflow"), + )?; // Stored lengths size the output buffer, so bound them by the codes: // symbols emit 1 to 8 bytes; escapes use two code bytes per output byte. vortex_ensure!( codes.len().div_ceil(2) <= total_size && total_size <= codes.len().saturating_mul(8), - "FSST recorded length {total_size} is impossible for {} code bytes", + Serde: "FSST recorded length {total_size} is impossible for {} code bytes", codes.len() ); @@ -142,7 +144,7 @@ impl FsstDecodePlan { out: &mut [MaybeUninit], ) -> VortexResult { let len = decompressor.decompress_into(self.codes.as_slice(), out); - vortex_ensure_eq!(len, self.total_size, "FSST decoded length mismatch"); + vortex_ensure_eq!(len, self.total_size, Serde: "FSST decoded length mismatch"); Ok(len) } } diff --git a/encodings/fsst/src/compress.rs b/encodings/fsst/src/compress.rs index bb786e47175..e58c6fb793c 100644 --- a/encodings/fsst/src/compress.rs +++ b/encodings/fsst/src/compress.rs @@ -60,7 +60,7 @@ pub fn fsst_compress( compress_varbin_array(varbin, compressor, ctx) } else { vortex_bail!( - "fsst_compress requires VarBinView or VarBin encoding, got {}", + InvalidArgument: "fsst_compress requires VarBinView or VarBin encoding, got {}", array.encoding_id() ) } @@ -76,7 +76,7 @@ pub fn fsst_train_compressor(array: &ArrayRef, ctx: &mut ExecutionCtx) -> Vortex train_varbin_array(varbin, ctx) } else { vortex_bail!( - "fsst_train_compressor requires VarBinView or VarBin encoding, got {}", + InvalidArgument: "fsst_train_compressor requires VarBinView or VarBin encoding, got {}", array.encoding_id() ) } diff --git a/encodings/fsst/src/compute/compare.rs b/encodings/fsst/src/compute/compare.rs index 53422acebee..bff8c0ab354 100644 --- a/encodings/fsst/src/compute/compare.rs +++ b/encodings/fsst/src/compute/compare.rs @@ -53,7 +53,7 @@ fn compare_fsst_constant( .as_utf8() .is_empty() .vortex_expect("RHS should not be null"), - _ => vortex_bail!("VarBinArray can only have type of Binary or Utf8"), + _ => vortex_bail!(MismatchedTypes: "VarBinArray can only have type of Binary or Utf8"), }; if is_rhs_empty { let buffer = match operator { diff --git a/encodings/fsst/src/dfa/flat_contains.rs b/encodings/fsst/src/dfa/flat_contains.rs index a33b82b4a0a..5979e9884f3 100644 --- a/encodings/fsst/src/dfa/flat_contains.rs +++ b/encodings/fsst/src/dfa/flat_contains.rs @@ -101,7 +101,7 @@ impl FlatContainsDfa { ) -> VortexResult { if needle.len() > Self::MAX_NEEDLE_LEN { vortex_bail!( - "needle length {} exceeds maximum {} for flat contains DFA", + InvalidArgument: "needle length {} exceeds maximum {} for flat contains DFA", needle.len(), Self::MAX_NEEDLE_LEN ); diff --git a/encodings/fsst/src/dfa/prefix.rs b/encodings/fsst/src/dfa/prefix.rs index 5c40affd7a1..de177c4a6c0 100644 --- a/encodings/fsst/src/dfa/prefix.rs +++ b/encodings/fsst/src/dfa/prefix.rs @@ -61,7 +61,7 @@ impl FlatPrefixDfa { ) -> VortexResult { if prefix.len() > Self::MAX_PREFIX_LEN { vortex_bail!( - "prefix length {} exceeds maximum {} for flat prefix DFA", + InvalidArgument: "prefix length {} exceeds maximum {} for flat prefix DFA", prefix.len(), Self::MAX_PREFIX_LEN ); diff --git a/encodings/fsst/src/slice.rs b/encodings/fsst/src/slice.rs index c2b2e320d31..b31d2e264a9 100644 --- a/encodings/fsst/src/slice.rs +++ b/encodings/fsst/src/slice.rs @@ -27,7 +27,7 @@ impl SliceReduce for FSST { .codes() .slice(range.clone())? .try_downcast::() - .map_err(|_| vortex_err!("cannot fail conversion"))?, + .map_err(|_| vortex_err!(AssertionFailed: "cannot fail conversion"))?, array.uncompressed_lengths().slice(range)?, ) } diff --git a/encodings/onpair/src/array.rs b/encodings/onpair/src/array.rs index d48287fac84..3bd099ee36c 100644 --- a/encodings/onpair/src/array.rs +++ b/encodings/onpair/src/array.rs @@ -104,8 +104,9 @@ pub struct OnPairMetadata { impl OnPairMetadata { /// Decode the recorded [`PType`] of the `uncompressed_lengths` slot child. pub fn get_uncompressed_lengths_ptype(&self) -> VortexResult { - PType::try_from(self.uncompressed_lengths_ptype) - .map_err(|_| vortex_err!("Invalid PType {}", self.uncompressed_lengths_ptype)) + PType::try_from(self.uncompressed_lengths_ptype).map_err( + |_| vortex_err!(InvalidArgument: "Invalid PType {}", self.uncompressed_lengths_ptype), + ) } } @@ -413,7 +414,7 @@ fn validate_parts( ) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - "OnPair arrays must be Binary or Utf8, found {dtype}" + MismatchedTypes: "OnPair arrays must be Binary or Utf8, found {dtype}" ); if !dict_offsets.dtype().is_int() || dict_offsets.dtype().is_nullable() { @@ -476,14 +477,14 @@ impl VTable for OnPair { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.dict_bytes_handle().clone(), - _ => vortex_panic!("OnPairArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "OnPairArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("dict_bytes".to_string()), - _ => vortex_panic!("OnPairArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "OnPairArray buffer_name index {idx} out of bounds"), } } @@ -492,7 +493,7 @@ impl VTable for OnPair { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1); + vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); let mut data = array.data().clone(); data.dict_bytes = buffers[0].clone(); // The replacement blob may differ from the one the memoized dictionary @@ -513,7 +514,7 @@ impl VTable for OnPair { _session: &VortexSession, ) -> VortexResult>> { let dict_size = u32::try_from(array.dict_offsets().len().saturating_sub(1)) - .map_err(|_| vortex_err!("OnPair dict_size exceeds u32"))?; + .map_err(|_| vortex_err!(Overflow: "OnPair dict_size exceeds u32"))?; let codes_len = array.codes().len() as u64; Ok(Some( OnPairMetadata { @@ -546,19 +547,21 @@ impl VTable for OnPair { // Slot children do not persist their own lengths, so metadata records // the dictionary and code-stream sizes needed to deserialize them. let dict_offsets_len = metadata.dict_size as usize + 1; - let codes_len = usize::try_from(metadata.codes_len) - .map_err(|_| vortex_err!("codes_len {} overflows usize", metadata.codes_len))?; + let codes_len = usize::try_from(metadata.codes_len).map_err( + |_| vortex_err!(Overflow: "codes_len {} overflows usize", metadata.codes_len), + )?; // The cascading compressor may have narrowed any of these integer // children to a tighter ptype; the recorded ptype tells the framework // exactly which dtype to materialise as. let dict_offsets_ptype = PType::try_from(metadata.dict_offsets_ptype).map_err(|_| { - vortex_err!("invalid dict_offsets_ptype {}", metadata.dict_offsets_ptype) + vortex_err!(InvalidArgument: "invalid dict_offsets_ptype {}", metadata.dict_offsets_ptype) })?; - let codes_ptype = PType::try_from(metadata.codes_ptype) - .map_err(|_| vortex_err!("invalid codes_ptype {}", metadata.codes_ptype))?; + let codes_ptype = PType::try_from(metadata.codes_ptype).map_err( + |_| vortex_err!(InvalidArgument: "invalid codes_ptype {}", metadata.codes_ptype), + )?; let codes_offsets_ptype = PType::try_from(metadata.codes_offsets_ptype).map_err(|_| { vortex_err!( - "invalid codes_offsets_ptype {}", + InvalidArgument: "invalid codes_offsets_ptype {}", metadata.codes_offsets_ptype ) })?; @@ -653,7 +656,7 @@ impl VTable for OnPair { // canonicalize-then-append fallback — it would decode to a `VarBinView` only for // `VarBinView::append_to_builder` to reject the same remainder. let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for OnPair requires a variable-binary builder") + vortex_bail!(InvalidArgument: "append_to_builder for OnPair requires a variable-binary builder") }; // Decode the whole code stream into a new buffer, which the builder adopts as a data diff --git a/encodings/onpair/src/canonical.rs b/encodings/onpair/src/canonical.rs index f31fae71cd0..a6217144cea 100644 --- a/encodings/onpair/src/canonical.rs +++ b/encodings/onpair/src/canonical.rs @@ -76,7 +76,9 @@ impl<'a> OnPairDecodePlan<'a> { .iter() .try_fold(0usize, |acc, &l| acc.checked_add(l.to_usize()?)) }) - .ok_or_else(|| vortex_err!("OnPair uncompressed lengths are negative or overflow"))?; + .ok_or_else( + || vortex_err!(Overflow: "OnPair uncompressed lengths are negative or overflow"), + )?; // `codes_offsets` holds the per-row code boundaries and may itself be a // sliced or filtered view of the original. Its first and last entries @@ -92,11 +94,11 @@ impl<'a> OnPairDecodePlan<'a> { let code_end = code_boundary_at(codes_offsets, array.len(), ctx)?; vortex_ensure!( code_start <= code_end, - "OnPair codes_offsets must be nondecreasing" + InvalidArgument: "OnPair codes_offsets must be nondecreasing" ); vortex_ensure!( code_end <= array.codes().len(), - "OnPair codes_offsets end {} exceeds codes len {}", + InvalidArgument: "OnPair codes_offsets end {} exceeds codes len {}", code_end, array.codes().len() ); @@ -104,7 +106,7 @@ impl<'a> OnPairDecodePlan<'a> { let n_codes = code_end - code_start; vortex_ensure!( n_codes <= total_size && total_size <= n_codes.saturating_mul(onpair::MAX_TOKEN_SIZE), - "OnPair recorded length {total_size} is impossible for {n_codes} codes" + Serde: "OnPair recorded length {total_size} is impossible for {n_codes} codes" ); // Slice the `codes` child to that window *before* unpacking it, so a sliced @@ -134,14 +136,14 @@ impl<'a> OnPairDecodePlan<'a> { let written = match onpair::try_decode_into(self.codes.as_slice(), self.dict, out) { Ok(written) => written, Err(_) => { - vortex_bail!("OnPair codes decode to more bytes than uncompressed_lengths records") + vortex_bail!(Serde: "OnPair codes decode to more bytes than uncompressed_lengths records") } }; vortex_ensure_eq!( written, self.total_size, - "OnPair codes decoded length must match uncompressed_lengths" + Serde: "OnPair codes decoded length must match uncompressed_lengths" ); Ok(written) } diff --git a/encodings/onpair/src/compute/compare.rs b/encodings/onpair/src/compute/compare.rs index fe8e6a0cec3..1af2d261613 100644 --- a/encodings/onpair/src/compute/compare.rs +++ b/encodings/onpair/src/compute/compare.rs @@ -211,7 +211,7 @@ mod tests { let mut ctx = SESSION.create_execution_ctx(); let arr = onpair_compress(input.as_array(), DEFAULT_CONFIG, &mut ctx)? .try_downcast::() - .map_err(|array| vortex_err!("expected OnPair array, got {}", array.encoding_id()))?; + .map_err(|array| vortex_err!(MismatchedTypes: "expected OnPair array, got {}", array.encoding_id()))?; let rhs = ConstantArray::new("hello", arr.len()).into_array(); let eq = @@ -254,7 +254,7 @@ mod tests { assert!(sliced.is::(), "slice dropped OnPair encoding"); let sliced = sliced .try_downcast::() - .map_err(|_| vortex_err!("sliced array was not OnPair"))?; + .map_err(|_| vortex_err!(AssertionFailed: "sliced array was not OnPair"))?; let rhs = ConstantArray::new("hello", sliced.len()).into_array(); let eq = ::compare( diff --git a/encodings/onpair/src/decode.rs b/encodings/onpair/src/decode.rs index a6071757e23..ee4fe22f224 100644 --- a/encodings/onpair/src/decode.rs +++ b/encodings/onpair/src/decode.rs @@ -52,9 +52,9 @@ pub(crate) fn collect_widened_range( primitive.as_slice::

()[range] .iter() .map(|&value| { - T::from(value).ok_or_else(|| { - vortex_err!("OnPair value {value} does not fit {}", T::PTYPE) - }) + T::from(value).ok_or_else( + || vortex_err!(Overflow: "OnPair value {value} does not fit {}", T::PTYPE), + ) }) .collect::>>() .map(Buffer::from) @@ -78,7 +78,7 @@ pub(crate) fn code_boundary_at( .as_primitive() .as_opt::() .flatten() - .ok_or_else(|| vortex_err!("OnPair codes_offsets[{index}] is null, negative, or too large")) + .ok_or_else(|| vortex_err!(InvalidArgument: "OnPair codes_offsets[{index}] is null, negative, or too large")) } /// A validated, materialised window over an array's `codes`: the widened @@ -122,17 +122,17 @@ pub(crate) fn collect_codes_window( vortex_ensure_eq!( offsets.len(), len + 1, - "OnPair codes_offsets must have len + 1 entries" + InvalidArgument: "OnPair codes_offsets must have len + 1 entries" ); vortex_ensure!( offsets.is_sorted(), - "OnPair codes_offsets must be nondecreasing" + InvalidArgument: "OnPair codes_offsets must be nondecreasing" ); let code_start = usize::try_from(offsets[0]).vortex_expect("code offset fits usize"); let code_end = usize::try_from(offsets[len]).vortex_expect("code offset fits usize"); vortex_ensure!( code_end <= array.codes().len(), - "OnPair codes_offsets end {} exceeds codes len {}", + InvalidArgument: "OnPair codes_offsets end {} exceeds codes len {}", code_end, array.codes().len() ); diff --git a/encodings/onpair/src/ops.rs b/encodings/onpair/src/ops.rs index 33e64225ab0..e2ec3e4a5fe 100644 --- a/encodings/onpair/src/ops.rs +++ b/encodings/onpair/src/ops.rs @@ -48,21 +48,23 @@ impl OperationsVTable for OnPair { .as_opt::() .flatten() .ok_or_else(|| { - vortex_err!("OnPair uncompressed_lengths[{index}] is null, negative, or too large") + vortex_err!( + InvalidArgument: "OnPair uncompressed_lengths[{index}] is null, negative, or too large" + ) })?; // The stored length controls allocation; each code emits 1 to MAX_TOKEN_SIZE bytes. vortex_ensure!( codes.len() <= len && len <= codes.len().saturating_mul(onpair::MAX_TOKEN_SIZE), - "OnPair row {index} recorded length {len} is impossible for {} codes", + Serde: "OnPair row {index} recorded length {len} is impossible for {} codes", codes.len() ); let mut buf: Vec = Vec::with_capacity(len); let written = match onpair::try_decode_into(codes.as_slice(), dict, buf.spare_capacity_mut()) { Ok(written) => written, - Err(_) => vortex_bail!("OnPair row {index} exceeds its recorded length"), + Err(_) => vortex_bail!(Serde: "OnPair row {index} exceeds its recorded length"), }; - vortex_ensure_eq!(written, len, "OnPair row {index} decoded length mismatch"); + vortex_ensure_eq!(written, len, Serde: "OnPair row {index} decoded length mismatch"); // SAFETY: `try_decode_into` initialised exactly `written` bytes. unsafe { buf.set_len(written) }; Ok(varbin_scalar(ByteBuffer::from(buf), array.dtype())) diff --git a/encodings/onpair/src/tests.rs b/encodings/onpair/src/tests.rs index aa735b0524a..f463f5150a1 100644 --- a/encodings/onpair/src/tests.rs +++ b/encodings/onpair/src/tests.rs @@ -51,7 +51,7 @@ fn compress_onpair( onpair_compress(array, DEFAULT_CONFIG, ctx)? .try_downcast::() .map_err(|array| { - vortex_error::vortex_err!("expected OnPair array, got {}", array.encoding_id()) + vortex_error::vortex_err!(MismatchedTypes: "expected OnPair array, got {}", array.encoding_id()) }) } @@ -391,7 +391,7 @@ fn test_onpair_filter_shares_dict() -> vortex_error::VortexResult<()> { ); let typed = filtered .try_downcast::() - .map_err(|_| vortex_error::vortex_err!("filter result was not OnPair"))?; + .map_err(|_| vortex_error::vortex_err!(AssertionFailed: "filter result was not OnPair"))?; assert_eq!(typed.dict_bytes().as_ptr(), arr.dict_bytes().as_ptr()); assert_eq!(typed.dict_bytes().as_slice(), arr.dict_bytes().as_slice()); assert_eq!(typed.dict_offsets().len(), arr.dict_offsets().len()); @@ -487,7 +487,7 @@ fn test_onpair_filter_with_narrowed_codes_offsets_u16() -> vortex_error::VortexR .expect("OnPair filter must return Some"); let typed = filtered .try_downcast::() - .map_err(|_| vortex_error::vortex_err!("filter result was not OnPair"))?; + .map_err(|_| vortex_error::vortex_err!(AssertionFailed: "filter result was not OnPair"))?; assert_eq!(typed.len(), expected.len()); assert_arrays_eq!(typed, VarBinViewArray::from_iter_str(&expected), &mut ctx); @@ -623,7 +623,7 @@ fn test_onpair_take_shares_dict() -> vortex_error::VortexResult<()> { .expect("OnPair take must return Some"); let typed = taken .try_downcast::() - .map_err(|_| vortex_error::vortex_err!("take result was not OnPair"))?; + .map_err(|_| vortex_error::vortex_err!(AssertionFailed: "take result was not OnPair"))?; assert_eq!(typed.dict_bytes().as_slice(), arr.dict_bytes().as_slice()); assert_eq!(typed.dict_offsets().len(), arr.dict_offsets().len()); diff --git a/encodings/parquet-variant/src/array.rs b/encodings/parquet-variant/src/array.rs index 8a88ed61d82..88a1ab4ae1e 100644 --- a/encodings/parquet-variant/src/array.rs +++ b/encodings/parquet-variant/src/array.rs @@ -388,11 +388,11 @@ fn parquet_shredded_field_from_logical( .as_opt::() .ok_or_else(|| { vortex_err!( - "cannot rebuild Parquet shredded field: nested Variant lacks Parquet Variant core storage" + NotImplemented: "cannot rebuild Parquet shredded field: nested Variant lacks Parquet Variant core storage" ) })?; let value = core.value().cloned().ok_or_else(|| { - vortex_err!("cannot rebuild Parquet shredded field: partially shredded Variant has no residual value") + vortex_err!(InvalidArgument: "cannot rebuild Parquet shredded field: partially shredded Variant has no residual value") })?; let typed_value = variant .shredded() @@ -552,7 +552,7 @@ mod tests { ); let inner = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant child"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant child"))?; let mut ctx = SESSION.create_execution_ctx(); let roundtripped = inner.to_arrow(&ArrowExportOptions::default(), &mut ctx)?; @@ -622,10 +622,10 @@ mod tests { let parquet_array = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant array"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; let typed_value = parquet_array .typed_value() - .ok_or_else(|| vortex_err!("expected typed_value child"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; assert_arrays_eq!( typed_value, PrimitiveArray::from_option_iter([Some(10), None, Some(30)]), @@ -729,16 +729,16 @@ mod tests { let vortex_arr = ParquetVariant::from_arrow_variant(&arrow_variant, &SESSION.arrow())?; let parquet_array = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant array"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; let mut ctx = SESSION.create_execution_ctx(); let value = parquet_array .value() - .ok_or_else(|| vortex_err!("expected synthesized value child"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected synthesized value child"))?; assert!(value.all_invalid(&mut ctx)?); let typed_value = parquet_array .typed_value() - .ok_or_else(|| vortex_err!("expected typed_value child"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; assert_arrays_eq!( typed_value, PrimitiveArray::from_option_iter([Some(10i32), Some(20), Some(30)]), @@ -768,7 +768,7 @@ mod tests { let vortex_arr = ParquetVariant::from_arrow_variant(&arrow_variant, &SESSION.arrow())?; let parquet_array = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant array"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; assert!(parquet_array.value().is_some()); assert!(parquet_array.typed_value().is_some()); @@ -841,7 +841,7 @@ mod tests { assert!( original .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant"))? .typed_value() .is_some(), "fixture must be shredded" @@ -850,15 +850,15 @@ mod tests { // Canonicalize: the forward transform lifts `typed_value` into a logical shredded child. let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = original.clone().execute::(&mut ctx)? else { - return Err(vortex_err!("expected canonical variant")); + return Err(vortex_err!(MismatchedTypes: "expected canonical variant")); }; let core = canonical .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; let logical = canonical .shredded() - .ok_or_else(|| vortex_err!("expected canonical shredded child"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))? .clone(); // Inverse transform: rebuild a Parquet `typed_value` and reattach it. diff --git a/encodings/parquet-variant/src/arrow.rs b/encodings/parquet-variant/src/arrow.rs index 48d2c305c94..530f10fe162 100644 --- a/encodings/parquet-variant/src/arrow.rs +++ b/encodings/parquet-variant/src/arrow.rs @@ -128,16 +128,16 @@ pub(crate) fn parquet_variant_for_export( return Ok(executed); } - let variant = executed - .as_opt::() - .ok_or_else(|| vortex_err!("cannot export Variant without ParquetVariant storage"))?; + let variant = executed.as_opt::().ok_or_else( + || vortex_err!(NotImplemented: "cannot export Variant without ParquetVariant storage"), + )?; let core_storage = variant .core_storage() .clone() .execute_until::(ctx)?; - let parquet_core = core_storage - .as_opt::() - .ok_or_else(|| vortex_err!("cannot export Variant without ParquetVariant core storage"))?; + let parquet_core = core_storage.as_opt::().ok_or_else( + || vortex_err!(NotImplemented: "cannot export Variant without ParquetVariant core storage"), + )?; let Some(shredded) = variant.shredded() else { return Ok(core_storage); }; diff --git a/encodings/parquet-variant/src/json_to_variant_tests.rs b/encodings/parquet-variant/src/json_to_variant_tests.rs index e66ed56c67d..516bd0b55b5 100644 --- a/encodings/parquet-variant/src/json_to_variant_tests.rs +++ b/encodings/parquet-variant/src/json_to_variant_tests.rs @@ -75,7 +75,9 @@ fn assert_variant_i64_rows(array: &ArrayRef, expected: &[Option]) -> Vortex Some(expected) => { let value = variant .value() - .ok_or_else(|| vortex_err!("expected non-null variant at row {idx}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "expected non-null variant at row {idx}"), + )? .cast(&i64_dtype())?; assert_eq!(value.as_primitive().typed_value::(), Some(*expected)); } @@ -112,14 +114,14 @@ fn converts_json_extension_rows() -> VortexResult<()> { let object = row0 .as_variant() .value() - .ok_or_else(|| vortex_err!("expected non-null variant"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant"))?; let field = object .as_struct() .field("a") - .ok_or_else(|| vortex_err!("expected field a"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected field a"))? .as_variant() .value() - .ok_or_else(|| vortex_err!("expected non-null field a"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null field a"))? .cast(&i64_dtype())?; assert_eq!(field.as_primitive().typed_value::(), Some(expected)); } @@ -128,7 +130,7 @@ fn converts_json_extension_rows() -> VortexResult<()> { let value = row1 .as_variant() .value() - .ok_or_else(|| vortex_err!("expected non-null variant"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant"))? .cast(&i64_dtype())?; assert_eq!(value.as_primitive().typed_value::(), Some(2)); Ok(()) @@ -210,11 +212,11 @@ fn shredding_produces_typed_value_child() -> VortexResult<()> { // The canonical form must expose field `a` through the shredded tree. let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = result.clone().execute::(&mut ctx)? else { - vortex_bail!("expected canonical variant array"); + vortex_bail!(MismatchedTypes: "expected canonical variant array"); }; let shredded = canonical .shredded() - .ok_or_else(|| vortex_err!("expected canonical shredded child"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))? .clone() .execute::(&mut ctx)?; assert!(shredded.unmasked_field_by_name_opt("a").is_some()); @@ -290,7 +292,7 @@ fn shredding_root_path_shreds_top_level_values() -> VortexResult<()> { let value = row2 .as_variant() .value() - .ok_or_else(|| vortex_err!("expected non-null variant"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant"))?; assert_eq!( value.as_utf8().value().map(|value| value.to_string()), Some("not-a-number".to_string()) diff --git a/encodings/parquet-variant/src/kernel.rs b/encodings/parquet-variant/src/kernel.rs index b218d9404f4..f162349b523 100644 --- a/encodings/parquet-variant/src/kernel.rs +++ b/encodings/parquet-variant/src/kernel.rs @@ -126,7 +126,7 @@ impl ExecuteParentKernel for VariantGetKernel { // Import through the same `as_type` field the cast targeted, so an extension target // dtype comes back as that extension rather than as its bare storage type. let as_type = as_type.ok_or_else(|| { - vortex_err!("a non-variant target dtype must produce an as_type field") + vortex_err!(AssertionFailed: "a non-variant target dtype must produce an as_type field") })?; session.arrow().from_arrow_array(arrow_output, &as_type)? }; @@ -134,7 +134,7 @@ impl ExecuteParentKernel for VariantGetKernel { vortex_ensure_eq!( output.dtype(), parent.dtype(), - "VariantGet output dtype must match parent dtype" + MismatchedTypes: "VariantGet output dtype must match parent dtype" ); Ok(Some(output)) } @@ -208,8 +208,9 @@ pub(crate) fn to_parquet_variant_path(path: &VariantPath) -> VortexResult { - let index = usize::try_from(*index) - .map_err(|_| vortex_err!("VariantGet path index {index} is too large"))?; + let index = usize::try_from(*index).map_err( + |_| vortex_err!(Overflow: "VariantGet path index {index} is too large"), + )?; Ok(PqVariantPathElement::index(index)) } }) @@ -371,7 +372,7 @@ mod tests { let arrow = SESSION.arrow(); let as_type = to_arrow_as_type(Some(&uuid), &arrow)? - .ok_or_else(|| vortex_err!("expected an as_type field"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected an as_type field"))?; assert_eq!(as_type.data_type(), &DataType::FixedSizeBinary(16)); assert_eq!(as_type.extension_type_name(), Some(ArrowUuid::NAME)); @@ -394,7 +395,7 @@ mod tests { )), &arrow, )? - .ok_or_else(|| vortex_err!("expected an as_type field"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected an as_type field"))?; assert_eq!(as_type.data_type(), &DataType::Int32); assert_eq!(as_type.extension_type_name(), None); assert!(as_type.is_nullable()); @@ -457,7 +458,7 @@ mod tests { .get(pos) .is_some_and(|byte| !matches!(byte, b'.' | b'[')) { - vortex_bail!("Invalid Variant path {path:?}: expected '.' or '[' after '$'"); + vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.' or '[' after '$'"); } while pos < path.len() { @@ -479,7 +480,7 @@ mod tests { pos = next_pos; } _ => { - vortex_bail!("Invalid Variant path {path:?}: expected '.', '[', or end of path") + vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.', '[', or end of path") } } } @@ -498,7 +499,7 @@ mod tests { } vortex_ensure!( pos > start, - "Invalid Variant path {path:?}: expected field name" + InvalidArgument: "Invalid Variant path {path:?}: expected field name" ); Ok((&path[start..pos], pos)) } @@ -514,15 +515,15 @@ mod tests { } vortex_ensure!( pos > start, - "Invalid Variant path {path:?}: expected list index" + InvalidArgument: "Invalid Variant path {path:?}: expected list index" ); vortex_ensure!( path.as_bytes().get(pos) == Some(&b']'), - "Invalid Variant path {path:?}: expected closing ']'" + InvalidArgument: "Invalid Variant path {path:?}: expected closing ']'" ); - let index = path[start..pos] - .parse() - .map_err(|_| vortex_err!("Invalid Variant path {path:?}: list index is too large"))?; + let index = path[start..pos].parse().map_err( + |_| vortex_err!(Overflow: "Invalid Variant path {path:?}: list index is too large"), + )?; Ok((index, pos + 1)) } @@ -872,7 +873,7 @@ mod tests { let parquet_array = ParquetVariant::from_arrow_variant(&arrow_variant, &SESSION.arrow())?; let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = parquet_array.execute::(&mut ctx)? else { - return Err(vortex_err!("expected canonical variant array")); + return Err(vortex_err!(MismatchedTypes: "expected canonical variant array")); }; Ok(canonical.into_array()) } @@ -914,9 +915,9 @@ mod tests { let variant = scalar.as_variant(); match expected { Some(expected) => { - let value = variant - .value() - .ok_or_else(|| vortex_err!("expected non-null variant scalar"))?; + let value = variant.value().ok_or_else( + || vortex_err!(InvalidArgument: "expected non-null variant scalar"), + )?; let value = value.cast(&VortexDType::Primitive(PType::I32, Nullability::Nullable))?; assert_eq!(value.as_primitive().typed_value::(), Some(*expected)); @@ -940,17 +941,17 @@ mod tests { let object = scalar .as_variant() .value() - .ok_or_else(|| vortex_err!("expected non-null variant object"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant object"))? .as_struct(); match expected_a[idx] { Some(expected) => { let value = object .field("a") - .ok_or_else(|| vortex_err!("expected field a"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected field a"))? .as_variant() .value() - .ok_or_else(|| vortex_err!("expected non-null field a"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null field a"))? .cast(&VortexDType::Primitive(PType::I32, Nullability::Nullable))?; assert_eq!(value.as_primitive().typed_value::(), Some(expected)); } @@ -959,11 +960,11 @@ mod tests { let field_b = object .field("b") - .ok_or_else(|| vortex_err!("expected field b"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected field b"))?; let value = field_b .as_variant() .value() - .ok_or_else(|| vortex_err!("expected non-null field b"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null field b"))?; assert_eq!( value.as_utf8().value().map(|value| value.as_str()), Some(expected_b[idx]) @@ -998,7 +999,7 @@ mod tests { let executed_variant = executed.as_::(); let typed_value = executed_variant .typed_value() - .ok_or_else(|| vortex_err!("expected typed_value child"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; assert_arrays_eq!( typed_value, @@ -1076,13 +1077,13 @@ mod tests { let core_storage = canonical_variant .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; assert!(core_storage.typed_value().is_none()); assert!(core_storage.value().is_some()); let shredded = canonical_variant .shredded() - .ok_or_else(|| vortex_err!("expected canonical shredded child"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))? .clone() .execute::(&mut SESSION.create_execution_ctx())?; assert_eq!( @@ -1182,14 +1183,14 @@ mod tests { let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = parquet_array.execute::(&mut ctx)? else { - return Err(vortex_err!("expected canonical variant array")); + return Err(vortex_err!(MismatchedTypes: "expected canonical variant array")); }; assert!(canonical.shredded().is_some()); let core_storage = canonical .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; assert!(core_storage.typed_value().is_none()); assert!(core_storage.value().is_some()); diff --git a/encodings/parquet-variant/src/operations.rs b/encodings/parquet-variant/src/operations.rs index 60a60a19eca..1229b2f88ce 100644 --- a/encodings/parquet-variant/src/operations.rs +++ b/encodings/parquet-variant/src/operations.rs @@ -225,7 +225,7 @@ fn scalar_from_shredded_object_scalar( let unshredded = scalar_from_unshredded_value(metadata, &value)?; if !unshredded.is_null() { let Some(unshredded) = unshredded.as_struct_opt() else { - vortex_bail!("Variant typed_value must be object if typed_value is a struct"); + vortex_bail!(InvalidArgument: "Variant typed_value must be object if typed_value is a struct"); }; for name in unshredded.names().iter() { if names @@ -322,17 +322,16 @@ fn parquet_variant_to_scalar(variant: PqVariant<'_, '_>) -> VortexResult let dtype = DType::Extension( Timestamp::new_with_tz(TimeUnit::Nanoseconds, Some(Arc::from("UTC")), nn).erased(), ); - let nanos = v - .timestamp_nanos_opt() - .ok_or_else(|| vortex_err!("Timestamp nanoseconds value out of i64 range"))?; + let nanos = v.timestamp_nanos_opt().ok_or_else( + || vortex_err!(Overflow: "Timestamp nanoseconds value out of i64 range"), + )?; Scalar::try_new(dtype, Some(ScalarValue::Primitive(PValue::I64(nanos))))? } PqVariant::TimestampNtzNanos(v) => { let dtype = DType::Extension(Timestamp::new(TimeUnit::Nanoseconds, nn).erased()); - let nanos = v - .and_utc() - .timestamp_nanos_opt() - .ok_or_else(|| vortex_err!("Timestamp nanoseconds value out of i64 range"))?; + let nanos = v.and_utc().timestamp_nanos_opt().ok_or_else( + || vortex_err!(Overflow: "Timestamp nanoseconds value out of i64 range"), + )?; Scalar::try_new(dtype, Some(ScalarValue::Primitive(PValue::I64(nanos))))? } PqVariant::Time(v) => { diff --git a/encodings/parquet-variant/src/vtable.rs b/encodings/parquet-variant/src/vtable.rs index 34703b17c45..ea8296005ad 100644 --- a/encodings/parquet-variant/src/vtable.rs +++ b/encodings/parquet-variant/src/vtable.rs @@ -96,57 +96,57 @@ impl VTable for ParquetVariant { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), ParquetVariantSlots::COUNT); + vortex_ensure_eq!(slots.len(), ParquetVariantSlots::COUNT, InvalidArgument); let validity = child_to_validity( slots[ParquetVariantSlots::VALIDITY].as_ref(), dtype.nullability(), ); let metadata = slots[ParquetVariantSlots::METADATA] .as_ref() - .ok_or_else(|| vortex_err!("ParquetVariantArray metadata slot"))?; + .ok_or_else(|| vortex_err!(NotFound: "ParquetVariantArray metadata slot"))?; let value = slots[ParquetVariantSlots::VALUE].as_ref(); let typed_value = slots[ParquetVariantSlots::TYPED_VALUE].as_ref(); vortex_ensure!( matches!(dtype, DType::Variant(_)), - "Expected Variant DType, found {dtype}" + MismatchedTypes: "Expected Variant DType, found {dtype}" ); vortex_ensure!( value.is_some() || typed_value.is_some(), - "at least one of value or typed_value must be present" + InvalidArgument: "at least one of value or typed_value must be present" ); vortex_ensure_eq!( dtype.nullability(), validity.nullability(), - "variant dtype nullability must match validity nullability" + InvalidArgument: "variant dtype nullability must match validity nullability" ); vortex_ensure_eq!( metadata.dtype(), &DType::Binary(Nullability::NonNullable), - "metadata dtype must be non-nullable binary" + MismatchedTypes: "metadata dtype must be non-nullable binary" ); vortex_ensure_eq!( metadata.len(), len, - "metadata length must match array length" + InvalidArgument: "metadata length must match array length" ); if let Some(validity_len) = validity.maybe_len() { - vortex_ensure_eq!(validity_len, len, "validity length must match array length"); + vortex_ensure_eq!(validity_len, len, InvalidArgument: "validity length must match array length"); } if let Some(value) = value { vortex_ensure!( matches!(value.dtype(), DType::Binary(_)), - "value dtype must be binary, found {}", + MismatchedTypes: "value dtype must be binary, found {}", value.dtype() ); - vortex_ensure_eq!(value.len(), len, "value length must match array length"); + vortex_ensure_eq!(value.len(), len, InvalidArgument: "value length must match array length"); } if let Some(typed_value) = typed_value { vortex_ensure_eq!( typed_value.len(), len, - "typed_value length must match array length" + InvalidArgument: "typed_value length must match array length" ); } Ok(()) @@ -157,7 +157,7 @@ impl VTable for ParquetVariant { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ParquetVariantArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ParquetVariantArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -205,7 +205,7 @@ impl VTable for ParquetVariant { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - "ParquetVariantArray expects 0 buffers, got {}", + InvalidArgument: "ParquetVariantArray expects 0 buffers, got {}", buffers.len() ); @@ -215,17 +215,17 @@ impl VTable for ParquetVariant { None => None, }; - vortex_ensure!(matches!(dtype, DType::Variant(_)), "Expected Variant DType"); + vortex_ensure!(matches!(dtype, DType::Variant(_)), MismatchedTypes: "Expected Variant DType"); let has_typed_value = typed_value_dtype.is_some(); vortex_ensure!( proto.has_value || has_typed_value, - "At least one of value or typed_value must be present" + InvalidArgument: "At least one of value or typed_value must be present" ); let expected_children = 1 + proto.has_value as usize + has_typed_value as usize; vortex_ensure!( children.len() == expected_children || children.len() == expected_children + 1, - "Expected {} or {} children, got {}", + InvalidArgument: "Expected {} or {} children, got {}", expected_children, expected_children + 1, children.len() @@ -250,8 +250,9 @@ impl VTable for ParquetVariant { let typed_value = if has_typed_value { // typed_value can be any type — primitive, list, struct, etc. - let dtype = typed_value_dtype - .ok_or_else(|| vortex_err!("typed_value_dtype missing for typed_value child"))?; + let dtype = typed_value_dtype.ok_or_else( + || vortex_err!(NotFound: "typed_value_dtype missing for typed_value child"), + )?; let tv = children.get(child_idx, &dtype, len)?; Some(tv) } else { @@ -407,12 +408,10 @@ mod tests { vortex_file::register_default_encodings(&session); session.arrays().register(ParquetVariant); let editions = session.editions(); - editions - .declare_edition(Edition { - id: TEST_EDITION, - min_library_version: None, - }) - .map_err(|error| vortex_err!("{error}"))?; + editions.declare_edition(Edition { + id: TEST_EDITION, + min_library_version: None, + })?; let component_ids = [ ( ComponentKind::Array, @@ -438,9 +437,7 @@ mod tests { ]; for (kind, ids) in component_ids { for id in ids { - editions - .declare_inclusion(EditionInclusion::new(kind, &id, TEST_EDITION)) - .map_err(|error| vortex_err!("{error}"))?; + editions.declare_inclusion(EditionInclusion::new(kind, &id, TEST_EDITION))?; } } for id in [ @@ -451,17 +448,13 @@ mod tests { "vortex.nan_count", "vortex.null_count", ] { - editions - .declare_inclusion(EditionInclusion::new( - ComponentKind::Aggregate, - id, - TEST_EDITION, - )) - .map_err(|error| vortex_err!("{error}"))?; + editions.declare_inclusion(EditionInclusion::new( + ComponentKind::Aggregate, + id, + TEST_EDITION, + ))?; } - session - .enable_edition(TEST_EDITION) - .map_err(|error| vortex_err!("{error}"))?; + session.enable_edition(TEST_EDITION)?; Ok(session) } @@ -481,17 +474,17 @@ mod tests { .into_array() .execute::(&mut ctx)? else { - return Err(vortex_err!("expected canonical variant")); + return Err(vortex_err!(MismatchedTypes: "expected canonical variant")); }; let core_storage = variant .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; assert!(core_storage.typed_value().is_none()); let shredded = variant .shredded() - .ok_or_else(|| vortex_err!("expected canonical shredded child"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))?; assert_eq!( shredded.dtype(), &DType::Primitive(PType::I32, Nullability::Nullable) @@ -591,10 +584,10 @@ mod tests { assert!(array.array_eq(&decoded, EqMode::Value)); let decoded_pv = decoded .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant array"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; let typed = decoded_pv .typed_value() - .ok_or_else(|| vortex_err!("expected typed_value child"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; assert_eq!(typed.dtype(), &DType::Variant(Nullability::NonNullable)); Ok(()) } @@ -614,7 +607,7 @@ mod tests { assert_eq!(decoded.dtype(), &DType::Variant(Nullability::Nullable)); let decoded_pv = decoded .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant array"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; assert!(decoded_pv.value().is_some()); assert!(decoded_pv.typed_value().is_none()); Ok(()) @@ -638,10 +631,10 @@ mod tests { assert!(array.array_eq(&decoded, EqMode::Value)); let decoded_pv = decoded .as_opt::() - .ok_or_else(|| vortex_err!("expected parquet variant array"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; let typed = decoded_pv .typed_value() - .ok_or_else(|| vortex_err!("expected typed_value child"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; assert_eq!( typed.dtype(), &DType::Primitive(PType::I32, Nullability::NonNullable) diff --git a/encodings/pco/src/array.rs b/encodings/pco/src/array.rs index c1a4347cd94..9a2c8591830 100644 --- a/encodings/pco/src/array.rs +++ b/encodings/pco/src/array.rs @@ -217,7 +217,7 @@ impl VTable for Pco { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("PcoArray expected 0 or 1 child, got {}", children.len()); + vortex_bail!(MismatchedTypes: "PcoArray expected 0 or 1 child, got {}", children.len()); }; vortex_ensure!(buffers.len() >= metadata.chunks.len()); @@ -316,7 +316,10 @@ pub(crate) fn vortex_err_from_pco(err: PcoError) -> VortexError { match err.kind { Io(io_kind) => VortexError::from(std::io::Error::new(io_kind, err.message)), InvalidArgument => vortex_err!(InvalidArgument: "{}", err.message), - other => vortex_err!("Pco {:?} error: {}", other, err.message), + kind @ (Corruption | InsufficientData) => { + vortex_err!(Serde: "Pco {:?} error: {}", kind, err.message) + } + other => vortex_err!(Other: "Pco {:?} error: {}", other, err.message), } } @@ -407,20 +410,24 @@ impl PcoData { /// Validate dtype, validity, slice, and Pco component invariants. pub fn validate(&self, dtype: &DType, len: usize, validity: &Validity) -> VortexResult<()> { let _ = number_type_from_ptype(self.ptype); - vortex_ensure_eq!(dtype.as_ptype(), self.ptype); - vortex_ensure_eq!(dtype.nullability(), validity.nullability()); + vortex_ensure_eq!(dtype.as_ptype(), self.ptype, MismatchedTypes); + vortex_ensure_eq!(dtype.nullability(), validity.nullability(), InvalidArgument); vortex_ensure!( self.slice_start <= self.slice_stop && self.slice_stop <= self.unsliced_n_rows, - "invalid slice range {}..{} for {} rows", + InvalidArgument: "invalid slice range {}..{} for {} rows", self.slice_start, self.slice_stop, self.unsliced_n_rows ); - vortex_ensure_eq!(self.slice_stop - self.slice_start, len); + vortex_ensure_eq!(self.slice_stop - self.slice_start, len, InvalidArgument); if let Some(validity_len) = validity.maybe_len() { - vortex_ensure_eq!(validity_len, self.unsliced_n_rows); + vortex_ensure_eq!(validity_len, self.unsliced_n_rows, InvalidArgument); } - vortex_ensure_eq!(self.chunk_metas.len(), self.metadata.chunks.len()); + vortex_ensure_eq!( + self.chunk_metas.len(), + self.metadata.chunks.len(), + InvalidArgument + ); vortex_ensure_eq!( self.pages.len(), self.metadata @@ -428,7 +435,7 @@ impl PcoData { .iter() .map(|chunk| chunk.pages.len()) .sum::(), - "page count does not match metadata" + InvalidArgument: "page count does not match metadata" ); let mut n_values = 0usize; @@ -438,33 +445,33 @@ impl PcoData { let page_n_values = page.n_values as usize; vortex_ensure!( page_n_values != 0, - "Pco chunk {chunk_idx} contains an empty page" + InvalidArgument: "Pco chunk {chunk_idx} contains an empty page" ); - chunk_n_values = chunk_n_values.checked_add(page_n_values).ok_or_else(|| { - vortex_err!("Pco chunk {chunk_idx} value count overflows usize") - })?; + chunk_n_values = chunk_n_values.checked_add(page_n_values).ok_or_else( + || vortex_err!(Overflow: "Pco chunk {chunk_idx} value count overflows usize"), + )?; } vortex_ensure!( chunk_n_values <= VALUES_PER_CHUNK, - "Pco chunk {chunk_idx} contains {chunk_n_values} values, exceeding the maximum of {VALUES_PER_CHUNK}" + InvalidArgument: "Pco chunk {chunk_idx} contains {chunk_n_values} values, exceeding the maximum of {VALUES_PER_CHUNK}" ); n_values = n_values .checked_add(chunk_n_values) - .ok_or_else(|| vortex_err!("Pco value count overflows usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "Pco value count overflows usize"))?; } vortex_ensure!( n_values <= self.unsliced_n_rows, - "Pco contains {n_values} values for only {} rows", + InvalidArgument: "Pco contains {n_values} values for only {} rows", self.unsliced_n_rows ); if validity.definitely_no_nulls() { vortex_ensure_eq!( n_values, self.unsliced_n_rows, - "Pco value count must match the row count of a non-null array" + InvalidArgument: "Pco value count must match the row count of a non-null array" ); } else if validity.definitely_all_null() { - vortex_ensure_eq!(n_values, 0, "Pco contains values for an all-null array"); + vortex_ensure_eq!(n_values, 0, InvalidArgument: "Pco contains values for an all-null array"); } Ok(()) } @@ -599,7 +606,7 @@ impl PcoData { ) -> VortexResult { let parray = array.try_downcast::().map_err(|a| { vortex_err!( - "Pco can only encode primitive arrays, got {}", + MismatchedTypes: "Pco can only encode primitive arrays, got {}", a.encoding_id() ) })?; @@ -677,7 +684,7 @@ impl PcoData { let page: &[u8] = self .pages .get(page_idx) - .ok_or_else(|| vortex_err!("Missing Pco page {page_idx}"))? + .ok_or_else(|| vortex_err!(NotFound: "Missing Pco page {page_idx}"))? .as_ref(); let mut cd = match chunk_decompressor.take() { @@ -713,7 +720,7 @@ impl PcoData { let value_stop = value_offset + slice_n_values; vortex_ensure!( value_stop <= decompressed_values.len(), - "Pco contains {} decompressed values, but the requested range ends at {value_stop}", + InvalidArgument: "Pco contains {} decompressed values, but the requested range ends at {value_stop}", decompressed_values.len() ); Ok(decompressed_values diff --git a/encodings/runend/src/array.rs b/encodings/runend/src/array.rs index 787a5a02ecd..1a652cb32cf 100644 --- a/encodings/runend/src/array.rs +++ b/encodings/runend/src/array.rs @@ -112,11 +112,11 @@ impl VTable for RunEnd { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("RunEndArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "RunEndArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("RunEndArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "RunEndArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -307,7 +307,7 @@ impl RunEnd { let data = unsafe { RunEndData::new_unchecked(0) }; Array::try_from_parts(ArrayParts::new(RunEnd, dtype, len, data, slots)) } else { - vortex_bail!("REE can only encode primitive arrays") + vortex_bail!(MismatchedTypes: "REE can only encode primitive arrays") } } } @@ -375,14 +375,14 @@ impl RunEndData { // DType validation vortex_ensure!( ends.dtype().is_unsigned_int(), - "run ends must be unsigned integers, was {}", + MismatchedTypes: "run ends must be unsigned integers, was {}", ends.dtype(), ); vortex_ensure_eq!(ends.len(), values.len()); // Handle empty run-ends if ends.is_empty() { - vortex_ensure_eq!(offset, 0, "non-zero offset provided for empty RunEndArray"); + vortex_ensure_eq!(offset, 0, InvalidArgument: "non-zero offset provided for empty RunEndArray"); return Ok(false); } @@ -398,12 +398,12 @@ impl RunEndData { length: usize, ) -> VortexResult<()> { if first_run_end < offset { - vortex_bail!("First run end {first_run_end} must be >= offset {offset}"); + vortex_bail!(InvalidArgument: "First run end {first_run_end} must be >= offset {offset}"); } let min_required_end = offset + length; if last_run_end < min_required_end { - vortex_bail!("Last run end {last_run_end} must be >= offset+length {min_required_end}"); + vortex_bail!(InvalidArgument: "Last run end {last_run_end} must be >= offset+length {min_required_end}"); } Ok(()) @@ -465,7 +465,7 @@ impl RunEndData { // SAFETY: runend_encode handles this unsafe { Ok(Self::new_unchecked(0)) } } else { - vortex_bail!("REE can only encode primitive arrays") + vortex_bail!(MismatchedTypes: "REE can only encode primitive arrays") } } @@ -532,7 +532,7 @@ pub(super) fn run_end_canonicalize( .execute_as::("values", ctx)?; runend_decode_listview(pends, values, array.offset(), array.len())?.into_array() } - _ => vortex_bail!("Unsupported RunEnd value type: {}", array.dtype()), + _ => vortex_bail!(InvalidArgument: "Unsupported RunEnd value type: {}", array.dtype()), }) } diff --git a/encodings/runend/src/compute/take.rs b/encodings/runend/src/compute/take.rs index 047a072e9ab..c61da1c8733 100644 --- a/encodings/runend/src/compute/take.rs +++ b/encodings/runend/src/compute/take.rs @@ -293,7 +293,7 @@ fn prefer_linear_scan( fn check_index(index: usize, array_len: usize) -> VortexResult<()> { if index >= array_len { - vortex_bail!(OutOfBounds: index, 0, array_len); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", index, 0, array_len); } Ok(()) } diff --git a/encodings/runend/src/iter.rs b/encodings/runend/src/iter.rs index 0e2f9bc30f7..356e2ff05ca 100644 --- a/encodings/runend/src/iter.rs +++ b/encodings/runend/src/iter.rs @@ -13,14 +13,14 @@ pub fn trimmed_ends_iter( ) -> impl Iterator + use<'_, E> { let offset_e = E::from_usize(offset).unwrap_or_else(|| { vortex_panic!( - "offset {} cannot be converted to {}", + Overflow: "offset {} cannot be converted to {}", offset, std::any::type_name::() ) }); let length_e = E::from_usize(length).unwrap_or_else(|| { vortex_panic!( - "length {} cannot be converted to {}", + Overflow: "length {} cannot be converted to {}", length, std::any::type_name::() ) @@ -30,7 +30,7 @@ pub fn trimmed_ends_iter( .copied() .map(move |v| { if v < offset_e { - vortex_panic!("run end {v} must be >= offset {offset}"); + vortex_panic!(AssertionFailed: "run end {v} must be >= offset {offset}"); } v - offset_e }) diff --git a/encodings/runend/src/probe.rs b/encodings/runend/src/probe.rs index abcb3d22e0d..9332d2b4916 100644 --- a/encodings/runend/src/probe.rs +++ b/encodings/runend/src/probe.rs @@ -22,13 +22,13 @@ pub(crate) fn scalar_at( let logical_index = array .offset() .checked_add(index) - .ok_or_else(|| vortex_err!("RunEnd logical index overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "RunEnd logical index overflow"))?; // Search for the first end strictly greater than the logical index. Every comparison // uses the same ends probe, so a retained read keeps the child's preparation within and // between searches. let mut ends = state .slot(RunEndSlots::ENDS)? - .ok_or_else(|| vortex_err!("RunEnd ends slot is missing"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "RunEnd ends slot is missing"))?; let mut left = 0; let mut right = ends.array().len(); while left < right { @@ -42,7 +42,7 @@ pub(crate) fn scalar_at( } state .slot(RunEndSlots::VALUES)? - .ok_or_else(|| vortex_err!("RunEnd values slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "RunEnd values slot is missing"))? .execute_scalar(left, ctx) } diff --git a/encodings/sequence/src/array.rs b/encodings/sequence/src/array.rs index f6ead2c5230..963c6a30941 100644 --- a/encodings/sequence/src/array.rs +++ b/encodings/sequence/src/array.rs @@ -127,14 +127,14 @@ impl SequenceData { length: usize, ) -> VortexResult<()> { let DType::Primitive(ptype, _) = dtype else { - vortex_bail!("only primitive dtypes are supported in SequenceArray currently"); + vortex_bail!(NotImplemented: "only primitive dtypes are supported in SequenceArray currently"); }; if !ptype.is_int() { - vortex_bail!("only integer ptypes are supported in SequenceArray currently") + vortex_bail!(NotImplemented: "only integer ptypes are supported in SequenceArray currently") } - vortex_ensure!(length > 0, "SequenceArray length must be greater than zero"); + vortex_ensure!(length > 0, InvalidArgument: "SequenceArray length must be greater than zero"); Self::narrowed_base(base, *ptype)?; Self::ensure_last_expressible(base, multiplier, *ptype, length) @@ -149,7 +149,7 @@ impl SequenceData { ) -> VortexResult<()> { let steps = (length - 1) as u64; let (ascending, magnitude) = eval::step_parts(multiplier) - .ok_or_else(|| vortex_err!("step {multiplier} must be an integer"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "step {multiplier} must be an integer"))?; if steps == 0 || magnitude == 0 { return Ok(()); } @@ -171,7 +171,7 @@ impl SequenceData { vortex_ensure!( steps <= room / magnitude, - "final value not expressible, base = {base:?}, multiplier = {multiplier:?}, len = {length}" + Overflow: "final value not expressible, base = {base:?}, multiplier = {multiplier:?}, len = {length}" ); Ok(()) } @@ -182,16 +182,18 @@ impl SequenceData { match multiplier .kind .as_ref() - .ok_or_else(|| vortex_err!("multiplier value missing kind"))? + .ok_or_else(|| vortex_err!(Serde: "multiplier value missing kind"))? { Kind::Int64Value(_) => Ok(PType::I64), Kind::Uint64Value(_) => Ok(PType::U64), - _ => vortex_bail!("only integer ptypes are supported in SequenceArray currently"), + _ => { + vortex_bail!(NotImplemented: "only integer ptypes are supported in SequenceArray currently") + } } } fn narrowed_base(base: PValue, ptype: PType) -> VortexResult { - vortex_ensure!(base.ptype().is_int(), "base {base} must be an integer"); + vortex_ensure!(base.ptype().is_int(), MismatchedTypes: "base {base} must be an integer"); match_each_integer_ptype!(ptype, |P| { Ok(PValue::from(base.cast::

()?)) }) } @@ -210,7 +212,7 @@ impl SequenceData { let v: i64 = v.as_(); PValue::from(v) }, - float: |v| { vortex_bail!("step {v} must be an integer") } + float: |v| { vortex_bail!(MismatchedTypes: "step {v} must be an integer") } ); Ok((base, multiplier)) @@ -245,7 +247,7 @@ impl SequenceData { pub(crate) fn wrapping_parts(&self) -> VortexResult<(O, O)> { eval::wrapping_parts(self.base, self.multiplier).ok_or_else(|| { vortex_err!( - "SequenceArray values must be integers, got base {:?} and step {:?}", + MismatchedTypes: "SequenceArray values must be integers, got base {:?} and step {:?}", self.base, self.multiplier ) @@ -319,11 +321,11 @@ impl VTable for Sequence { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("SequenceArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "SequenceArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("SequenceArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "SequenceArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -357,17 +359,17 @@ impl VTable for Sequence { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - "SequenceArray expects 0 buffers, got {}", + InvalidArgument: "SequenceArray expects 0 buffers, got {}", buffers.len() ); vortex_ensure!( children.is_empty(), - "SequenceArray expects 0 children, got {}", + InvalidArgument: "SequenceArray expects 0 children, got {}", children.len() ); let DType::Primitive(output_ptype, _) = dtype else { vortex_bail!( - "only primitive dtypes are supported in SequenceArray currently, got {dtype}" + NotImplemented: "only primitive dtypes are supported in SequenceArray currently, got {dtype}" ); }; let metadata = SequenceMetadata::decode(metadata)?; @@ -375,12 +377,12 @@ impl VTable for Sequence { let base_metadata = metadata .base .as_ref() - .ok_or_else(|| vortex_err!("base required"))?; + .ok_or_else(|| vortex_err!(Serde: "base required"))?; let multiplier_metadata = metadata .multiplier .as_ref() - .ok_or_else(|| vortex_err!("multiplier required"))?; + .ok_or_else(|| vortex_err!(Serde: "multiplier required"))?; // We go via Scalar to validate that the value is valid for the ptype. let base = Scalar::from_proto_value( @@ -743,9 +745,9 @@ mod tests { &SESSION, )?; - let decoded_sequence = decoded - .as_opt::() - .ok_or_else(|| vortex_err!("decoded array should still be a SequenceArray"))?; + let decoded_sequence = decoded.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "decoded array should still be a SequenceArray"), + )?; assert_eq!(decoded_sequence.ptype(), output_ptype); assert_eq!(decoded_sequence.multiplier(), array.multiplier()); assert_eq!(decoded.dtype(), &dtype); diff --git a/encodings/sequence/src/compute/min_max.rs b/encodings/sequence/src/compute/min_max.rs index adb0781657f..a229c7961b3 100644 --- a/encodings/sequence/src/compute/min_max.rs +++ b/encodings/sequence/src/compute/min_max.rs @@ -50,8 +50,9 @@ impl DynAggregateKernel for SequenceMinMaxKernel { // A sequence's extrema are its first and last values. let last = seq.index_value(seq.len() - 1); - let (ascending, _) = eval::step_parts(seq.multiplier()) - .ok_or_else(|| vortex_err!("step {} must be an integer", seq.multiplier()))?; + let (ascending, _) = eval::step_parts(seq.multiplier()).ok_or_else( + || vortex_err!(MismatchedTypes: "step {} must be an integer", seq.multiplier()), + )?; let (min_pvalue, max_pvalue) = if ascending { (seq.base(), last) @@ -111,7 +112,9 @@ mod tests { &mut SESSION.create_execution_ctx(), NumericalAggregateOpts::default(), )? - .ok_or_else(|| vortex_err!("min_max of a non-empty sequence should not be null"))?; + .ok_or_else( + || vortex_err!(AssertionFailed: "min_max of a non-empty sequence should not be null"), + )?; assert_eq!(min, Scalar::from(60u8)); assert_eq!(max, Scalar::from(100u8)); diff --git a/encodings/sequence/src/compute/take.rs b/encodings/sequence/src/compute/take.rs index daf23a713ad..9525eebe12b 100644 --- a/encodings/sequence/src/compute/take.rs +++ b/encodings/sequence/src/compute/take.rs @@ -47,7 +47,12 @@ fn take_inner( let validity = match indices_mask.bit_buffer() { AllOr::All => { if let Err(position) = indices.try_map_into(out, value_at) { - vortex_panic!(OutOfBounds: indices[position].as_(), 0, len); + vortex_panic!( + OutOfBounds: "index {} out of bounds from {} to {}", + indices[position].as_(), + 0, + len + ); } Validity::from(result_nullability) } @@ -60,7 +65,12 @@ fn take_inner( } AllOr::Some(bits) => { if let Err(position) = indices.try_map_masked_into(bits, out, value_at) { - vortex_panic!(OutOfBounds: indices[position].as_(), 0, len); + vortex_panic!( + OutOfBounds: "index {} out of bounds from {} to {}", + indices[position].as_(), + 0, + len + ); } Validity::from(bits.clone()) } diff --git a/encodings/sequence/src/model_tests.rs b/encodings/sequence/src/model_tests.rs index 9bfb4624bf0..9db8962c2b8 100644 --- a/encodings/sequence/src/model_tests.rs +++ b/encodings/sequence/src/model_tests.rs @@ -122,7 +122,7 @@ fn values(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult> { fn constant(value: i128, ptype: PType, len: usize) -> VortexResult { let value = narrow(value, ptype) - .ok_or_else(|| vortex_err!("{value} is not representable in {ptype}"))?; + .ok_or_else(|| vortex_err!(Overflow: "{value} is not representable in {ptype}"))?; let scalar = Scalar::try_new( DType::Primitive(ptype, NonNullable), Some(ScalarValue::Primitive(value)), diff --git a/encodings/sparse/src/canonical.rs b/encodings/sparse/src/canonical.rs index 7430228e931..de8aa616b67 100644 --- a/encodings/sparse/src/canonical.rs +++ b/encodings/sparse/src/canonical.rs @@ -103,7 +103,9 @@ impl SparseStringParts { .cloned() .map(BufferString::into_inner), DType::Binary(_) => fill_scalar.as_binary().value().cloned(), - dtype => vortex_bail!("Sparse string decode of non-string dtype {dtype}"), + dtype => { + vortex_bail!(MismatchedTypes: "Sparse string decode of non-string dtype {dtype}") + } }; Ok(Self { len: array.len(), @@ -247,7 +249,7 @@ where } vortex_ensure!( previous <= row && row < len, - "Sparse patch indices must be ascending within the array length {len}" + InvalidArgument: "Sparse patch indices must be ascending within the array length {len}" ); fill_run(builder, row - previous)?; if patch_validity.value(patch) { @@ -346,7 +348,9 @@ pub(super) fn execute_sparse(parts: SparseParts, ctx: &mut ExecutionCtx) -> Vort DType::FixedSizeList(.., nullability) => { execute_sparse_fixed_size_list(&patches, &fill_value, len, *nullability, ctx)? } - DType::Map(..) => vortex_bail!("Sparse canonicalization does not support Map arrays yet"), + DType::Map(..) => { + vortex_bail!(InvalidArgument: "Sparse canonicalization does not support Map arrays yet") + } DType::Struct(struct_fields, ..) => execute_sparse_struct( struct_fields, fill_value.as_struct(), @@ -355,10 +359,14 @@ pub(super) fn execute_sparse(parts: SparseParts, ctx: &mut ExecutionCtx) -> Vort len, ctx, )?, - DType::Union(..) => vortex_bail!("TODO(connor)[Union]: unimplemented"), - DType::Variant(_) => vortex_bail!("Sparse canonicalization does not support Variant"), + DType::Union(..) => vortex_bail!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Variant(_) => { + vortex_bail!(InvalidArgument: "Sparse canonicalization does not support Variant") + } DType::Extension(..) => { - vortex_bail!("Sparse canonicalization does not support Extension arrays yet") + vortex_bail!( + NotImplemented: "Sparse canonicalization does not support Extension arrays yet" + ) } }) } diff --git a/encodings/sparse/src/compute/sum.rs b/encodings/sparse/src/compute/sum.rs index c02e3e04e44..c55d3f9c5e5 100644 --- a/encodings/sparse/src/compute/sum.rs +++ b/encodings/sparse/src/compute/sum.rs @@ -116,12 +116,12 @@ mod tests { .aggregate_fns() .find_aggregate_kernel(arr.encoding_id(), aggregate.id()) else { - vortex_bail!("Sparse SumV2 kernel is not registered"); + vortex_bail!(NotFound: "Sparse SumV2 kernel is not registered"); }; let Some(partial) = kernel.aggregate(&aggregate, arr, &mut SESSION.create_execution_ctx())? else { - vortex_bail!("Sparse SumV2 kernel declined the aggregate"); + vortex_bail!(AssertionFailed: "Sparse SumV2 kernel declined the aggregate"); }; let mut accumulator = Accumulator::try_new(SumV2, options, arr.dtype().clone())?; diff --git a/encodings/sparse/src/lib.rs b/encodings/sparse/src/lib.rs index 55e5ed883e2..655bb6ddd22 100644 --- a/encodings/sparse/src/lib.rs +++ b/encodings/sparse/src/lib.rs @@ -231,14 +231,14 @@ impl VTable for Sparse { ScalarValue::to_proto_bytes::>(array.fill_value.value()).into(); BufferHandle::new_host(fill_value_buffer) } - _ => vortex_panic!("SparseArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "SparseArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("fill_value".to_string()), - _ => vortex_panic!("SparseArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "SparseArray buffer_name index {idx} out of bounds"), } } @@ -275,14 +275,14 @@ impl VTable for Sparse { // Once we have the patches metadata, we need to get the fill value from the buffers. if buffers.len() != 1 { - vortex_bail!("Expected 1 buffer, got {}", buffers.len()); + vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); } let scalar_bytes: &[u8] = &buffers[0].clone().try_to_host_sync()?; let scalar_value = ScalarValue::from_proto_bytes(scalar_bytes, dtype, session)?; let fill_value = Scalar::try_new(dtype.clone(), scalar_value)?; - vortex_ensure_eq!(children.len(), 2, "SparseArray expects 2 children"); + vortex_ensure_eq!(children.len(), 2, InvalidArgument: "SparseArray expects 2 children"); let patch_indices = children.get( 0, @@ -437,7 +437,7 @@ impl Sparse { vortex_ensure_eq!( values.dtype(), &dtype, - "sparse values dtype must match fill value dtype" + MismatchedTypes: "sparse values dtype must match fill value dtype" ); let patches = Patches::new(len, 0, indices, values, None, ctx)?; let slots = SparseData::make_slots(&patches); @@ -486,9 +486,9 @@ impl SparseData { dtype: &DType, len: usize, ) -> VortexResult<()> { - vortex_ensure_eq!(fill_value.dtype(), dtype); - vortex_ensure_eq!(patches.array_len(), len); - vortex_ensure_eq!(patches.values().dtype(), dtype); + vortex_ensure_eq!(fill_value.dtype(), dtype, MismatchedTypes); + vortex_ensure_eq!(patches.array_len(), len, InvalidArgument); + vortex_ensure_eq!(patches.values().dtype(), dtype, MismatchedTypes); Ok(()) } @@ -514,7 +514,11 @@ impl SparseData { /// Patch values must already match the fill dtype; callers are expected to construct patches /// with the correct dtype rather than relying on this to normalize them. fn from_patches(patches: &Patches, fill_value: Scalar) -> VortexResult { - vortex_ensure_eq!(patches.values().dtype(), fill_value.dtype()); + vortex_ensure_eq!( + patches.values().dtype(), + fill_value.dtype(), + MismatchedTypes + ); Ok(Self::from_patches_unchecked(patches, fill_value)) } @@ -568,7 +572,7 @@ impl SparseData { && !array.dtype().eq_ignore_nullability(fill_value.dtype()) { vortex_bail!( - "Array and fill value types must have the same base type. got {} and {}", + MismatchedTypes: "Array and fill value types must have the same base type. got {} and {}", array.dtype(), fill_value.dtype() ) diff --git a/encodings/uuid/src/arrow.rs b/encodings/uuid/src/arrow.rs index 55202147633..79af83b6ca5 100644 --- a/encodings/uuid/src/arrow.rs +++ b/encodings/uuid/src/arrow.rs @@ -581,7 +581,7 @@ mod tests { .downcast_ref::>() .ok_or_else(|| { vortex_err!( - "expected an Int32 run-end array, got {}", + MismatchedTypes: "expected an Int32 run-end array, got {}", exported.data_type() ) })?; diff --git a/encodings/uuid/src/metadata.rs b/encodings/uuid/src/metadata.rs index 986e0330d71..83b212675be 100644 --- a/encodings/uuid/src/metadata.rs +++ b/encodings/uuid/src/metadata.rs @@ -26,7 +26,7 @@ pub(crate) fn u8_to_version(b: u8) -> VortexResult { // UUID crate changed from 0xff to 0x0f for maximum uuid version in 1.23.0 0x0f => Ok(Version::Max), 0xff => Ok(Version::Max), - _ => vortex_bail!("unknown UUID version discriminant: {b}"), + _ => vortex_bail!(Serde: "unknown UUID version discriminant: {b}"), } } diff --git a/encodings/uuid/src/vtable.rs b/encodings/uuid/src/vtable.rs index f937e8fd81d..7ae5191d244 100644 --- a/encodings/uuid/src/vtable.rs +++ b/encodings/uuid/src/vtable.rs @@ -44,7 +44,9 @@ impl ExtVTable for Uuid { let version = match metadata.len() { 0 => None, 1 => Some(u8_to_version(metadata[0])?), - other => vortex_bail!("UUID metadata must be 0 or 1 bytes, got {other}"), + other => { + vortex_bail!(InvalidArgument: "UUID metadata must be 0 or 1 bytes, got {other}") + } }; Ok(UuidMetadata { version }) @@ -53,23 +55,23 @@ impl ExtVTable for Uuid { fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { let storage_dtype = ext_dtype.storage_dtype(); let DType::FixedSizeList(element_dtype, list_size, _nullability) = storage_dtype else { - vortex_bail!("UUID storage dtype must be a FixedSizeList, got {storage_dtype}"); + vortex_bail!(InvalidArgument: "UUID storage dtype must be a FixedSizeList, got {storage_dtype}"); }; vortex_ensure_eq!( *list_size as usize, UUID_BYTE_LEN, - "UUID storage FixedSizeList size mismatch" + InvalidArgument: "UUID storage FixedSizeList size mismatch" ); let DType::Primitive(ptype, elem_nullability) = element_dtype.as_ref() else { - vortex_bail!("UUID element dtype must be Primitive(U8), got {element_dtype}"); + vortex_bail!(MismatchedTypes: "UUID element dtype must be Primitive(U8), got {element_dtype}"); }; - vortex_ensure_eq!(*ptype, PType::U8, "UUID element dtype must be U8"); + vortex_ensure_eq!(*ptype, PType::U8, MismatchedTypes: "UUID element dtype must be U8"); vortex_ensure!( !elem_nullability.is_nullable(), - "UUID element dtype must be non-nullable" + InvalidArgument: "UUID element dtype must be non-nullable" ); Ok(()) @@ -83,16 +85,16 @@ impl ExtVTable for Uuid { vortex_ensure_eq!( elements.len(), UUID_BYTE_LEN, - "UUID scalar byte length mismatch" + InvalidArgument: "UUID scalar byte length mismatch" ); let mut bytes = [0u8; UUID_BYTE_LEN]; for (i, elem) in elements.iter().enumerate() { let Some(scalar_value) = elem else { - vortex_bail!("UUID byte at index {i} must not be null"); + vortex_bail!(InvalidArgument: "UUID byte at index {i} must not be null"); }; let PValue::U8(b) = scalar_value.as_primitive() else { - vortex_bail!("UUID byte at index {i} must be U8"); + vortex_bail!(InvalidArgument: "UUID byte at index {i} must be U8"); }; bytes[i] = *b; } @@ -102,12 +104,11 @@ impl ExtVTable for Uuid { // Verify the parsed UUID matches the expected version, if one is set. if let Some(expected) = ext_dtype.metadata().version { let expected = expected as u8; - let actual = parsed - .get_version() - .ok_or_else(|| vortex_err!("UUID has unrecognized version nibble"))? - as u8; + let actual = parsed.get_version().ok_or_else( + || vortex_err!(InvalidArgument: "UUID has unrecognized version nibble"), + )? as u8; - vortex_ensure_eq!(expected, actual, "UUID version mismatch"); + vortex_ensure_eq!(expected, actual, InvalidArgument: "UUID version mismatch"); } Ok(parsed) @@ -223,7 +224,7 @@ mod tests { #[test] fn unpack_native_uuid() -> VortexResult<()> { let expected = uuid::Uuid::parse_str("550e8400-e29b-41d4-a716-446655440000") - .map_err(|e| vortex_error::vortex_err!("{e}"))?; + .map_err(|e| vortex_error::vortex_err!(InvalidArgument: "{e}"))?; let ext_dtype = ExtDType::try_new( UuidMetadata::default(), @@ -240,9 +241,9 @@ mod tests { Nullability::NonNullable, ); - let storage_value = storage_scalar - .value() - .ok_or_else(|| vortex_error::vortex_err!("expected non-null scalar"))?; + let storage_value = storage_scalar.value().ok_or_else( + || vortex_error::vortex_err!(MismatchedTypes: "expected non-null scalar"), + )?; let result = Uuid::unpack_native(&ext_dtype, storage_value)?; assert_eq!(result, expected); assert_eq!(result.to_string(), "550e8400-e29b-41d4-a716-446655440000"); @@ -253,7 +254,7 @@ mod tests { fn unpack_native_rejects_version_mismatch() -> VortexResult<()> { // This is a v4 UUID. let v4_uuid = uuid::Uuid::parse_str("550e8400-e29b-41d4-a716-446655440000") - .map_err(|e| vortex_error::vortex_err!("{e}"))?; + .map_err(|e| vortex_error::vortex_err!(InvalidArgument: "{e}"))?; assert_eq!(v4_uuid.get_version(), Some(Version::Random)); // Metadata says v7, but the UUID is v4. @@ -275,9 +276,9 @@ mod tests { Nullability::NonNullable, ); - let storage_value = storage_scalar - .value() - .ok_or_else(|| vortex_error::vortex_err!("expected non-null scalar"))?; + let storage_value = storage_scalar.value().ok_or_else( + || vortex_error::vortex_err!(MismatchedTypes: "expected non-null scalar"), + )?; assert!(Uuid::unpack_native(&ext_dtype, storage_value).is_err()); Ok(()) } @@ -301,7 +302,7 @@ mod tests { fn unpack_native_accepts_matching_version() -> VortexResult<()> { // This is a v4 UUID. let v4_uuid = uuid::Uuid::parse_str("550e8400-e29b-41d4-a716-446655440000") - .map_err(|e| vortex_error::vortex_err!("{e}"))?; + .map_err(|e| vortex_error::vortex_err!(InvalidArgument: "{e}"))?; let ext_dtype = ExtDType::try_new( UuidMetadata { diff --git a/encodings/zigzag/src/array.rs b/encodings/zigzag/src/array.rs index 25fed1c159e..556e0ac03bc 100644 --- a/encodings/zigzag/src/array.rs +++ b/encodings/zigzag/src/array.rs @@ -67,8 +67,8 @@ impl VTable for ZigZag { ) -> VortexResult<()> { let encoded = ZigZagSlotsView::from_slots(slots).encoded; let expected_dtype = ZigZagData::dtype_from_encoded_dtype(encoded.dtype())?; - vortex_ensure_eq!(dtype, &expected_dtype); - vortex_ensure_eq!(encoded.len(), len); + vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes); + vortex_ensure_eq!(encoded.len(), len, InvalidArgument); Ok(()) } @@ -77,11 +77,11 @@ impl VTable for ZigZag { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ZigZagArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ZigZagArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("ZigZagArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ZigZagArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -110,12 +110,12 @@ impl VTable for ZigZag { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "ZigZagArray expects empty metadata, got {} bytes", + InvalidArgument: "ZigZagArray expects empty metadata, got {} bytes", metadata.len() ); } if children.len() != 1 { - vortex_bail!("Expected 1 child, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 1 child, got {}", children.len()); } let ptype = PType::try_from(dtype)?; @@ -218,7 +218,7 @@ impl ZigZagData { pub fn try_new(encoded_dtype: &DType) -> VortexResult { if !encoded_dtype.is_unsigned_int() { - vortex_bail!(MismatchedTypes: "unsigned int", encoded_dtype); + vortex_bail!(MismatchedTypes: "expected type: unsigned int but instead got {}", encoded_dtype); } Self::dtype_from_encoded_dtype(encoded_dtype)?; @@ -244,7 +244,7 @@ impl OperationsVTable for ZigZag { let array = state.array(); let scalar = state .slot(ZigZagSlots::ENCODED)? - .ok_or_else(|| vortex_err!("ZigZag encoded slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "ZigZag encoded slot is missing"))? .execute_scalar(index, ctx)?; if scalar.is_null() { return scalar.primitive_reinterpret_cast(ZigZagArrayExt::ptype(&array)); diff --git a/encodings/zigzag/src/compress.rs b/encodings/zigzag/src/compress.rs index b7082d4514e..3d29d6c642e 100644 --- a/encodings/zigzag/src/compress.rs +++ b/encodings/zigzag/src/compress.rs @@ -28,7 +28,7 @@ pub fn zigzag_encode(parray: ArrayView<'_, Primitive>) -> VortexResult zigzag_encode_primitive::(parray.into_buffer_mut(), validity), PType::I64 => zigzag_encode_primitive::(parray.into_buffer_mut(), validity), _ => vortex_bail!( - "ZigZag can only encode signed integers, got {}", + MismatchedTypes: "ZigZag can only encode signed integers, got {}", parray.ptype() ), }; @@ -61,7 +61,7 @@ pub fn zigzag_decode(parray: PrimitiveArray) -> PrimitiveArray { PType::U32 => zigzag_decode_primitive::(parray.into_buffer_mut(), validity), PType::U64 => zigzag_decode_primitive::(parray.into_buffer_mut(), validity), _ => vortex_panic!( - "ZigZag can only decode unsigned integers, got {}", + MismatchedTypes: "ZigZag can only decode unsigned integers, got {}", parray.ptype() ), } diff --git a/encodings/zstd/src/array.rs b/encodings/zstd/src/array.rs index 78034a5fd83..c5059c70c8c 100644 --- a/encodings/zstd/src/array.rs +++ b/encodings/zstd/src/array.rs @@ -195,7 +195,7 @@ impl VTable for Zstd { let mut data = array.data().clone(); if data.dictionary.is_some() { let Some((dictionary, frames)) = buffers.split_first() else { - vortex_bail!("Expected dictionary buffer"); + vortex_bail!(MismatchedTypes: "Expected dictionary buffer"); }; data.dictionary = Some(dictionary.clone().try_to_host_sync()?); data.frames = frames @@ -240,7 +240,7 @@ impl VTable for Zstd { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("ZstdArray expected 0 or 1 child, got {}", children.len()); + vortex_bail!(MismatchedTypes: "ZstdArray expected 0 or 1 child, got {}", children.len()); }; let (dictionary_buffer, compressed_buffers) = if metadata.dictionary_size == 0 { @@ -398,7 +398,7 @@ fn append_to_varbinview( vortex_ensure_eq!( valid_views.len(), mask.true_count(), - "Corrupt zstd metadata: the decompressed frames must hold one value per valid row of \ + Serde: "Corrupt zstd metadata: the decompressed frames must hold one value per valid row of \ the slice" ); @@ -672,7 +672,7 @@ fn walk_views( buffers.push(buffer.slice(segment_start..offset)); segment_start = offset; let Some(next_index) = buf_index.checked_add(1) else { - error = Some(vortex_err!("Zstd values need more than u32::MAX buffers")); + error = Some(vortex_err!(Overflow: "Zstd values need more than u32::MAX buffers")); break; }; buf_index = next_index; @@ -680,14 +680,14 @@ fn walk_views( let Ok(local_offset) = u32::try_from(value_data_offset - segment_start) else { error = Some(vortex_err!( - "Zstd value offset {} does not fit in u32; max_buffer_len {max_buffer_len} is too large", + Overflow: "Zstd value offset {} does not fit in u32; max_buffer_len {max_buffer_len} is too large", value_data_offset - segment_start )); break; }; let Some(value) = buffer.get(value_data_offset..value_data_offset + str_len) else { error = Some(vortex_err!( - "Corrupt zstd value: {str_len} bytes at offset {value_data_offset} run past the \ + Serde: "Corrupt zstd value: {str_len} bytes at offset {value_data_offset} run past the \ end of the {} byte frame buffer", buffer.len() )); @@ -711,7 +711,7 @@ fn slice_views( ) -> VortexResult> { vortex_ensure!( range.end <= views.len(), - "Corrupt zstd metadata: values {}..{} are out of bounds of the {} values held by the \ + Serde: "Corrupt zstd metadata: values {}..{} are out of bounds of the {} values held by the \ decompressed frames", range.start, range.end, @@ -784,7 +784,7 @@ impl DecompressedSlice { .checked_sub(self.n_skipped_values) .ok_or_else(|| { vortex_err!( - "Corrupt zstd metadata: skipped frames hold {} values, past the first \ + Serde: "Corrupt zstd metadata: skipped frames hold {} values, past the first \ requested value {}", self.n_skipped_values, self.value_idx_start @@ -795,7 +795,7 @@ impl DecompressedSlice { .checked_sub(self.n_skipped_values) .ok_or_else(|| { vortex_err!( - "Corrupt zstd metadata: skipped frames hold {} values, past the last \ + Serde: "Corrupt zstd metadata: skipped frames hold {} values, past the last \ requested value {}", self.n_skipped_values, self.value_idx_stop @@ -803,7 +803,7 @@ impl DecompressedSlice { })?; vortex_ensure!( start <= end, - "Corrupt zstd metadata: value range {start}..{end} is not ascending" + Serde: "Corrupt zstd metadata: value range {start}..{end} is not ascending" ); Ok(start..end) } @@ -828,7 +828,7 @@ impl DecompressedSlice { }; vortex_ensure!( from <= to && to <= buffer.len(), - "Corrupt zstd metadata: values {from}..{to} are out of bounds of the {} byte frame \ + Serde: "Corrupt zstd metadata: values {from}..{to} are out of bounds of the {} byte frame \ buffer", buffer.len() ); @@ -843,7 +843,7 @@ impl DecompressedSlice { let buffer = self.bytes.as_slice(); let bytes = buffer.get(range.clone()).ok_or_else(|| { vortex_err!( - "Corrupt zstd metadata: values {}..{} are out of bounds of the {} byte frame \ + Serde: "Corrupt zstd metadata: values {}..{} are out of bounds of the {} byte frame \ buffer", range.start, range.end, @@ -852,11 +852,11 @@ impl DecompressedSlice { })?; // Every value carries a length prefix, so the region must be at least that large. let prefix_bytes = n_values.checked_mul(size_of::()).ok_or_else(|| { - vortex_err!("Corrupt zstd metadata: value count {n_values} overflows a byte count") + vortex_err!(Serde: "Corrupt zstd metadata: value count {n_values} overflows a byte count") })?; let num_bytes = bytes.len().checked_sub(prefix_bytes).ok_or_else(|| { vortex_err!( - "Corrupt zstd metadata: {n_values} values do not fit in the {} bytes holding them", + Serde: "Corrupt zstd metadata: {n_values} values do not fit in the {} bytes holding them", bytes.len() ) })?; @@ -874,7 +874,7 @@ fn zstd_value_offset(buffer: &[u8], mut offset: usize, count: usize) -> VortexRe } vortex_ensure!( offset <= buffer.len(), - "Corrupt zstd values: walking {count} values ended at offset {offset}, past the end of \ + Serde: "Corrupt zstd values: walking {count} values ended at offset {offset}, past the end of \ the {} byte frame buffer", buffer.len() ); @@ -889,7 +889,7 @@ fn zstd_value_len(buffer: &[u8], offset: usize) -> VortexResult { .and_then(|rest| rest.first_chunk::<{ size_of::() }>()) .ok_or_else(|| { vortex_err!( - "Corrupt zstd values: length prefix at offset {offset} runs past the end of the \ + Serde: "Corrupt zstd values: length prefix at offset {offset} runs past the end of the \ {} byte frame buffer", buffer.len() ) @@ -955,37 +955,38 @@ impl ZstdData { dtype, DType::Primitive(..) | DType::Binary(_) | DType::Utf8(_) ), - "Unsupported dtype for Zstd array: {dtype}" + MismatchedTypes: "Unsupported dtype for Zstd array: {dtype}" ); vortex_ensure!( self.slice_start <= self.slice_stop, - "Invalid slice range {}..{}", + InvalidArgument: "Invalid slice range {}..{}", self.slice_start, self.slice_stop ); vortex_ensure!( self.slice_stop <= self.unsliced_n_rows, - "Slice stop {} exceeds unsliced row count {}", + InvalidArgument: "Slice stop {} exceeds unsliced row count {}", self.slice_stop, self.unsliced_n_rows ); - vortex_ensure_eq!(self.slice_stop - self.slice_start, len); + vortex_ensure_eq!(self.slice_stop - self.slice_start, len, InvalidArgument); if let Some(validity_len) = validity.maybe_len() { - vortex_ensure_eq!(validity_len, self.unsliced_n_rows); + vortex_ensure_eq!(validity_len, self.unsliced_n_rows, InvalidArgument); } match &self.dictionary { Some(dictionary) => vortex_ensure_eq!( usize::try_from(self.metadata.dictionary_size)?, - dictionary.len() + dictionary.len(), + Serde ), None => vortex_ensure_eq!( self.metadata.dictionary_size, 0, - "Dictionary metadata present without dictionary buffer" + Serde: "Dictionary metadata present without dictionary buffer" ), } - vortex_ensure_eq!(self.frames.len(), self.metadata.frames.len()); + vortex_ensure_eq!(self.frames.len(), self.metadata.frames.len(), Serde); for (index, (frame, metadata)) in self.frames.iter().zip(&self.metadata.frames).enumerate() { validate_frame_content_size(frame.as_slice(), metadata.uncompressed_size, index)?; @@ -1290,8 +1291,9 @@ impl ZstdData { ctx: &mut ExecutionCtx, ) -> VortexResult { let canonical = array.execute::(ctx)?; - Self::from_canonical(&canonical, level, values_per_frame, ctx)? - .ok_or_else(|| vortex_err!("Zstd can only encode Primitive and VarBinView arrays")) + Self::from_canonical(&canonical, level, values_per_frame, ctx)?.ok_or_else( + || vortex_err!(MismatchedTypes: "Zstd can only encode Primitive and VarBinView arrays"), + ) } fn byte_width(dtype: &DType) -> usize { @@ -1332,14 +1334,14 @@ impl ZstdData { let frame_uncompressed_size = usize::try_from(frame_meta.uncompressed_size).map_err(|_| { vortex_err!( - "Zstd frame uncompressed size {} does not fit in a usize", + Overflow: "Zstd frame uncompressed size {} does not fit in a usize", frame_meta.uncompressed_size ) })?; let frame_n_values = if frame_meta.n_values != 0 { usize::try_from(frame_meta.n_values).map_err(|_| { vortex_err!( - "Zstd frame value count {} does not fit in a usize", + Overflow: "Zstd frame value count {} does not fit in a usize", frame_meta.n_values ) })? @@ -1354,23 +1356,23 @@ impl ZstdData { vortex_ensure_eq!( self.frames.len(), 1, - "Zstd frame metadata for a variable-width array is missing its value count" + Serde: "Zstd frame metadata for a variable-width array is missing its value count" ); unsliced_mask.true_count() }; // Bounding the running total also bounds the two accumulators below, which partition // it between the frames we keep and the ones we skip. - let value_idx_stop = value_idx_start.checked_add(frame_n_values).ok_or_else(|| { - vortex_err!("Corrupt zstd metadata: frame value counts overflow a usize") - })?; + let value_idx_stop = value_idx_start.checked_add(frame_n_values).ok_or_else( + || vortex_err!(Serde: "Corrupt zstd metadata: frame value counts overflow a usize"), + )?; if value_idx_stop > slice_value_idx_start { // we need this frame frames_to_decompress.push(frame); uncompressed_size_to_decompress = uncompressed_size_to_decompress .checked_add(frame_uncompressed_size) .ok_or_else(|| { - vortex_err!("Corrupt zstd metadata: frame sizes overflow a usize") + vortex_err!(Serde: "Corrupt zstd metadata: frame sizes overflow a usize") })?; n_buffered_values += frame_n_values; } else { @@ -1409,7 +1411,7 @@ impl ZstdData { }; if uncompressed_start != uncompressed_size_to_decompress { vortex_bail!( - "Zstd metadata or frames were corrupt; expected {} bytes but decompressed {}", + Serde: "Zstd metadata or frames were corrupt; expected {} bytes but decompressed {}", uncompressed_size_to_decompress, uncompressed_start ); @@ -1433,7 +1435,7 @@ impl ZstdData { if !dtype.is_nullable() && !matches!(slice_validity, Validity::NonNullable) { vortex_ensure!( matches!(slice_validity, Validity::AllValid), - "ZSTD array expects to be non-nullable but there are nulls after decompression" + Serde: "ZSTD array expects to be non-nullable but there are nulls after decompression" ); slice_validity = Validity::NonNullable; @@ -1472,7 +1474,7 @@ impl ZstdData { .map(|(byte_start, byte_stop)| byte_start..byte_stop) .ok_or_else(|| { vortex_err!( - "Corrupt zstd metadata: values {start}..{end} of {} bytes each are \ + Serde: "Corrupt zstd metadata: values {start}..{end} of {} bytes each are \ out of bounds of the {} byte frame buffer", slice.byte_width, slice.bytes.len() @@ -1535,7 +1537,7 @@ impl ZstdData { } } } - _ => vortex_bail!("Unsupported dtype for Zstd array: {}", dtype), + _ => vortex_bail!(MismatchedTypes: "Unsupported dtype for Zstd array: {}", dtype), } } diff --git a/encodings/zstd/src/lib.rs b/encodings/zstd/src/lib.rs index e50f3cb1e21..89e5980ea68 100644 --- a/encodings/zstd/src/lib.rs +++ b/encodings/zstd/src/lib.rs @@ -52,11 +52,9 @@ pub fn initialize(session: &VortexSession) { session .editions() .declare_family(&editions::FAMILY) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("Zstd edition family is valid"); session .register_edition(&editions::DECLARATION) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("Zstd edition declaration is valid"); } } @@ -68,12 +66,12 @@ pub(crate) fn validate_frame_content_size( index: usize, ) -> VortexResult<()> { let frame_content_size = zstd::zstd_safe::get_frame_content_size(frame) - .map_err(|error| vortex_err!("Invalid zstd frame {index}: {error}"))? - .ok_or_else(|| vortex_err!("Zstd frame {index} does not declare a content size"))?; + .map_err(|error| vortex_err!(InvalidArgument: "Invalid zstd frame {index}: {error}"))? + .ok_or_else(|| vortex_err!(Serde: "Zstd frame {index} does not declare a content size"))?; vortex_ensure_eq!( metadata_size, frame_content_size, - "Zstd frame {index} metadata declares a different uncompressed size than its header" + Serde: "Zstd frame {index} metadata declares a different uncompressed size than its header" ); Ok(()) } diff --git a/encodings/zstd/src/zstd_buffers.rs b/encodings/zstd/src/zstd_buffers.rs index c7478e79c0b..c4881877e74 100644 --- a/encodings/zstd/src/zstd_buffers.rs +++ b/encodings/zstd/src/zstd_buffers.rs @@ -78,9 +78,9 @@ impl ZstdBuffers { level: i32, session: &VortexSession, ) -> VortexResult { - let serialization = session - .array_serialize(array)? - .ok_or_else(|| vortex_err!("[ZstdBuffers]: Array does not support serialization"))?; + let serialization = session.array_serialize(array)?.ok_or_else( + || vortex_err!(Serde: "[ZstdBuffers]: Array does not support serialization"), + )?; let mut compressed_buffers = Vec::with_capacity(serialization.buffers.len()); let mut uncompressed_sizes = Vec::with_capacity(serialization.buffers.len()); @@ -132,7 +132,7 @@ impl ZstdBuffers { .registry() .get(&array.data().inner_encoding_id) .ok_or_else(|| { - vortex_err!("Unknown inner encoding: {}", array.data().inner_encoding_id) + vortex_err!(NotFound: "Unknown inner encoding: {}", array.data().inner_encoding_id) })?; let children: Vec = array.slots()[..array.data().inner_child_count] @@ -260,12 +260,12 @@ impl ZstdBuffersData { vortex_ensure_eq!( self.compressed_buffers.len(), self.uncompressed_sizes.len(), - "zstd_buffers metadata mismatch" + Serde: "zstd_buffers metadata mismatch" ); vortex_ensure_eq!( self.compressed_buffers.len(), self.buffer_alignments.len(), - "zstd_buffers metadata mismatch" + Serde: "zstd_buffers metadata mismatch" ); Ok(()) } @@ -294,7 +294,7 @@ impl ZstdBuffersData { // of the unsafe calls below. if spare.len() < size { return Err(vortex_err!( - "Insufficient output capacity: expected at least {}, got {}", + MismatchedTypes: "Insufficient output capacity: expected at least {}, got {}", size, spare.len() )); @@ -307,7 +307,7 @@ impl ZstdBuffersData { let written = decompressor.decompress_to_buffer(compressed.as_slice(), dst)?; if written != size { return Err(vortex_err!( - "Decompressed size mismatch: expected {}, got {}", + MismatchedTypes: "Decompressed size mismatch: expected {}, got {}", size, written )); @@ -467,7 +467,7 @@ impl VTable for ZstdBuffers { data.validate()?; vortex_ensure!( data.inner_child_count <= slots.len(), - "ZstdBuffers has {} slots but {} inner children", + InvalidArgument: "ZstdBuffers has {} slots but {} inner children", slots.len(), data.inner_child_count ); @@ -476,23 +476,25 @@ impl VTable for ZstdBuffers { Some(idx) => { vortex_ensure!( dtype.is_nullable(), - "ZstdBuffers validity requires a nullable dtype" + InvalidArgument: "ZstdBuffers validity requires a nullable dtype" ); vortex_ensure!( idx < slots.len(), - "ZstdBuffers validity slot {idx} out of bounds" + OutOfBounds: "ZstdBuffers validity slot {idx} out of bounds" ); vortex_ensure!( extra_slots == usize::from(idx == data.inner_child_count), - "ZstdBuffers has {extra_slots} unexpected extra slots" + InvalidArgument: "ZstdBuffers has {extra_slots} unexpected extra slots" ); - let validity = slots[idx] - .as_ref() - .ok_or_else(|| vortex_err!("ZstdBuffers validity slot {idx} is empty"))?; + let validity = slots[idx].as_ref().ok_or_else( + || vortex_err!(InvalidArgument: "ZstdBuffers validity slot {idx} is empty"), + )?; vortex_ensure_eq!(validity.dtype(), &Validity::DTYPE); vortex_ensure_eq!(validity.len(), len); } - None => vortex_ensure_eq!(extra_slots, 0, "ZstdBuffers has unexpected extra slots"), + None => { + vortex_ensure_eq!(extra_slots, 0, InvalidArgument: "ZstdBuffers has unexpected extra slots") + } } Ok(()) } diff --git a/fuzz/fuzz_targets/array_ops.rs b/fuzz/fuzz_targets/array_ops.rs index 17324abe3c3..b483ed6e648 100644 --- a/fuzz/fuzz_targets/array_ops.rs +++ b/fuzz/fuzz_targets/array_ops.rs @@ -30,6 +30,6 @@ fuzz_target!( match run_fuzz_action(fuzz_action) { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, - Err(e) => vortex_panic!("{e}"), + Err(e) => vortex_panic!(AssertionFailed: "{e}"), } }); diff --git a/fuzz/fuzz_targets/compress_gpu.rs b/fuzz/fuzz_targets/compress_gpu.rs index 91d7e9b9f9d..a6d616a6933 100644 --- a/fuzz/fuzz_targets/compress_gpu.rs +++ b/fuzz/fuzz_targets/compress_gpu.rs @@ -22,7 +22,7 @@ fuzz_target!(|fuzz: FuzzCompressGpu| -> Corpus { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, Err(e) => { - vortex_panic!("{e}"); + vortex_panic!(AssertionFailed: "{e}"); } } }); diff --git a/fuzz/fuzz_targets/compress_roundtrip.rs b/fuzz/fuzz_targets/compress_roundtrip.rs index bb5b9e464ce..75ae06ccc28 100644 --- a/fuzz/fuzz_targets/compress_roundtrip.rs +++ b/fuzz/fuzz_targets/compress_roundtrip.rs @@ -14,7 +14,7 @@ fuzz_target!(|fuzz: FuzzCompressRoundtrip| -> Corpus { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, Err(e) => { - vortex_panic!("{e}"); + vortex_panic!(AssertionFailed: "{e}"); } } }); diff --git a/fuzz/fuzz_targets/fsst_like.rs b/fuzz/fuzz_targets/fsst_like.rs index bf61b2430cf..2cd0e18f8d9 100644 --- a/fuzz/fuzz_targets/fsst_like.rs +++ b/fuzz/fuzz_targets/fsst_like.rs @@ -30,6 +30,6 @@ fuzz_target!( match run_fsst_like_fuzz(fuzz_action) { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, - Err(e) => vortex_panic!("{e}"), + Err(e) => vortex_panic!(AssertionFailed: "{e}"), } }); diff --git a/fuzz/fuzz_targets/row_encode.rs b/fuzz/fuzz_targets/row_encode.rs index 07d63cc322c..f421128bfeb 100644 --- a/fuzz/fuzz_targets/row_encode.rs +++ b/fuzz/fuzz_targets/row_encode.rs @@ -30,6 +30,6 @@ fuzz_target!( match run_row_encode(input) { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, - Err(e) => vortex_panic!("{e}"), + Err(e) => vortex_panic!(AssertionFailed: "{e}"), } }); diff --git a/fuzz/src/array/compare.rs b/fuzz/src/array/compare.rs index 03ce50a7170..bf8b1bcb2c0 100644 --- a/fuzz/src/array/compare.rs +++ b/fuzz/src/array/compare.rs @@ -107,7 +107,9 @@ pub fn compare_canonical_array( .decimal_value() .vortex_expect("nulls handled before") .cast::() - .unwrap_or_else(|| vortex_panic!("todo: handle upcast of decimal array")); + .unwrap_or_else( + || vortex_panic!(NotImplemented: "todo: handle upcast of decimal array"), + ); let buf = decimal_array.buffer::(); compare_to( buf.as_slice() diff --git a/fuzz/src/array/fill_null.rs b/fuzz/src/array/fill_null.rs index 69e10482658..6b07121dde9 100644 --- a/fuzz/src/array/fill_null.rs +++ b/fuzz/src/array/fill_null.rs @@ -52,7 +52,7 @@ pub fn fill_null_canonical_array( | Canonical::FixedSizeList(_) | Canonical::Extension(_) => canonical.into_array().fill_null(fill_value.clone())?, Canonical::Union(_) => { - vortex_bail!("TODO(connor)[Union]: support Union arrays in the fill_null fuzzer") + vortex_bail!(NotImplemented: "TODO(connor)[Union]: support Union arrays in the fill_null fuzzer") } Canonical::Variant(_) => unreachable!("Variant arrays are not fuzzed"), }) diff --git a/fuzz/src/array/mask.rs b/fuzz/src/array/mask.rs index c20f024448a..904b08edd91 100644 --- a/fuzz/src/array/mask.rs +++ b/fuzz/src/array/mask.rs @@ -165,7 +165,7 @@ pub fn mask_canonical_array( ExtensionArray::new(ext_dtype, masked_storage).into_array() } Canonical::Union(_) => { - vortex_bail!("TODO(connor)[Union]: support Union arrays in the mask fuzzer") + vortex_bail!(NotImplemented: "TODO(connor)[Union]: support Union arrays in the mask fuzzer") } Canonical::Variant(_) => unreachable!("Variant arrays are not fuzzed"), }) diff --git a/fuzz/src/array/mod.rs b/fuzz/src/array/mod.rs index 638bd1559cf..f23cf40b54c 100644 --- a/fuzz/src/array/mod.rs +++ b/fuzz/src/array/mod.rs @@ -142,35 +142,35 @@ impl ExpectedValue { pub fn array(self) -> ArrayRef { match self { ExpectedValue::Array(array) => array, - _ => vortex_panic!("expected array"), + _ => vortex_panic!(AssertionFailed: "expected array"), } } pub fn search(self) -> SearchResult { match self { ExpectedValue::Search(s) => s, - _ => vortex_panic!("expected search"), + _ => vortex_panic!(AssertionFailed: "expected search"), } } pub fn scalar(self) -> Scalar { match self { ExpectedValue::Scalar(s) => s, - _ => vortex_panic!("expected scalar"), + _ => vortex_panic!(AssertionFailed: "expected scalar"), } } pub fn min_max(self) -> Option { match self { ExpectedValue::MinMax(m) => m, - _ => vortex_panic!("expected min_max"), + _ => vortex_panic!(AssertionFailed: "expected min_max"), } } pub fn scalar_vec(self) -> Vec { match self { ExpectedValue::ScalarVec(v) => v, - _ => vortex_panic!("expected scalar_vec"), + _ => vortex_panic!(AssertionFailed: "expected scalar_vec"), } } } @@ -516,7 +516,7 @@ fn actions_for_dtype(dtype: &DType) -> HashSet { }) } DType::Map(..) => [Compress, Slice, Take, Filter, Mask, ScalarAt].into(), - DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), // Currently, no support at all DType::Variant(_) => unreachable!("Variant dtype shouldn't be fuzzed"), DType::Extension(_) => { @@ -650,7 +650,7 @@ pub fn run_fuzz_action(fuzz_action: FuzzArrayAction) -> VortexFuzzResult { .vortex_expect("compare operation should succeed in fuzz test"); if let Err(e) = assert_array_eq(&expected.array(), &compare_result, i, &mut ctx) { vortex_panic!( - "Failed to compare {}with {op} {v}\nError: {e}", + AssertionFailed: "Failed to compare {}with {op} {v}\nError: {e}", current_array.display_tree() ) } @@ -662,7 +662,7 @@ pub fn run_fuzz_action(fuzz_action: FuzzArrayAction) -> VortexFuzzResult { .vortex_expect("cast operation should succeed in fuzz test"); if let Err(e) = assert_array_eq(&expected.array(), &cast_result, i, &mut ctx) { vortex_panic!( - "Failed to cast {} to dtype {to}\nError: {e}", + AssertionFailed: "Failed to cast {} to dtype {to}\nError: {e}", current_array.display_tree() ) } diff --git a/fuzz/src/array/scalar_at.rs b/fuzz/src/array/scalar_at.rs index c978aacbc0d..5d73ee3d6b1 100644 --- a/fuzz/src/array/scalar_at.rs +++ b/fuzz/src/array/scalar_at.rs @@ -108,7 +108,7 @@ pub fn scalar_at_canonical_array( Scalar::extension_ref(array.ext_dtype().clone(), storage_scalar) } Canonical::Union(_) => { - vortex_bail!("TODO(connor)[Union]: support Union arrays in the scalar_at fuzzer") + vortex_bail!(NotImplemented: "TODO(connor)[Union]: support Union arrays in the scalar_at fuzzer") } Canonical::Map(array) => { let entries = array.entries_at(index, ctx)?.execute::(ctx)?; diff --git a/fuzz/src/array/search_sorted.rs b/fuzz/src/array/search_sorted.rs index eb9c8131001..b728de1a462 100644 --- a/fuzz/src/array/search_sorted.rs +++ b/fuzz/src/array/search_sorted.rs @@ -122,11 +122,11 @@ pub fn search_sorted_canonical_array( .decimal_value() .map(|v| { v.cast::().ok_or_else(|| { - vortex_err!("cannot cast value {v} to decimal value type {d}") + vortex_err!(MismatchedTypes: "cannot cast value {v} to decimal value type {d}") }) }) .transpose()? - .ok_or_else(|| vortex_err!("unexpected null scalar"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "unexpected null scalar"))?; Ok(linear_search( opt_values.iter().map(|value| value.cmp(&Some(to_find))), side, diff --git a/fuzz/src/array/sum/mod.rs b/fuzz/src/array/sum/mod.rs index 98b3f69ce2c..f9488f47a38 100644 --- a/fuzz/src/array/sum/mod.rs +++ b/fuzz/src/array/sum/mod.rs @@ -68,7 +68,7 @@ pub fn sum_canonical_array( ) }) } - _ => vortex_bail!("Unsupported sum dtype: {}", array.dtype()), + _ => vortex_bail!(NotImplemented: "Unsupported sum dtype: {}", array.dtype()), } } @@ -141,6 +141,6 @@ fn native_values(array: &ArrayRef, ctx: &mut ExecutionCtx) -> Vortex .map(|value| T::from(value).vortex_expect("decimal value fits accumulator")) .collect() }), - _ => vortex_bail!("Unsupported sum dtype: {}", array.dtype()), + _ => vortex_bail!(NotImplemented: "Unsupported sum dtype: {}", array.dtype()), }) } diff --git a/fuzz/src/array/sum/tests.rs b/fuzz/src/array/sum/tests.rs index f48fb01604f..4f770745b89 100644 --- a/fuzz/src/array/sum/tests.rs +++ b/fuzz/src/array/sum/tests.rs @@ -144,7 +144,7 @@ fn test_sum_decimal_storage(#[case] values_type: DecimalType) -> VortexResult<() let array = match_each_decimal_value_type!(values_type, |D| { let value = DecimalValue::I8(99) .cast::() - .ok_or_else(|| vortex_err!("99 fits in every decimal storage type"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "99 fits in every decimal storage type"))?; DecimalArray::new( buffer![value, value, -value], DecimalDType::new(2, 0), @@ -323,7 +323,7 @@ fn test_sum_action_accepts_unambiguous_inputs( actions.push((Action::Sum, ExpectedValue::Scalar(expected))); assert!( run_fuzz_action(FuzzArrayAction { array, actions }) - .map_err(|error| vortex_err!("{error}"))? + .map_err(|error| vortex_err!(AssertionFailed: "{error}"))? ); Ok(()) } diff --git a/fuzz/src/fsst_like.rs b/fuzz/src/fsst_like.rs index 0cd9b4c0cae..5d8ab7338cf 100644 --- a/fuzz/src/fsst_like.rs +++ b/fuzz/src/fsst_like.rs @@ -139,7 +139,7 @@ pub fn run_fsst_like_fuzz(fuzz: FuzzFsstLike) -> VortexFuzzResult { if expected_val != actual_val { return Err(VortexFuzzError::VortexError( vortex_error::vortex_err!( - "FSST LIKE mismatch at index {idx}:\n \ + MismatchedTypes: "FSST LIKE mismatch at index {idx}:\n \ pattern: {pattern:?}\n \ string: {:?}\n \ expected: {expected_val}\n \ diff --git a/fuzz/src/gpu/mod.rs b/fuzz/src/gpu/mod.rs index 91e116e38cd..3cccde25f20 100644 --- a/fuzz/src/gpu/mod.rs +++ b/fuzz/src/gpu/mod.rs @@ -104,7 +104,7 @@ pub async fn run_compress_gpu(fuzz: FuzzCompressGpu) -> VortexFuzzResult { if !vortex_cuda::cuda_available() { return Err(VortexFuzzError::VortexError( - vortex_err!("no cuda device to run the fuzzer on"), + vortex_err!(Io: "no cuda device to run the fuzzer on"), Backtrace::capture(), )); } diff --git a/fuzz/src/lib.rs b/fuzz/src/lib.rs index ca6cd49535e..6747b27be17 100644 --- a/fuzz/src/lib.rs +++ b/fuzz/src/lib.rs @@ -42,11 +42,9 @@ fn enable_latest_core_edition(session: &vortex_session::VortexSession) { use vortex::editions::CORE_2026_08_3; use vortex::editions::EditionSessionExt; use vortex_error::VortexExpect; - use vortex_error::vortex_err; session .enable_edition(CORE_2026_08_3) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("latest core edition is registered"); } diff --git a/lang/cpp/include/vortex/error.hpp b/lang/cpp/include/vortex/error.hpp index 8793be76dbb..8f01c0c782d 100644 --- a/lang/cpp/include/vortex/error.hpp +++ b/lang/cpp/include/vortex/error.hpp @@ -12,7 +12,6 @@ namespace vortex { enum class ErrorCode { Other = VX_ERROR_CODE_OTHER, OutOfBounds = VX_ERROR_CODE_OUT_OF_BOUNDS, - Compute = VX_ERROR_CODE_COMPUTE, InvalidArgument = VX_ERROR_CODE_INVALID_ARGUMENT, Serialization = VX_ERROR_CODE_SERIALIZATION, NotImplemented = VX_ERROR_CODE_NOT_IMPLEMENTED, @@ -20,6 +19,8 @@ enum class ErrorCode { AssertionFailed = VX_ERROR_CODE_ASSERTION_FAILED, Io = VX_ERROR_CODE_IO, Panic = VX_ERROR_CODE_PANIC, + NotFound = VX_ERROR_CODE_NOT_FOUND, + Overflow = VX_ERROR_CODE_OVERFLOW, }; class VortexException : public std::runtime_error { diff --git a/lang/cpp/src/array.cpp b/lang/cpp/src/array.cpp index 55c4b2827dd..f774c3c2228 100644 --- a/lang/cpp/src/array.cpp +++ b/lang/cpp/src/array.cpp @@ -254,7 +254,7 @@ Array Array::field(std::string_view name) const { return this->field(i); } } - throw VortexException("no field named \"" + std::string(name) + "\"", ErrorCode::InvalidArgument); + throw VortexException("no field named \"" + std::string(name) + "\"", ErrorCode::NotFound); } Array Array::slice(size_t begin, size_t end) const { diff --git a/vortex-array/benches/row_fn_bool_retry.rs b/vortex-array/benches/row_fn_bool_retry.rs index 858c7eb8a3a..dd25f961145 100644 --- a/vortex-array/benches/row_fn_bool_retry.rs +++ b/vortex-array/benches/row_fn_bool_retry.rs @@ -86,7 +86,7 @@ impl RowFn for Predicate { visitor.visit_deferred_bool::<(i64, i64), bool, true>( |(lhs, rhs)| (lhs < rhs, lhs == i64::MAX || rhs == i64::MAX), |failed| { - vortex_ensure!(!failed, "predicate rejected sentinel"); + vortex_ensure!(!failed, AssertionFailed: "predicate rejected sentinel"); Ok(()) }, ) diff --git a/vortex-array/benches/row_fn_output.rs b/vortex-array/benches/row_fn_output.rs index 200a04a7810..0314b54c8eb 100644 --- a/vortex-array/benches/row_fn_output.rs +++ b/vortex-array/benches/row_fn_output.rs @@ -148,7 +148,7 @@ impl RowFn for DeferredBool { |negative| { vortex_ensure!( !negative, - "deferred-bool benchmark inputs must be nonnegative" + InvalidArgument: "deferred-bool benchmark inputs must be nonnegative" ); Ok(()) }, @@ -178,7 +178,7 @@ impl RowFn for DeferredI64 { |overflowed| { vortex_ensure!( !overflowed, - "deferred-i64 benchmark inputs must not overflow" + Overflow: "deferred-i64 benchmark inputs must not overflow" ); Ok(()) }, diff --git a/vortex-array/src/aggregate_fn/accumulator.rs b/vortex-array/src/aggregate_fn/accumulator.rs index 388d92ffd2f..46dfa31a3a3 100644 --- a/vortex-array/src/aggregate_fn/accumulator.rs +++ b/vortex-array/src/aggregate_fn/accumulator.rs @@ -120,7 +120,7 @@ impl Accumulator { vortex_ensure_eq!( result.dtype(), &self.dtypes.partial_dtype, - "Aggregate kernel returned the wrong partial dtype", + AssertionFailed: "Aggregate kernel returned the wrong partial dtype", ); self.fold_partial_scalar(&result)?; return Ok(()); @@ -156,7 +156,7 @@ impl Accumulator { vortex_ensure_eq!( result.dtype(), &self.dtypes.partial_dtype, - "Aggregate kernel returned the wrong partial dtype", + AssertionFailed: "Aggregate kernel returned the wrong partial dtype", ); self.fold_partial_scalar(&result)?; return Ok(()); @@ -234,7 +234,7 @@ impl DynAccumulator for Accumulator { return Ok(()); } - vortex_ensure_eq!(batch.dtype(), &self.dtypes.dtype, "Input DType mismatch"); + vortex_ensure_eq!(batch.dtype(), &self.dtypes.dtype, MismatchedTypes: "Input DType mismatch"); // Legacy stats bridge: an aggregate still cached under a legacy `Stat` slot consumes that // exact stat before kernel dispatch or decode, and otherwise caches its result there. @@ -250,7 +250,7 @@ impl DynAccumulator for Accumulator { partial .dtype() .eq_ignore_nullability(&self.dtypes.partial_dtype), - "Aggregate {} read legacy stat {} with dtype {}, expected {}", + MismatchedTypes: "Aggregate {} read legacy stat {} with dtype {}, expected {}", self.aggregate_fn, stat, partial.dtype(), @@ -286,13 +286,13 @@ impl DynAccumulator for Accumulator { fn merge_from(&mut self, other: &mut dyn DynAccumulator) -> VortexResult<()> { let Some(other) = other.downcast_mut::() else { vortex_bail!( - "Cannot merge into a {} accumulator from an accumulator of a different aggregate", + MismatchedTypes: "Cannot merge into a {} accumulator from an accumulator of a different aggregate", self.aggregate_fn, ); }; vortex_ensure!( other.options == self.options && other.dtypes.dtype == self.dtypes.dtype, - "Cannot merge {} accumulators with different options or input dtypes", + InvalidArgument: "Cannot merge {} accumulators with different options or input dtypes", self.aggregate_fn, ); match other.partial.take() { @@ -305,7 +305,7 @@ impl DynAccumulator for Accumulator { vortex_ensure_eq!( partial.dtype(), &self.dtypes.partial_dtype, - "Partial DType mismatch for {}", + MismatchedTypes: "Partial DType mismatch for {}", self.aggregate_fn, ); self.fold_partial_scalar(partial) @@ -338,7 +338,7 @@ impl DynAccumulator for Accumulator { vortex_ensure_eq!( partial.dtype(), args.partial_dtype, - "Aggregate returned incorrect DType on partial_scalar", + AssertionFailed: "Aggregate returned incorrect DType on partial_scalar", ); } @@ -355,7 +355,7 @@ impl DynAccumulator for Accumulator { vortex_ensure_eq!( result.dtype(), args.return_dtype, - "Aggregate returned incorrect DType on final_scalar", + AssertionFailed: "Aggregate returned incorrect DType on final_scalar", ); Ok(result) diff --git a/vortex-array/src/aggregate_fn/accumulator_grouped.rs b/vortex-array/src/aggregate_fn/accumulator_grouped.rs index 6405d993f40..b24c0cd3eeb 100644 --- a/vortex-array/src/aggregate_fn/accumulator_grouped.rs +++ b/vortex-array/src/aggregate_fn/accumulator_grouped.rs @@ -234,14 +234,14 @@ impl DynGroupedAccumulator for GroupedAccumulator { DType::List(elem, _) => elem, DType::FixedSizeList(elem, ..) => elem, _ => vortex_bail!( - "Input DType mismatch: expected List or FixedSizeList, got {}", + MismatchedTypes: "Input DType mismatch: expected List or FixedSizeList, got {}", groups.dtype() ), }; vortex_ensure_eq!( elements_dtype.as_ref(), &self.dtypes.dtype, - "Input DType mismatch" + MismatchedTypes: "Input DType mismatch" ); // We first execute the groups until it is a ListView or FixedSizeList, since we only @@ -253,7 +253,9 @@ impl DynGroupedAccumulator for GroupedAccumulator { match canonical { Canonical::List(groups) => self.accumulate_grouped_array(groups.into(), ctx), Canonical::FixedSizeList(groups) => self.accumulate_grouped_array(groups.into(), ctx), - _ => vortex_panic!("We checked the DType above, so this should never happen"), + _ => { + vortex_panic!(AssertionFailed: "We checked the DType above, so this should never happen") + } } } @@ -274,7 +276,7 @@ impl DynGroupedAccumulator for GroupedAccumulator { vortex_ensure_eq!( results.dtype(), &self.dtypes.return_dtype, - "Return DType mismatch" + AssertionFailed: "Return DType mismatch" ); Ok(results) @@ -367,7 +369,7 @@ impl GroupedAccumulator { vortex_ensure_eq!( state.dtype(), &self.dtypes.partial_dtype, - "State DType mismatch" + AssertionFailed: "State DType mismatch" ); self.partials.push(state); Ok(()) diff --git a/vortex-array/src/aggregate_fn/combined.rs b/vortex-array/src/aggregate_fn/combined.rs index 842603c672e..91c1561ee51 100644 --- a/vortex-array/src/aggregate_fn/combined.rs +++ b/vortex-array/src/aggregate_fn/combined.rs @@ -118,7 +118,7 @@ pub trait BinaryCombined: 'static + Send + Sync + Clone { ) -> VortexResult> { let _ = (metadata, session); vortex_bail!( - "Combined aggregate function {} is not deserializable", + Serde: "Combined aggregate function {} is not deserializable", BinaryCombined::id(self) ); } @@ -146,7 +146,7 @@ fn child_return_dtype( ) -> VortexResult { vtable.return_dtype(options, input_dtype).ok_or_else(|| { vortex_err!( - "Aggregate function {} cannot be applied to dtype {}", + InvalidArgument: "Aggregate function {} cannot be applied to dtype {}", vtable.id(), input_dtype ) @@ -174,7 +174,7 @@ impl Combined { ) -> VortexResult<(AggregateDTypes, AggregateDTypes)> { let partials = args.partial_dtype.as_struct_fields_opt().ok_or_else(|| { vortex_err!( - "Combined partial dtype must be a struct, got {}", + MismatchedTypes: "Combined partial dtype must be a struct, got {}", args.partial_dtype ) })?; @@ -182,7 +182,7 @@ impl Combined { [partials.field_by_index(0), partials.field_by_index(1)] else { vortex_bail!( - "Combined partial dtype {} must have two fields", + MismatchedTypes: "Combined partial dtype {} must have two fields", args.partial_dtype ); }; @@ -254,12 +254,12 @@ impl AggregateFnVTable for Combined { let s = scalar.as_struct(); let lname = self.0.left_name(); let rname = self.0.right_name(); - let l_field = s - .field(lname) - .ok_or_else(|| vortex_err!("BinaryCombined partial missing `{}` field", lname))?; - let r_field = s - .field(rname) - .ok_or_else(|| vortex_err!("BinaryCombined partial missing `{}` field", rname))?; + let l_field = s.field(lname).ok_or_else( + || vortex_err!(NotFound: "BinaryCombined partial missing `{}` field", lname), + )?; + let r_field = s.field(rname).ok_or_else( + || vortex_err!(NotFound: "BinaryCombined partial missing `{}` field", rname), + )?; left.combine_partials(&l_field)?; right.combine_partials(&r_field)?; } diff --git a/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs b/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs index adfb4a22954..b4b020b34fe 100644 --- a/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs @@ -64,7 +64,7 @@ use crate::validity::Validity; pub fn all_non_distinct(a: &ArrayRef, b: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { if a.dtype() != b.dtype() { vortex_bail!( - "all_non_distinct: dtype mismatch: {} vs {}", + MismatchedTypes: "all_non_distinct: dtype mismatch: {} vs {}", a.dtype(), b.dtype() ); @@ -72,7 +72,7 @@ pub fn all_non_distinct(a: &ArrayRef, b: &ArrayRef, ctx: &mut ExecutionCtx) -> V if a.len() != b.len() { vortex_bail!( - "all_non_distinct: length mismatch: {} vs {}", + MismatchedTypes: "all_non_distinct: length mismatch: {} vs {}", a.len(), b.len() ); @@ -130,7 +130,7 @@ impl AggregateFnVTable for AllNonDistinct { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!("AllNonDistinct is not yet serializable"); + vortex_bail!(NotImplemented: "AllNonDistinct is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { @@ -217,7 +217,7 @@ impl AggregateFnVTable for AllNonDistinct { Columnar::Canonical(c) => { let Canonical::Struct(s) = c else { vortex_bail!( - "AllNonDistinct expects a Struct canonical, got {:?}", + InvalidArgument: "AllNonDistinct expects a Struct canonical, got {:?}", c.dtype() ); }; @@ -255,7 +255,7 @@ impl AggregateFnVTable for AllNonDistinct { _args: AggregateArgs<'_, Self::Options>, _partials: ArrayRef, ) -> VortexResult { - vortex_bail!("AllNonDistinct does not support array finalization"); + vortex_bail!(InvalidArgument: "AllNonDistinct does not support array finalization"); } fn finalize_scalar( @@ -298,7 +298,7 @@ fn check_canonical_identical( check_variant_identical(lhs, rhs, ctx) } _ => Err(vortex_err!( - "Canonical type mismatch in AllNonDistinct: {:?} vs {:?}", + MismatchedTypes: "Canonical type mismatch in AllNonDistinct: {:?} vs {:?}", lhs.dtype(), rhs.dtype() )), diff --git a/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs b/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs index d9ae58f6669..bc809f93f66 100644 --- a/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs @@ -142,12 +142,12 @@ impl AggregateFnVTable for BoundedMax { vortex_ensure_eq!( metadata.len(), size_of::(), - "BoundedMax options have the wrong byte length" + Serde: "BoundedMax options have the wrong byte length" ); let mut bytes = [0u8; size_of::()]; bytes.copy_from_slice(metadata); let max_bytes = usize::try_from(u64::from_le_bytes(bytes))?; - vortex_ensure!(max_bytes > 0, "BoundedMax requires max_bytes > 0"); + vortex_ensure!(max_bytes > 0, InvalidArgument: "BoundedMax requires max_bytes > 0"); Ok(BoundedMaxOptions { max_bytes: NonZeroUsize::new(max_bytes).vortex_expect("checked non-zero max_bytes"), }) @@ -207,18 +207,18 @@ impl AggregateFnVTable for BoundedMax { } else { let Some(fields) = scalar.as_struct_opt() else { vortex_bail!( - "BoundedMax partial must be a struct, got {}", + MismatchedTypes: "BoundedMax partial must be a struct, got {}", scalar.dtype() ); }; let Some(bound) = fields.field_by_idx(0) else { - vortex_bail!("BoundedMax partial is missing its bound field"); + vortex_bail!(NotFound: "BoundedMax partial is missing its bound field"); }; let Some(unknown) = fields .field_by_idx(1) .and_then(|unknown| unknown.as_bool().value()) else { - vortex_bail!("BoundedMax partial is missing its non-null unknown field"); + vortex_bail!(NotFound: "BoundedMax partial is missing its non-null unknown field"); }; if unknown { diff --git a/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs b/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs index c6c8b1ce7ed..35491e68dba 100644 --- a/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs @@ -96,12 +96,12 @@ impl AggregateFnVTable for BoundedMin { vortex_ensure_eq!( metadata.len(), size_of::(), - "BoundedMin options have the wrong byte length" + Serde: "BoundedMin options have the wrong byte length" ); let mut bytes = [0u8; size_of::()]; bytes.copy_from_slice(metadata); let max_bytes = usize::try_from(u64::from_le_bytes(bytes))?; - vortex_ensure!(max_bytes > 0, "BoundedMin requires max_bytes > 0"); + vortex_ensure!(max_bytes > 0, InvalidArgument: "BoundedMin requires max_bytes > 0"); Ok(BoundedMinOptions { max_bytes: NonZeroUsize::new(max_bytes).vortex_expect("checked non-zero max_bytes"), }) diff --git a/vortex-array/src/aggregate_fn/fns/count/mod.rs b/vortex-array/src/aggregate_fn/fns/count/mod.rs index ba9a97fc7f8..fc3b22439c2 100644 --- a/vortex-array/src/aggregate_fn/fns/count/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/count/mod.rs @@ -42,7 +42,7 @@ impl AggregateFnVTable for Count { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!("Count is not yet serializable"); + vortex_bail!(NotImplemented: "Count is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, _input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/first/mod.rs b/vortex-array/src/aggregate_fn/fns/first/mod.rs index 5f614532482..603bc077a0b 100644 --- a/vortex-array/src/aggregate_fn/fns/first/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/first/mod.rs @@ -46,7 +46,7 @@ impl AggregateFnVTable for First { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!("First is not yet serializable"); + vortex_bail!(NotImplemented: "First is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs b/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs index ff8e526402b..e3cfb52cfe2 100644 --- a/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs @@ -275,7 +275,7 @@ impl AggregateFnVTable for IsConstant { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!("IsConstant is not yet serializable"); + vortex_bail!(NotImplemented: "IsConstant is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { @@ -426,10 +426,10 @@ impl AggregateFnVTable for IsConstant { Canonical::FixedSizeList(f) => check_fixed_size_list_constant(f, ctx)?, Canonical::Null(_) => true, Canonical::Union(_) => { - vortex_bail!("TODO(connor)[Union]: implement IsConstant for Union arrays") + vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement IsConstant for Union arrays") } Canonical::Variant(_) => { - vortex_bail!("Variant arrays don't support IsConstant") + vortex_bail!(NotImplemented: "Variant arrays don't support IsConstant") } }; diff --git a/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs b/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs index 402eb1f6fb8..9acf0da62eb 100644 --- a/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs @@ -252,7 +252,7 @@ impl AggregateFnVTable for IsSorted { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!("IsSorted is not yet serializable"); + vortex_bail!(NotImplemented: "IsSorted is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/last/mod.rs b/vortex-array/src/aggregate_fn/fns/last/mod.rs index 1a631ede3a0..ffc0e140d79 100644 --- a/vortex-array/src/aggregate_fn/fns/last/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/last/mod.rs @@ -46,7 +46,7 @@ impl AggregateFnVTable for Last { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!("Last is not yet serializable"); + vortex_bail!(NotImplemented: "Last is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/mean/mod.rs b/vortex-array/src/aggregate_fn/fns/mean/mod.rs index b2dcf09fab4..b9b164aa8e1 100644 --- a/vortex-array/src/aggregate_fn/fns/mean/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/mean/mod.rs @@ -101,7 +101,7 @@ impl BinaryCombined for Mean { count: ArrayRef, ) -> VortexResult { if let DType::Decimal(..) = sum.dtype() { - vortex_bail!("grouped mean over decimals is not yet supported"); + vortex_bail!(NotImplemented: "grouped mean over decimals is not yet supported"); } let target = args.return_dtype.clone(); let sum = sum.cast(target.clone())?; @@ -151,7 +151,7 @@ impl BinaryCombined for Mean { } fn serialize(&self, _options: &CombinedOptions) -> VortexResult>> { - vortex_bail!("mean is not yet serializable"); + vortex_bail!(NotImplemented: "mean is not yet serializable"); } } diff --git a/vortex-array/src/aggregate_fn/fns/min_max/mod.rs b/vortex-array/src/aggregate_fn/fns/min_max/mod.rs index 8aa0e559e84..35a5f03fddc 100644 --- a/vortex-array/src/aggregate_fn/fns/min_max/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/min_max/mod.rs @@ -170,7 +170,7 @@ pub(crate) fn nan_scalar(dtype: &DType) -> Scalar { PType::F16 => Scalar::primitive(f16::NAN, Nullability::NonNullable), PType::F32 => Scalar::primitive(f32::NAN, Nullability::NonNullable), PType::F64 => Scalar::primitive(f64::NAN, Nullability::NonNullable), - _ => vortex_panic!("NaN scalar requested for non-float dtype {dtype}"), + _ => vortex_panic!(AssertionFailed: "NaN scalar requested for non-float dtype {dtype}"), } } @@ -482,14 +482,14 @@ impl AggregateFnVTable for MinMax { } Canonical::Null(_) => Ok(()), Canonical::Union(_) => { - vortex_bail!("TODO(connor)[Union]: implement min_max for Union arrays") + vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement min_max for Union arrays") } Canonical::Struct(_) | Canonical::List(_) | Canonical::Map(_) | Canonical::FixedSizeList(_) | Canonical::Variant(_) => { - vortex_bail!("Unsupported canonical type for min_max: {}", batch.dtype()) + vortex_bail!(InvalidArgument: "Unsupported canonical type for min_max: {}", batch.dtype()) } }, } diff --git a/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs b/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs index ecc1e30afbb..1e937ab791e 100644 --- a/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs +++ b/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs @@ -154,7 +154,7 @@ fn make_scalar(dtype: &DType, value: &[u8]) -> Scalar { let value = unsafe { str::from_utf8_unchecked(value) }; Scalar::utf8(value, NonNullable) } - _ => vortex_panic!("cannot make Scalar from bytes with dtype {dtype}"), + _ => vortex_panic!(MismatchedTypes: "cannot make Scalar from bytes with dtype {dtype}"), } } diff --git a/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs b/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs index d77d6dc5a26..e3799331e0d 100644 --- a/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs @@ -6,7 +6,6 @@ mod primitive; use vortex_error::VortexExpect; use vortex_error::VortexResult; use vortex_error::vortex_bail; -use vortex_error::vortex_err; use vortex_session::VortexSession; use vortex_session::registry::CachedId; @@ -39,7 +38,7 @@ pub fn nan_count(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult match c { Canonical::Primitive(p) => accumulate_primitive(partial, p, ctx), _ => vortex_bail!( - "Unsupported canonical type for nan_count: {}", + InvalidArgument: "Unsupported canonical type for nan_count: {}", batch.dtype() ), }, diff --git a/vortex-array/src/aggregate_fn/fns/null_count/mod.rs b/vortex-array/src/aggregate_fn/fns/null_count/mod.rs index adf35c24c89..d2876220f9a 100644 --- a/vortex-array/src/aggregate_fn/fns/null_count/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/null_count/mod.rs @@ -3,7 +3,6 @@ use vortex_error::VortexExpect; use vortex_error::VortexResult; -use vortex_error::vortex_err; use vortex_session::VortexSession; use vortex_session::registry::CachedId; @@ -29,7 +28,7 @@ use crate::scalar::Scalar; pub fn null_count(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { if let Precision::Exact(null_count_scalar) = array.statistics().get(Stat::NullCount) { return usize::try_from(&null_count_scalar) - .map_err(|e| vortex_err!("Failed to convert null count stat to usize: {e}")); + .map_err(|e| e.with_context("Failed to convert null count stat to usize")); } let mut acc = Accumulator::try_new(NullCount, EmptyOptions, array.dtype().clone())?; diff --git a/vortex-array/src/aggregate_fn/fns/sum/bool.rs b/vortex-array/src/aggregate_fn/fns/sum/bool.rs index d6c42f31ba3..07c78c122b1 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/bool.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/bool.rs @@ -19,7 +19,7 @@ pub(crate) fn accumulate_bool( ctx: &mut ExecutionCtx, ) -> VortexResult { let SumState::Unsigned(acc) = inner else { - vortex_panic!("expected unsigned sum state for bool input"); + vortex_panic!(AssertionFailed: "expected unsigned sum state for bool input"); }; let mask = b.as_ref().validity()?.execute_mask(b.as_ref().len(), ctx)?; diff --git a/vortex-array/src/aggregate_fn/fns/sum/constant.rs b/vortex-array/src/aggregate_fn/fns/sum/constant.rs index f1b21c8b0b2..42278d1936c 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/constant.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/constant.rs @@ -27,20 +27,18 @@ pub(crate) fn multiply_constant( let product = match scalar.dtype() { DType::Bool(_) => { - let val = scalar - .as_bool() - .value() - .ok_or_else(|| vortex_err!("Expected non-null bool scalar for sum"))?; + let val = scalar.as_bool().value().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected non-null bool scalar for sum"), + )?; if !val { return Ok(None); } Scalar::primitive(len as u64, Nullability::Nullable) } DType::Primitive(..) => { - let pvalue = scalar - .as_primitive() - .pvalue() - .ok_or_else(|| vortex_err!("Expected non-null primitive scalar for sum"))?; + let pvalue = scalar.as_primitive().pvalue().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected non-null primitive scalar for sum"), + )?; match return_dtype { DType::Primitive(PType::U64, _) => { let val = pvalue.cast::()?; @@ -61,19 +59,18 @@ pub(crate) fn multiply_constant( Scalar::primitive(val * len as f64, Nullability::Nullable) } _ => vortex_bail!( - "Unexpected return dtype for primitive sum: {}", + AssertionFailed: "Unexpected return dtype for primitive sum: {}", return_dtype ), } } DType::Decimal(..) => { - let val = scalar - .as_decimal() - .decimal_value() - .ok_or_else(|| vortex_err!("Expected non-null decimal scalar for sum"))?; + let val = scalar.as_decimal().decimal_value().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected non-null decimal scalar for sum"), + )?; let ret_decimal = *return_dtype .as_decimal_opt() - .ok_or_else(|| vortex_err!("Expected decimal return dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected decimal return dtype"))?; // Multiply in i256, the widest storage type, because the operands can be narrower // than the return type. Then check the product against the return precision. @@ -87,7 +84,7 @@ pub(crate) fn multiply_constant( None => Scalar::null(return_dtype.as_nullable()), } } - _ => vortex_bail!("Unsupported constant type for sum: {}", scalar.dtype()), + _ => vortex_bail!(InvalidArgument: "Unsupported constant type for sum: {}", scalar.dtype()), }; Ok(Some(product)) diff --git a/vortex-array/src/aggregate_fn/fns/sum/decimal.rs b/vortex-array/src/aggregate_fn/fns/sum/decimal.rs index 799d83b7219..6f67b22603d 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/decimal.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/decimal.rs @@ -40,7 +40,7 @@ pub(crate) fn accumulate_decimal( }; let SumState::Decimal(value) = inner else { - vortex_panic!("expected decimal sum state for decimal input"); + vortex_panic!(AssertionFailed: "expected decimal sum state for decimal input"); }; let dtype = return_dtype .as_decimal_opt() diff --git a/vortex-array/src/aggregate_fn/fns/sum/mod.rs b/vortex-array/src/aggregate_fn/fns/sum/mod.rs index 94c5fa7643d..1dbc4055aa3 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/mod.rs @@ -150,7 +150,7 @@ impl AggregateFnVTable for Sum { ) -> VortexResult { vortex_ensure!( scalar.dtype().eq_ignore_nullability(args.return_dtype), - "Sum partial has dtype {}, expected {}", + MismatchedTypes: "Sum partial has dtype {}, expected {}", scalar.dtype(), args.return_dtype ); @@ -283,7 +283,9 @@ impl AggregateFnVTable for Sum { } Canonical::Bool(b) => accumulate_bool(&mut inner, b, ctx), Canonical::Decimal(d) => accumulate_decimal(&mut inner, args.return_dtype, d, ctx), - _ => vortex_bail!("Unsupported canonical type for sum: {}", batch.dtype()), + _ => { + vortex_bail!(InvalidArgument: "Unsupported canonical type for sum: {}", batch.dtype()) + } }, Columnar::Constant(_) => unreachable!(), }; @@ -343,7 +345,7 @@ pub(crate) fn make_zero_state(return_dtype: &DType) -> SumState { PType::F16 | PType::F32 | PType::F64 => SumState::Float(0.0), }, DType::Decimal(decimal, _) => SumState::Decimal(DecimalValue::zero(decimal)), - _ => vortex_panic!("Unsupported sum type"), + _ => vortex_panic!(NotImplemented: "Unsupported sum type"), } } @@ -358,7 +360,7 @@ fn sum_state_from_scalar(scalar: &Scalar, return_dtype: &DType) -> VortexResult< } DType::Primitive(..) => SumState::Float(f64::try_from(scalar)?), DType::Decimal(..) => SumState::Decimal(DecimalValue::try_from(scalar)?), - _ => vortex_bail!("Unsupported sum type {}", return_dtype), + _ => vortex_bail!(InvalidArgument: "Unsupported sum type {}", return_dtype), }) } @@ -389,7 +391,7 @@ pub(crate) fn checked_add_sum_states( Some(_) | None => true, } } - _ => vortex_bail!("Mismatched sum partial states"), + _ => vortex_bail!(MismatchedTypes: "Mismatched sum partial states"), }) } diff --git a/vortex-array/src/aggregate_fn/fns/sum/primitive.rs b/vortex-array/src/aggregate_fn/fns/sum/primitive.rs index fe61454a914..5f582c8812e 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/primitive.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/primitive.rs @@ -43,23 +43,25 @@ fn accumulate_primitive_all( match inner { SumState::Unsigned(acc) => match_each_native_ptype!(p.ptype(), unsigned: |T| { Ok(sum_unsigned_all(acc, p.as_slice::())) }, - signed: |_T| { vortex_panic!("unsigned sum state with signed input") }, - floating: |_T| { vortex_panic!("unsigned sum state with float input") } + signed: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with signed input") }, + floating: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with float input") } ), SumState::Signed(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!("signed sum state with unsigned input") }, + unsigned: |_T| { vortex_panic!(AssertionFailed: "signed sum state with unsigned input") }, signed: |T| { Ok(sum_signed_all(acc, p.as_slice::())) }, - floating: |_T| { vortex_panic!("signed sum state with float input") } + floating: |_T| { vortex_panic!(AssertionFailed: "signed sum state with float input") } ), SumState::Float(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!("float sum state with unsigned input") }, - signed: |_T| { vortex_panic!("float sum state with signed input") }, + unsigned: |_T| { vortex_panic!(AssertionFailed: "float sum state with unsigned input") }, + signed: |_T| { vortex_panic!(AssertionFailed: "float sum state with signed input") }, floating: |T| { sum_float_all(acc, p.as_slice::(), skip_nans); Ok(false) } ), - SumState::Decimal(_) => vortex_panic!("decimal sum state with primitive input"), + SumState::Decimal(_) => { + vortex_panic!(AssertionFailed: "decimal sum state with primitive input") + } } } @@ -147,11 +149,11 @@ fn accumulate_primitive_valid( } Ok(false) }, - signed: |_T| { vortex_panic!("unsigned sum state with signed input") }, - floating: |_T| { vortex_panic!("unsigned sum state with float input") } + signed: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with signed input") }, + floating: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with float input") } ), SumState::Signed(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!("signed sum state with unsigned input") }, + unsigned: |_T| { vortex_panic!(AssertionFailed: "signed sum state with unsigned input") }, signed: |T| { let values = p.as_slice::(); for &(start, end) in slices { @@ -161,11 +163,11 @@ fn accumulate_primitive_valid( } Ok(false) }, - floating: |_T| { vortex_panic!("signed sum state with float input") } + floating: |_T| { vortex_panic!(AssertionFailed: "signed sum state with float input") } ), SumState::Float(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!("float sum state with unsigned input") }, - signed: |_T| { vortex_panic!("float sum state with signed input") }, + unsigned: |_T| { vortex_panic!(AssertionFailed: "float sum state with unsigned input") }, + signed: |_T| { vortex_panic!(AssertionFailed: "float sum state with signed input") }, floating: |T| { let values = p.as_slice::(); for &(start, end) in slices { @@ -174,7 +176,9 @@ fn accumulate_primitive_valid( Ok(false) } ), - SumState::Decimal(_) => vortex_panic!("decimal sum state with primitive input"), + SumState::Decimal(_) => { + vortex_panic!(AssertionFailed: "decimal sum state with primitive input") + } } } diff --git a/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs b/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs index 46fe681ab0a..fc4f9e71fc0 100644 --- a/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs @@ -95,7 +95,7 @@ impl SumV2 { sum.dtype(), DType::Primitive(PType::U64 | PType::I64 | PType::F64, _) ), - "Expected a widened primitive sum, got {}", + MismatchedTypes: "Expected a widened primitive sum, got {}", sum.dtype(), ); @@ -291,7 +291,9 @@ impl AggregateFnVTable for SumV2 { Canonical::Decimal(array) => { accumulate_decimal(&mut partial.sum, args.return_dtype, array, ctx) } - _ => vortex_bail!("Unsupported canonical type for sum_v2: {}", batch.dtype()), + _ => { + vortex_bail!(InvalidArgument: "Unsupported canonical type for sum_v2: {}", batch.dtype()) + } }, Columnar::Constant(_) => unreachable!(), }; @@ -403,23 +405,25 @@ fn decode_partial_scalar<'a>( scalar: &'a Scalar, return_dtype: &DType, ) -> VortexResult<(&'a ScalarValue, bool, bool)> { - vortex_ensure!(!scalar.is_null(), "SumV2 partial must not be null"); + vortex_ensure!(!scalar.is_null(), InvalidArgument: "SumV2 partial must not be null"); let (DType::Struct(fields, _), Some(ScalarValue::Tuple(values))) = (scalar.dtype(), scalar.value()) else { - vortex_bail!("SumV2 partial must be a struct, got {}", scalar.dtype()); + vortex_bail!(MismatchedTypes: "SumV2 partial must be a struct, got {}", scalar.dtype()); }; let field_index = |name: &str| { fields .find(name) - .ok_or_else(|| vortex_err!("SumV2 partial is missing the {name} field")) + .ok_or_else(|| vortex_err!(NotFound: "SumV2 partial is missing the {name} field")) }; let bool_field = |name: &str| -> VortexResult { match &values[field_index(name)?] { Some(ScalarValue::Bool(value)) => Ok(*value), - _ => vortex_bail!("SumV2 partial field {name} must be a non-null bool"), + _ => { + vortex_bail!(MismatchedTypes: "SumV2 partial field {name} must be a non-null bool") + } } }; @@ -432,7 +436,7 @@ fn decode_partial_scalar<'a>( let sum = values[sum_index] .as_ref() - .ok_or_else(|| vortex_err!("SumV2 partial sum must not be null"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "SumV2 partial sum must not be null"))?; Ok(( sum, @@ -445,7 +449,7 @@ fn validate_sum_field_dtype(sum_dtype: &DType, return_dtype: &DType) -> VortexRe vortex_ensure!( sum_dtype.nullability() == Nullability::NonNullable && sum_dtype.eq_ignore_nullability(return_dtype), - "SumV2 partial value has dtype {}, expected {}", + MismatchedTypes: "SumV2 partial value has dtype {}, expected {}", sum_dtype, return_dtype.as_nonnullable(), ); @@ -457,9 +461,9 @@ fn checked_add_sum_state( return_dtype: &DType, other: &Scalar, ) -> VortexResult { - let other = other - .value() - .ok_or_else(|| vortex_err!("Can't extract present value from null scalar"))?; + let other = other.value().ok_or_else( + || vortex_err!(InvalidArgument: "Can't extract present value from null scalar"), + )?; checked_add_sum_value(state, return_dtype, other) } @@ -491,7 +495,9 @@ fn checked_add_sum_value( Some(_) | None => true, } } - (_, other) => vortex_bail!("SumV2 cannot add {other} to a {return_dtype} sum"), + (_, other) => { + vortex_bail!(MismatchedTypes: "SumV2 cannot add {other} to a {return_dtype} sum") + } }) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs index 4c5c0a4df8d..7f6f9724606 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs @@ -23,5 +23,5 @@ pub(super) fn bool_uncompressed_size_in_bytes( value_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs index c04fa55f0ab..590326fac61 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs @@ -15,14 +15,16 @@ pub(super) fn decimal_uncompressed_size_in_bytes( ctx: &mut ExecutionCtx, ) -> VortexResult { let value_size = u64::try_from(array.len()) - .map_err(|e| vortex_err!("Failed to convert decimal array length to u64: {e}"))? + .map_err(|e| vortex_err!(Overflow: "Failed to convert decimal array length to u64: {e}"))? .checked_mul( u64::try_from( DecimalType::smallest_decimal_value_type(&array.decimal_dtype()).byte_width(), ) - .map_err(|e| vortex_err!("Failed to convert decimal byte width to u64: {e}"))?, + .map_err( + |e| vortex_err!(Overflow: "Failed to convert decimal byte width to u64: {e}"), + )?, ) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; let validity_size = validity_uncompressed_size_in_bytes( array .as_ref() @@ -32,5 +34,5 @@ pub(super) fn decimal_uncompressed_size_in_bytes( value_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs index 0d36b3b6208..947f42fb9d1 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs @@ -26,5 +26,5 @@ pub(super) fn fixed_size_list_uncompressed_size_in_bytes( elements_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs index 8abf0586396..9a30dfc4aa0 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs @@ -40,18 +40,18 @@ pub(super) fn list_view_uncompressed_size_in_bytes( }; let view_buffer_size = u64::try_from(array.len()) - .map_err(|e| vortex_err!("Failed to convert list array length to u64: {e}"))? + .map_err(|e| vortex_err!(Overflow: "Failed to convert list array length to u64: {e}"))? .checked_mul(8) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; // ListView stores both offsets and sizes as u64 view buffers. size = size .checked_add(view_buffer_size) .and_then(|size| size.checked_add(view_buffer_size)) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; size = size .checked_add(validity_uncompressed_size_in_bytes(validity)?) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; Ok(size) } @@ -135,7 +135,7 @@ fn referenced_elements_size( values_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } fn for_each_valid_list( diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs index 285d1948960..50cd013d347 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs @@ -142,7 +142,7 @@ pub fn uncompressed_size_in_bytes( let size = uncompressed_size_in_bytes_u64(array, opts, ctx)?; usize::try_from(size) - .map_err(|e| vortex_err!("Failed to convert uncompressed size to usize: {e}")) + .map_err(|e| vortex_err!(Overflow: "Failed to convert uncompressed size to usize: {e}")) } fn uncompressed_size_in_bytes_u64( @@ -160,7 +160,7 @@ fn uncompressed_size_in_bytes_u64( }; if let Some(size_scalar) = cached { return u64::try_from(&size_scalar) - .map_err(|e| vortex_err!("Failed to convert uncompressed size stat to u64: {e}")); + .map_err(|e| e.with_context("Failed to convert uncompressed size stat to u64")); } // The accumulator caches an exact size on `array` through the stat slot. @@ -260,7 +260,7 @@ impl AggregateFnVTable for UncompressedSizeInBytes { ) -> VortexResult { first .checked_add(second) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } fn to_scalar( @@ -298,7 +298,7 @@ impl AggregateFnVTable for UncompressedSizeInBytes { }; *partial = partial .checked_add(size) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; Ok(()) } @@ -344,7 +344,7 @@ pub(crate) fn canonical_uncompressed_size_in_bytes( Canonical::Union(array) => union_uncompressed_size_in_bytes(array, opts, ctx), Canonical::Extension(array) => extension_uncompressed_size_in_bytes(array, opts, ctx), Canonical::Variant(_) => { - vortex_bail!("UncompressedSizeInBytes is not supported for Variant arrays") + vortex_bail!(InvalidArgument: "UncompressedSizeInBytes is not supported for Variant arrays") } } } @@ -383,13 +383,13 @@ pub(crate) fn constant_uncompressed_size_in_bytes( return canonical_uncompressed_size_in_bytes(&canonical, opts, ctx); } DType::Variant(_) => { - vortex_bail!("UncompressedSizeInBytes is not supported for Variant arrays") + vortex_bail!(InvalidArgument: "UncompressedSizeInBytes is not supported for Variant arrays") } }; value_size .checked_add(constant_validity_size(array, ctx)?) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } fn constant_varbinview_value_size(len: usize, scalar_len: Option) -> VortexResult { @@ -397,13 +397,15 @@ fn constant_varbinview_value_size(len: usize, scalar_len: Option) -> Vort // Only a value too long to inline adds a data buffer, matching `constant_canonicalize`. let data_size = match scalar_len { Some(scalar_len) if scalar_len > BinaryView::MAX_INLINED_SIZE => u64::try_from(scalar_len) - .map_err(|e| vortex_err!("Failed to convert data buffer length to u64: {e}"))?, + .map_err( + |e| vortex_err!(Overflow: "Failed to convert data buffer length to u64: {e}"), + )?, _ => 0, }; views_size .checked_add(data_size) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } fn constant_validity_size( @@ -416,12 +418,12 @@ fn constant_validity_size( fn checked_len_mul(len: usize, width: usize, name: &str) -> VortexResult { let len = u64::try_from(len) - .map_err(|e| vortex_err!("Failed to convert {name} length to u64: {e}"))?; + .map_err(|e| vortex_err!(Overflow: "Failed to convert {name} length to u64: {e}"))?; let width = u64::try_from(width) - .map_err(|e| vortex_err!("Failed to convert {name} byte width to u64: {e}"))?; + .map_err(|e| vortex_err!(Overflow: "Failed to convert {name} byte width to u64: {e}"))?; len.checked_mul(width) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } fn supports_uncompressed_size_in_bytes(dtype: &DType) -> bool { @@ -462,7 +464,7 @@ pub(crate) fn validity_uncompressed_size_in_bytes(validity: Mask) -> VortexResul pub(crate) fn packed_bit_buffer_size_in_bytes(len: usize) -> VortexResult { u64::try_from(len.div_ceil(8)) - .map_err(|e| vortex_err!("Failed to convert bit buffer length to u64: {e}")) + .map_err(|e| vortex_err!(Overflow: "Failed to convert bit buffer length to u64: {e}")) } #[cfg(test)] @@ -560,7 +562,9 @@ mod tests { acc.finish()? .as_primitive() .typed_value::() - .ok_or_else(|| vortex_err!("uncompressed size result should not be null")) + .ok_or_else( + || vortex_err!(AssertionFailed: "uncompressed size result should not be null"), + ) } /// A view array whose rows point into one shared data buffer, like Arrow's Parquet reader diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs index 8ca149e791a..079f843f011 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs @@ -14,12 +14,11 @@ pub(super) fn primitive_uncompressed_size_in_bytes( ctx: &mut ExecutionCtx, ) -> VortexResult { let value_size = u64::try_from(array.len()) - .map_err(|e| vortex_err!("Failed to convert primitive array length to u64: {e}"))? - .checked_mul( - u64::try_from(array.ptype().byte_width()) - .map_err(|e| vortex_err!("Failed to convert primitive byte width to u64: {e}"))?, - ) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .map_err(|e| vortex_err!(Overflow: "Failed to convert primitive array length to u64: {e}"))? + .checked_mul(u64::try_from(array.ptype().byte_width()).map_err( + |e| vortex_err!(Overflow: "Failed to convert primitive byte width to u64: {e}"), + )?) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; let validity_size = validity_uncompressed_size_in_bytes( array .as_ref() @@ -29,5 +28,5 @@ pub(super) fn primitive_uncompressed_size_in_bytes( value_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs index 069a2df76bb..794bbce480c 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs @@ -21,7 +21,7 @@ pub(super) fn struct_uncompressed_size_in_bytes( for field in array.iter_unmasked_fields() { size = size .checked_add(uncompressed_size_in_bytes_u64(field, opts, ctx)?) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; } size = size @@ -31,7 +31,7 @@ pub(super) fn struct_uncompressed_size_in_bytes( .validity()? .execute_mask(array.as_ref().len(), ctx)?, )?) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; Ok(size) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs index 760a874d4a7..2aa0c71479f 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs @@ -21,7 +21,7 @@ pub(super) fn union_uncompressed_size_in_bytes( for child in array.iter_children() { size = size .checked_add(uncompressed_size_in_bytes_u64(child, opts, ctx)?) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; } Ok(size) diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs index 55cabfff1a4..41fea5e2c63 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs @@ -19,12 +19,13 @@ pub(super) fn varbinview_uncompressed_size_in_bytes( ctx: &mut ExecutionCtx, ) -> VortexResult { let views_size = u64::try_from(array.len()) - .map_err(|e| vortex_err!("Failed to convert varbinview array length to u64: {e}"))? - .checked_mul( - u64::try_from(size_of::()) - .map_err(|e| vortex_err!("Failed to convert binary view width to u64: {e}"))?, - ) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .map_err( + |e| vortex_err!(Overflow: "Failed to convert varbinview array length to u64: {e}"), + )? + .checked_mul(u64::try_from(size_of::()).map_err( + |e| vortex_err!(Overflow: "Failed to convert binary view width to u64: {e}"), + )?) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; let validity = array .as_ref() @@ -40,7 +41,7 @@ pub(super) fn varbinview_uncompressed_size_in_bytes( views_size .checked_add(data_size) .and_then(|size| size.checked_add(validity_uncompressed_size_in_bytes(validity).ok()?)) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) } /// Every byte of every data buffer, referenced or not. @@ -48,11 +49,10 @@ fn held_data_size(array: &VarBinViewArray) -> VortexResult { let mut size = 0u64; for buffer in array.data_buffers().iter() { size = size - .checked_add( - u64::try_from(buffer.len()) - .map_err(|e| vortex_err!("Failed to convert data buffer length to u64: {e}"))?, - ) - .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; + .checked_add(u64::try_from(buffer.len()).map_err( + |e| vortex_err!(Overflow: "Failed to convert data buffer length to u64: {e}"), + )?) + .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; } Ok(size) } diff --git a/vortex-array/src/aggregate_fn/foreign.rs b/vortex-array/src/aggregate_fn/foreign.rs index 7e32d9e0b2c..bc953fa0a60 100644 --- a/vortex-array/src/aggregate_fn/foreign.rs +++ b/vortex-array/src/aggregate_fn/foreign.rs @@ -82,7 +82,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { &self, _args: AggregateArgs<'_, Self::Options>, ) -> VortexResult { - vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) } fn partial_from_scalar( @@ -90,7 +90,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _scalar: &Scalar, ) -> VortexResult { - vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) } fn merge_partials( @@ -99,7 +99,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _first: Self::Partial, _second: Self::Partial, ) -> VortexResult { - vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) } fn to_scalar( @@ -107,7 +107,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) } fn is_saturated( @@ -125,7 +125,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _batch: &Columnar, _ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) } fn finalize( @@ -133,7 +133,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _states: ArrayRef, ) -> VortexResult { - vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) } fn finalize_scalar( @@ -141,7 +141,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) } } diff --git a/vortex-array/src/aggregate_fn/proto.rs b/vortex-array/src/aggregate_fn/proto.rs index 684d582ce21..c954ea80046 100644 --- a/vortex-array/src/aggregate_fn/proto.rs +++ b/vortex-array/src/aggregate_fn/proto.rs @@ -17,10 +17,9 @@ impl AggregateFnRef { /// /// Note: the serialization format is not stable and may change between versions. pub fn serialize_proto(&self) -> VortexResult { - let metadata = self - .options() - .serialize()? - .ok_or_else(|| vortex_err!("Aggregate function '{}' is not serializable", self.id()))?; + let metadata = self.options().serialize()?.ok_or_else( + || vortex_err!(Serde: "Aggregate function '{}' is not serializable", self.id()), + )?; Ok(pb::AggregateFn { id: self.id().to_string(), @@ -42,12 +41,12 @@ impl AggregateFnRef { } else if session.allows_unknown() { new_foreign_aggregate_fn(agg_fn_id, proto.metadata().to_vec()) } else { - return Err(vortex_err!("unknown aggregate function id: {}", proto.id)); + return Err(vortex_err!(NotFound: "unknown aggregate function id: {}", proto.id)); }; if agg_fn.id() != agg_fn_id { vortex_bail!( - "Aggregate function ID mismatch: expected {}, got {}", + MismatchedTypes: "Aggregate function ID mismatch: expected {}, got {}", agg_fn_id, agg_fn.id() ); @@ -152,7 +151,7 @@ mod tests { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_panic!("TestAgg is for serde tests only"); + vortex_panic!(NotImplemented: "TestAgg is for serde tests only"); } fn is_saturated( @@ -186,7 +185,7 @@ mod tests { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_panic!("TestAgg is for serde tests only"); + vortex_panic!(NotImplemented: "TestAgg is for serde tests only"); } } diff --git a/vortex-array/src/aggregate_fn/storage_pushdown.rs b/vortex-array/src/aggregate_fn/storage_pushdown.rs index 2e8d5123693..84ad002851b 100644 --- a/vortex-array/src/aggregate_fn/storage_pushdown.rs +++ b/vortex-array/src/aggregate_fn/storage_pushdown.rs @@ -144,7 +144,7 @@ impl ExtensionStoragePushdown { ) -> VortexResult> { let dtype = self.storage_dtype(args.dtype).ok_or_else(|| { vortex_err!( - "Aggregate function {} expects extension type {}, got {}", + MismatchedTypes: "Aggregate function {} expects extension type {}, got {}", self.id, self.ext.id(), args.dtype @@ -288,7 +288,7 @@ impl AggregateFnVTable for ExtensionStorageP } Columnar::Canonical(_) => { vortex_bail!( - "Aggregate function {} expects an extension array, got {}", + MismatchedTypes: "Aggregate function {} expects an extension array, got {}", self.id, batch.dtype() ) diff --git a/vortex-array/src/aggregate_fn/vtable.rs b/vortex-array/src/aggregate_fn/vtable.rs index ba236ab1d5f..3cb40bd243d 100644 --- a/vortex-array/src/aggregate_fn/vtable.rs +++ b/vortex-array/src/aggregate_fn/vtable.rs @@ -59,14 +59,14 @@ impl AggregateDTypes { ) -> VortexResult { let return_dtype = vtable.return_dtype(options, &dtype).ok_or_else(|| { vortex_err!( - "Aggregate function {} cannot be applied to dtype {}", + InvalidArgument: "Aggregate function {} cannot be applied to dtype {}", vtable.id(), dtype ) })?; let partial_dtype = vtable.partial_dtype(options, &dtype).ok_or_else(|| { vortex_err!( - "Aggregate function {} cannot be applied to dtype {}", + InvalidArgument: "Aggregate function {} cannot be applied to dtype {}", vtable.id(), dtype ) @@ -142,7 +142,7 @@ pub trait AggregateFnVTable: 'static + Sized + Clone + Send + Sync { _metadata: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!("Aggregate function {} is not deserializable", self.id()); + vortex_bail!(Serde: "Aggregate function {} is not deserializable", self.id()); } /// Return whether this stored aggregate can satisfy `requested`. diff --git a/vortex-array/src/array/erased.rs b/vortex-array/src/array/erased.rs index f630d42a4f8..14389400ada 100644 --- a/vortex-array/src/array/erased.rs +++ b/vortex-array/src/array/erased.rs @@ -219,10 +219,10 @@ impl ArrayRef { return Ok(self.clone()); } - vortex_ensure!(start <= len, "OutOfBounds: start {start} > length {}", len); - vortex_ensure!(stop <= len, "OutOfBounds: stop {stop} > length {}", len); + vortex_ensure!(start <= len, OutOfBounds: "OutOfBounds: start {start} > length {}", len); + vortex_ensure!(stop <= len, OutOfBounds: "OutOfBounds: stop {stop} > length {}", len); - vortex_ensure!(start <= stop, "start ({start}) must be <= stop ({stop})"); + vortex_ensure!(start <= stop, InvalidArgument: "start ({start}) must be <= stop ({stop})"); if start == stop { return Ok(Canonical::empty(self.dtype()).into_array()); @@ -368,10 +368,10 @@ impl ArrayRef { array_sum .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("sum of validity array is null"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "sum of validity array is null"))? } }; - vortex_ensure!(count <= len, "Valid count exceeds array length"); + vortex_ensure!(count <= len, InvalidArgument: "Valid count exceeds array length"); self.statistics() .set(Stat::NullCount, Precision::exact(len - count)); @@ -432,8 +432,9 @@ impl ArrayRef { /// /// Panics if the array is not of the given type. pub fn downcast(self) -> Array { - Self::try_downcast(self) - .unwrap_or_else(|_| vortex_panic!("Failed to downcast to {}", type_name::())) + Self::try_downcast(self).unwrap_or_else( + |_| vortex_panic!(MismatchedTypes: "Failed to downcast to {}", type_name::()), + ) } /// Returns a reference to the typed `ArrayData` if this array matches the given vtable type. @@ -498,7 +499,7 @@ impl ArrayRef { let nslots = slots.len(); vortex_ensure!( slot_idx < nslots, - "slot index {} out of bounds for array with {} slots", + OutOfBounds: "slot index {} out of bounds for array with {} slots", slot_idx, nslots ); @@ -508,13 +509,13 @@ impl ArrayRef { vortex_ensure_eq!( existing.dtype(), replacement.dtype(), - "slot {} dtype changed during physical rewrite", + AssertionFailed: "slot {} dtype changed during physical rewrite", slot_idx ); vortex_ensure_eq!( existing.len(), replacement.len(), - "slot {} len changed during physical rewrite", + AssertionFailed: "slot {} len changed during physical rewrite", slot_idx ); slots[slot_idx] = Some(replacement); @@ -597,26 +598,26 @@ impl ArrayRef { vortex_ensure_eq!( old_slots.len(), slots.len(), - "slot count changed during physical rewrite" + AssertionFailed: "slot count changed during physical rewrite" ); for (idx, (old_slot, new_slot)) in old_slots.iter().zip(slots.iter()).enumerate() { vortex_ensure_eq!( old_slot.is_some(), new_slot.is_some(), - "slot {} presence changed during physical rewrite", + AssertionFailed: "slot {} presence changed during physical rewrite", idx ); if let (Some(old_slot), Some(new_slot)) = (old_slot.as_ref(), new_slot.as_ref()) { vortex_ensure_eq!( old_slot.dtype(), new_slot.dtype(), - "slot {} dtype changed during physical rewrite", + AssertionFailed: "slot {} dtype changed during physical rewrite", idx ); vortex_ensure_eq!( old_slot.len(), new_slot.len(), - "slot {} len changed during physical rewrite", + AssertionFailed: "slot {} len changed during physical rewrite", idx ); } @@ -645,7 +646,7 @@ impl ArrayRef { vortex_ensure_eq!( nbuffers, buffers.len(), - "buffer count changed during physical rewrite" + AssertionFailed: "buffer count changed during physical rewrite" ); for (idx, (old_buffer, new_buffer)) in self .buffer_handles() @@ -656,7 +657,7 @@ impl ArrayRef { vortex_ensure_eq!( old_buffer.len(), new_buffer.len(), - "buffer {} length changed during physical rewrite", + AssertionFailed: "buffer {} length changed during physical rewrite", idx ); } diff --git a/vortex-array/src/array/foreign.rs b/vortex-array/src/array/foreign.rs index 57a0d74ba45..a153a5d2ea4 100644 --- a/vortex-array/src/array/foreign.rs +++ b/vortex-array/src/array/foreign.rs @@ -169,7 +169,7 @@ impl VTable for ForeignArray { fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { vortex_bail!( - "Cannot execute unknown array encoding '{}'", + NotFound: "Cannot execute unknown array encoding '{}'", array.encoding_id() ) } diff --git a/vortex-array/src/array/mod.rs b/vortex-array/src/array/mod.rs index fae796e1714..6229f4501f8 100644 --- a/vortex-array/src/array/mod.rs +++ b/vortex-array/src/array/mod.rs @@ -306,10 +306,10 @@ impl DynArrayData for ArrayData { let view = unsafe { ArrayView::new_unchecked(this, &self.data) }; let validity = >::validity(view)?; if let Validity::Array(array) = &validity { - vortex_ensure_eq!(array.len(), this.len(), "Validity array length mismatch"); + vortex_ensure_eq!(array.len(), this.len(), InvalidArgument: "Validity array length mismatch"); vortex_ensure!( matches!(array.dtype(), DType::Bool(Nullability::NonNullable)), - "Validity array is not non-nullable boolean: {}", + MismatchedTypes: "Validity array is not non-nullable boolean: {}", this.encoding_id(), ); } @@ -327,7 +327,7 @@ impl DynArrayData for ArrayData { ) -> VortexResult<()> { if builder.dtype() != this.dtype() { vortex_panic!( - "Builder dtype mismatch: expected {}, got {}", + MismatchedTypes: "Builder dtype mismatch: expected {}, got {}", this.dtype(), builder.dtype(), ); @@ -452,7 +452,7 @@ impl DynArrayData for ArrayData { vortex_ensure_eq!( reduced.len(), this.len(), - "Reduced array length mismatch from {} to {}", + AssertionFailed: "Reduced array length mismatch from {} to {}", this.encoding_id(), reduced.encoding_id() ); @@ -461,7 +461,7 @@ impl DynArrayData for ArrayData { reduced.dtype() == this.dtype() || (reduced.dtype().eq_ignore_nullability(this.dtype()) && !reduced.dtype().is_nullable()), - "Reduced array dtype mismatch from {} ({}) to {} ({})", + AssertionFailed: "Reduced array dtype mismatch from {} ({}) to {} ({})", this.encoding_id(), this.dtype(), reduced.encoding_id(), @@ -484,14 +484,14 @@ impl DynArrayData for ArrayData { vortex_ensure_eq!( reduced.len(), parent.len(), - "Reduced array length mismatch from {} to {}", + AssertionFailed: "Reduced array length mismatch from {} to {}", parent.encoding_id(), reduced.encoding_id() ); vortex_ensure_eq!( reduced.dtype(), parent.dtype(), - "Reduced array dtype mismatch from {} to {}", + AssertionFailed: "Reduced array dtype mismatch from {} to {}", parent.encoding_id(), reduced.encoding_id() ); @@ -510,13 +510,13 @@ impl DynArrayData for ArrayData { vortex_ensure_eq!( result.array().len(), len, - "Result length mismatch for {:?}", + AssertionFailed: "Result length mismatch for {:?}", self.vtable ); vortex_ensure_eq!( result.array().dtype(), &dtype, - "Executed canonical dtype mismatch for {:?}", + AssertionFailed: "Executed canonical dtype mismatch for {:?}", self.vtable ); } @@ -533,7 +533,7 @@ impl DynArrayData for ArrayData { ctx: &mut ExecutionCtx, ) -> VortexResult { let typed = Array::::try_from_array_ref(this) - .map_err(|_| vortex_err!("Failed to downcast array for execute")) + .map_err(|_| vortex_err!(AssertionFailed: "Failed to downcast array for execute")) .vortex_expect("Failed to downcast array for execute"); V::execute(typed, ctx) } diff --git a/vortex-array/src/array/plugin.rs b/vortex-array/src/array/plugin.rs index 979d644228c..cd937d8d4a1 100644 --- a/vortex-array/src/array/plugin.rs +++ b/vortex-array/src/array/plugin.rs @@ -175,7 +175,7 @@ impl ArrayPlugin for V { vortex_ensure_eq!( self.id(), array.encoding_id(), - "array plugin cannot serialize an in-memory array of another encoding", + Serde: "array plugin cannot serialize an in-memory array of another encoding", ); Ok(V::serialize(array.as_::(), session)? .map(|metadata| ArraySerialization::from_array(self.id(), array, metadata))) @@ -189,7 +189,7 @@ impl ArrayPlugin for V { vortex_ensure_eq!( self.id(), parts.serialized_id, - "array plugin does not recognize the serialized ID", + Serde: "array plugin does not recognize the serialized ID", ); Ok(Array::::try_from_parts(V::deserialize( self, diff --git a/vortex-array/src/array/probe/array.rs b/vortex-array/src/array/probe/array.rs index 57a908905a4..9356073965d 100644 --- a/vortex-array/src/array/probe/array.rs +++ b/vortex-array/src/array/probe/array.rs @@ -138,7 +138,7 @@ pub(super) fn check_bounds(array: &ArrayRef, index: usize) -> VortexResult<()> { #[cold] #[inline(never)] fn out_of_bounds(index: usize, len: usize) -> VortexError { - vortex_err!(OutOfBounds: index, 0, len) + vortex_err!(OutOfBounds: "index {index} out of bounds from 0 to {len}") } /// The encoding state type of `V`'s operations vtable. @@ -276,7 +276,7 @@ pub(super) fn child_of(parent: &ArrayRef, slot: usize) -> VortexResult() - .ok_or_else(|| vortex_err!("expected a primitive"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "expected a primitive"))?; let mut once = ProbeState::once(typed); assert!(once.is_valid(0, &mut ctx)?); @@ -407,7 +407,7 @@ mod tests { let all_valid = PrimitiveArray::from_option_iter([Some(1i32)]).into_array(); let typed = all_valid .as_opt::() - .ok_or_else(|| vortex_err!("expected a primitive"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "expected a primitive"))?; assert!(ProbeState::once(typed).is_valid(0, &mut ctx)?); Ok(()) } @@ -418,14 +418,16 @@ mod tests { let array = struct_of_two_fields()?; let typed = array .as_opt::() - .ok_or_else(|| vortex_err!("expected a struct"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected a struct"))?; let mut state = ProbeState::once(typed); assert!(state.slot(5).is_err()); // Slot 0 is the struct's absent validity. assert!(state.slot(0)?.is_none()); { - let mut field = state.slot(2)?.ok_or_else(|| vortex_err!("missing field"))?; + let mut field = state + .slot(2)? + .ok_or_else(|| vortex_err!(NotFound: "missing field"))?; assert!(matches!(field, ArrayProbe::Once(_))); assert_eq!(field.array().len(), 2); assert_eq!(field.execute_scalar(1, &mut ctx)?, Scalar::from(4i64)); @@ -436,7 +438,7 @@ mod tests { assert!(retained.is_none()); let mut field = children .slot(1)? - .ok_or_else(|| vortex_err!("missing field"))?; + .ok_or_else(|| vortex_err!(NotFound: "missing field"))?; assert_eq!(field.execute_scalar(1, &mut ctx)?, Scalar::from(2i32)); Ok(()) } diff --git a/vortex-array/src/array/probe/repeated.rs b/vortex-array/src/array/probe/repeated.rs index da0669f80a9..811604af0d8 100644 --- a/vortex-array/src/array/probe/repeated.rs +++ b/vortex-array/src/array/probe/repeated.rs @@ -122,7 +122,7 @@ pub(super) fn is_valid_scalar(scalar: Scalar, index: usize) -> VortexResult( ) -> VortexResult<&mut RepeatedState> { slot.get_or_insert_with(|| Box::new(RepeatedState::::default())) .downcast_mut::>() - .ok_or_else(|| vortex_err!("Probe state type mismatch")) + .ok_or_else(|| vortex_err!(MismatchedTypes: "Probe state type mismatch")) } /// What a [`RepeatedArrayProbe`] keeps for its encoding between reads. @@ -270,7 +270,7 @@ mod tests { let Some(ResolvedValidity::Array(validity)) = &repeated_state::<()>(&mut probe.state)?.validity else { - return Err(vortex_err!("validity slot should hold a probe")); + return Err(vortex_err!(AssertionFailed: "validity slot should hold a probe")); }; assert!(validity.state.is_some()); assert!(probe.execute_scalar(1, &mut ctx)?.is_null()); @@ -298,14 +298,16 @@ mod tests { let array = struct_of_two_fields()?; let typed = array .as_opt::() - .ok_or_else(|| vortex_err!("expected a struct"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected a struct"))?; let mut repeated = RepeatedState::<()>::default(); { let mut state = ProbeState::repeated(typed, &mut repeated); assert!(state.slot(5).is_err()); assert!(state.slot(0)?.is_none()); assert!(state.retained().is_some()); - let mut field = state.slot(2)?.ok_or_else(|| vortex_err!("missing field"))?; + let mut field = state + .slot(2)? + .ok_or_else(|| vortex_err!(NotFound: "missing field"))?; assert!(matches!(field, ArrayProbe::Repeated(_))); assert_eq!(field.execute_scalar(1, &mut ctx)?, Scalar::from(4i64)); assert_eq!(field.execute_scalar(0, &mut ctx)?, Scalar::from(3i64)); @@ -315,7 +317,7 @@ mod tests { assert!(repeated.slots[1].is_none()); let child = repeated.slots[2] .as_ref() - .ok_or_else(|| vortex_err!("missing child probe"))?; + .ok_or_else(|| vortex_err!(NotFound: "missing child probe"))?; assert_eq!(child.array().len(), 2); Ok(()) } diff --git a/vortex-array/src/array/vtable/mod.rs b/vortex-array/src/array/vtable/mod.rs index e4a23ebe16c..89f9c4f6137 100644 --- a/vortex-array/src/array/vtable/mod.rs +++ b/vortex-array/src/array/vtable/mod.rs @@ -243,7 +243,7 @@ pub fn with_empty_buffers( ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - "Array {} expects 0 buffers, got {}", + InvalidArgument: "Array {} expects 0 buffers, got {}", array.encoding_id(), buffers.len() ); @@ -263,7 +263,7 @@ pub fn unsupported_buffer_replacement( _buffers: &[BufferHandle], ) -> VortexResult> { vortex_bail!( - "Array {} does not support in-memory buffer replacement", + InvalidArgument: "Array {} does not support in-memory buffer replacement", array.encoding_id() ) } @@ -331,7 +331,7 @@ pub fn patches_child(patches: &Patches, idx: usize) -> ArrayRef { .as_ref() .vortex_expect("patch_chunk_offsets child out of bounds") .clone(), - _ => vortex_panic!("patches child index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "patches child index {idx} out of bounds"), } } @@ -342,6 +342,6 @@ pub fn patches_child_name(idx: usize) -> &'static str { 0 => "patch_indices", 1 => "patch_values", 2 => "patch_chunk_offsets", - _ => vortex_panic!("patches child name index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "patches child name index {idx} out of bounds"), } } diff --git a/vortex-array/src/array/vtable/operations.rs b/vortex-array/src/array/vtable/operations.rs index 0ffbeef953a..c8ee269a4f0 100644 --- a/vortex-array/src/array/vtable/operations.rs +++ b/vortex-array/src/array/vtable/operations.rs @@ -85,7 +85,7 @@ impl OperationsVTable for NotSupported { _ctx: &mut ExecutionCtx, ) -> VortexResult { vortex_bail!( - "Legacy scalar_at operation is not supported for {} arrays", + InvalidArgument: "Legacy scalar_at operation is not supported for {} arrays", array.encoding_id() ) } diff --git a/vortex-array/src/arrays/bool/array.rs b/vortex-array/src/arrays/bool/array.rs index d72a4b439e5..ad9e270cf8e 100644 --- a/vortex-array/src/arrays/bool/array.rs +++ b/vortex-array/src/arrays/bool/array.rs @@ -268,18 +268,18 @@ impl BoolData { len: usize, validity: Validity, ) -> VortexResult { - vortex_ensure!(offset < 8, "BitBuffer offset must be <8, got {}", offset); + vortex_ensure!(offset < 8, InvalidArgument: "BitBuffer offset must be <8, got {}", offset); if let Some(validity_len) = validity.maybe_len() { vortex_ensure_eq!( validity_len, len, - "BoolArray validity length does not match array length", + InvalidArgument: "BoolArray validity length does not match array length", ); } vortex_ensure!( bits.len() * 8 >= (len + offset), - "provided BufferHandle with offset {offset} len {len} had size {} bits", + InvalidArgument: "provided BufferHandle with offset {offset} len {len} had size {} bits", bits.len() * 8, ); @@ -305,7 +305,7 @@ impl BoolData { pub(super) fn validate(bits: &BitBuffer, validity: &Validity) -> VortexResult<()> { vortex_ensure!( bits.offset() < 8, - "BitBuffer offset must be <8, got {}", + InvalidArgument: "BitBuffer offset must be <8, got {}", bits.offset() ); @@ -313,7 +313,7 @@ impl BoolData { vortex_ensure_eq!( validity_len, bits.len(), - "BoolArray validity length does not match array length", + InvalidArgument: "BoolArray validity length does not match array length", ); } diff --git a/vortex-array/src/arrays/bool/compute/boolean.rs b/vortex-array/src/arrays/bool/compute/boolean.rs index 28d1bbb7f52..427442598e3 100644 --- a/vortex-array/src/arrays/bool/compute/boolean.rs +++ b/vortex-array/src/arrays/bool/compute/boolean.rs @@ -28,7 +28,7 @@ impl BooleanKernel for Bool { let rhs = rhs .scalar() .as_bool_opt() - .ok_or_else(|| vortex_err!("expected boolean scalar"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))?; return kleene_boolean_buffer_scalar( lhs.to_bit_buffer(), lhs.validity()?, diff --git a/vortex-array/src/arrays/bool/compute/fill_null.rs b/vortex-array/src/arrays/bool/compute/fill_null.rs index 94966f2e829..dddc5119493 100644 --- a/vortex-array/src/arrays/bool/compute/fill_null.rs +++ b/vortex-array/src/arrays/bool/compute/fill_null.rs @@ -24,7 +24,7 @@ impl FillNullKernel for Bool { let fill = fill_value .as_bool() .value() - .ok_or_else(|| vortex_err!("Fill value must be non null"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "Fill value must be non null"))?; Ok(Some(match array.validity()? { Validity::Array(v) => { diff --git a/vortex-array/src/arrays/bool/compute/mask.rs b/vortex-array/src/arrays/bool/compute/mask.rs index 818dbaebca5..a44220a89b6 100644 --- a/vortex-array/src/arrays/bool/compute/mask.rs +++ b/vortex-array/src/arrays/bool/compute/mask.rs @@ -75,14 +75,14 @@ mod tests { } fn copy_to_host_sync(&self, _alignment: Alignment) -> VortexResult { - vortex_bail!("mask reduction must not copy device values") + vortex_bail!(InvalidArgument: "mask reduction must not copy device values") } fn copy_to_host( &self, _alignment: Alignment, ) -> VortexResult>> { - vortex_bail!("mask reduction must not copy device values") + vortex_bail!(InvalidArgument: "mask reduction must not copy device values") } fn slice(&self, _range: Range) -> Arc { diff --git a/vortex-array/src/arrays/bool/compute/take.rs b/vortex-array/src/arrays/bool/compute/take.rs index a19b994bf5c..4bccdf9b9a9 100644 --- a/vortex-array/src/arrays/bool/compute/take.rs +++ b/vortex-array/src/arrays/bool/compute/take.rs @@ -132,14 +132,13 @@ fn take_bit_slices_constant_length( where S: UnsignedPType, { - let computed_len = starts - .len() - .checked_mul(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + let computed_len = starts.len().checked_mul(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; vortex_ensure_eq!( computed_len, output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); let mut values = BitBufferMut::with_capacity(output_len); @@ -171,7 +170,7 @@ where vortex_ensure_eq!( values.len(), output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); Ok(values.freeze()) } diff --git a/vortex-array/src/arrays/bool/test_harness.rs b/vortex-array/src/arrays/bool/test_harness.rs index 66bfd26771c..fa4a9cf70ec 100644 --- a/vortex-array/src/arrays/bool/test_harness.rs +++ b/vortex-array/src/arrays/bool/test_harness.rs @@ -31,7 +31,7 @@ impl BoolArray { .zip(self.to_bit_buffer().iter()) .map(|(valid, value)| { if !valid { - vortex_panic!("trying to get bool values from an array with null elements") + vortex_panic!(AssertionFailed: "trying to get bool values from an array with null elements") } value diff --git a/vortex-array/src/arrays/bool/vtable/mod.rs b/vortex-array/src/arrays/bool/vtable/mod.rs index 18fea87307d..ab94175b9bc 100644 --- a/vortex-array/src/arrays/bool/vtable/mod.rs +++ b/vortex-array/src/arrays/bool/vtable/mod.rs @@ -86,7 +86,7 @@ impl VTable for Bool { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.bits.clone(), - _ => vortex_panic!("BoolArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "BoolArray buffer index {idx} out of bounds"), } } @@ -102,7 +102,7 @@ impl VTable for Bool { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1); + vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); let mut data = array.data().clone(); data.bits = buffers[0].clone(); Ok(ArrayParts::new( @@ -136,11 +136,11 @@ impl VTable for Bool { slots: &[Option], ) -> VortexResult<()> { let DType::Bool(nullability) = dtype else { - vortex_bail!("Expected bool dtype, got {dtype:?}"); + vortex_bail!(MismatchedTypes: "Expected bool dtype, got {dtype:?}"); }; vortex_ensure!( data.bits.len() * 8 >= data.meta.offset() + len, - "BoolArray buffer with offset {} cannot back outer length {} (buffer bits = {})", + InvalidArgument: "BoolArray buffer with offset {} cannot back outer length {} (buffer bits = {})", data.meta.offset(), len, data.bits.len() * 8 @@ -151,7 +151,7 @@ impl VTable for Bool { vortex_ensure_eq!( validity_len, len, - "BoolArray validity len does not match outer length", + InvalidArgument: "BoolArray validity len does not match outer length", ); } @@ -169,7 +169,7 @@ impl VTable for Bool { ) -> VortexResult> { let metadata = BoolMetadata::decode(metadata)?; if buffers.len() != 1 { - vortex_bail!("Expected 1 buffer, got {}", buffers.len()); + vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); } let validity = if children.is_empty() { @@ -178,7 +178,7 @@ impl VTable for Bool { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("Expected 0 or 1 child, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 0 or 1 child, got {}", children.len()); }; let buffer = buffers[0].clone(); @@ -203,7 +203,7 @@ impl VTable for Bool { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for Bool requires a BoolBuilder"); + vortex_bail!(InvalidArgument: "append_to_builder for Bool requires a BoolBuilder"); }; builder.append_bool_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/chunked/array.rs b/vortex-array/src/arrays/chunked/array.rs index 6c0169d7a7c..361ca4a6004 100644 --- a/vortex-array/src/arrays/chunked/array.rs +++ b/vortex-array/src/arrays/chunked/array.rs @@ -149,7 +149,7 @@ impl ChunkedData { pub fn validate(chunks: &[ArrayRef], dtype: &DType) -> VortexResult<()> { for chunk in chunks { if chunk.dtype() != dtype { - vortex_bail!(MismatchedTypes: dtype, chunk.dtype()); + vortex_bail!(MismatchedTypes: "expected type: {} but instead got {}", dtype, chunk.dtype()); } } @@ -172,7 +172,7 @@ impl Array { for chunk in chunks { if VALIDATE && chunk.dtype() != &dtype { - vortex_bail!(MismatchedTypes: &dtype, chunk.dtype()); + vortex_bail!(MismatchedTypes: "expected type: {} but instead got {}", &dtype, chunk.dtype()); } len += chunk.len(); chunk_offsets.push(len); diff --git a/vortex-array/src/arrays/chunked/compute/take.rs b/vortex-array/src/arrays/chunked/compute/take.rs index 15511c5a8cc..52a6a3eb7c4 100644 --- a/vortex-array/src/arrays/chunked/compute/take.rs +++ b/vortex-array/src/arrays/chunked/compute/take.rs @@ -97,7 +97,7 @@ fn take_chunked_via_sort( if let Some(&(index, _)) = pairs.last() { let index = usize::try_from(index)?; if index >= array.len() { - vortex_bail!(OutOfBounds: index, 0, array.len()); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", index, 0, array.len()); } } @@ -209,7 +209,7 @@ fn take_chunked( let index = usize::try_from(index)?; if index >= array.len() { - vortex_bail!(OutOfBounds: index, 0, array.len()); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", index, 0, array.len()); } let still_sorted = last_index.is_none_or(|last_index| index >= last_index); @@ -314,8 +314,7 @@ fn take_chunked_sorted( } if cursor != indices_values.len() { vortex_bail!( - OutOfBounds: usize::try_from(indices_values[cursor])?, 0, array.as_ref().len() - ); + OutOfBounds: "index {} out of bounds from {} to {}", usize::try_from(indices_values[cursor])?, 0, array.as_ref().len()); } if chunks.len() == 1 { @@ -432,13 +431,13 @@ fn take_piecewise_chunked( } let end = start .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"))?; if end > array_len { - vortex_bail!(OutOfBounds: end - 1, 0, array_len); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", end - 1, 0, array_len); } - total_len = total_len - .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + total_len = total_len.checked_add(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; // Locate the chunk containing `start`; `<=` skips empty chunks sharing the same offset. let mut chunk_idx = chunk_offsets.partition_point(|&offset| offset <= start) - 1; @@ -481,7 +480,7 @@ fn take_piecewise_chunked( vortex_ensure_eq!( total_len, output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); // Chunks visited in order: the per-chunk gathers already concatenate into the result. diff --git a/vortex-array/src/arrays/chunked/vtable/canonical.rs b/vortex-array/src/arrays/chunked/vtable/canonical.rs index b0c935fcedb..0d42aa41126 100644 --- a/vortex-array/src/arrays/chunked/vtable/canonical.rs +++ b/vortex-array/src/arrays/chunked/vtable/canonical.rs @@ -114,7 +114,7 @@ fn pack_variant_chunks( for chunk in &variant_chunks[1..] { vortex_ensure!( chunk.shredded().is_none(), - "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" + NotImplemented: "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" ); } None @@ -127,13 +127,13 @@ fn pack_variant_chunks( for chunk in &variant_chunks[1..] { let shredded = chunk.shredded().ok_or_else(|| { vortex_err!( - "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" + NotImplemented: "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" ) })?; vortex_ensure_eq!( shredded.dtype(), &shredded_dtype, - "cannot canonicalize ChunkedArray: shredded dtype mismatch", + MismatchedTypes: "cannot canonicalize ChunkedArray: shredded dtype mismatch", ); shredded_chunks.push(shredded.clone()); } @@ -366,7 +366,9 @@ mod tests { fn into_variant(canonical: Canonical) -> VortexResult { match canonical { Canonical::Variant(array) => Ok(array), - other => vortex_bail!("expected Variant canonical array, got {other:?}"), + other => { + vortex_bail!(MismatchedTypes: "expected Variant canonical array, got {other:?}") + } } } @@ -426,7 +428,7 @@ mod tests { let variant = into_variant(chunked.execute::(&mut ctx)?)?; let shredded = variant .shredded() - .ok_or_else(|| vortex_err!("expected shredded child"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected shredded child"))?; for (index, value) in [1, 2, 3].into_iter().enumerate() { assert_eq!( @@ -549,7 +551,9 @@ mod tests { let canonical = chunked.clone().execute::(&mut ctx)?; let fsl = match canonical { Canonical::FixedSizeList(fsl) => fsl, - other => vortex_bail!("expected FixedSizeList canonical array, got {other:?}"), + other => { + vortex_bail!(MismatchedTypes: "expected FixedSizeList canonical array, got {other:?}") + } }; assert_eq!(fsl.len(), 5); diff --git a/vortex-array/src/arrays/chunked/vtable/mod.rs b/vortex-array/src/arrays/chunked/vtable/mod.rs index cfd8b94cb90..05cb07d14fc 100644 --- a/vortex-array/src/arrays/chunked/vtable/mod.rs +++ b/vortex-array/src/arrays/chunked/vtable/mod.rs @@ -86,7 +86,7 @@ impl VTable for Chunked { ) -> VortexResult<()> { vortex_ensure!( !slots.is_empty(), - "ChunkedArray must have at least a chunk offsets slot" + InvalidArgument: "ChunkedArray must have at least a chunk offsets slot" ); let chunk_offsets = slots[ChunkedSlots::CHUNK_OFFSETS] .as_ref() @@ -94,17 +94,17 @@ impl VTable for Chunked { vortex_ensure_eq!( chunk_offsets.dtype(), &DType::Primitive(PType::U64, Nullability::NonNullable), - "ChunkedArray chunk offsets must be non-nullable u64", + MismatchedTypes: "ChunkedArray chunk offsets must be non-nullable u64", ); vortex_ensure_eq!( chunk_offsets.len(), data.chunk_offsets.len(), - "ChunkedArray chunk offsets slot length does not match cached offsets length", + InvalidArgument: "ChunkedArray chunk offsets slot length does not match cached offsets length", ); vortex_ensure_eq!( data.chunk_offsets.len(), slots.len() - ChunkedSlots::CHUNKS_OFFSET + 1, - "ChunkedArray must have one more chunk offset than chunks", + InvalidArgument: "ChunkedArray must have one more chunk offset than chunks", ); vortex_ensure_eq!( data.chunk_offsets @@ -112,7 +112,7 @@ impl VTable for Chunked { .copied() .vortex_expect("chunked arrays always have a leading 0 offset"), len, - "ChunkedArray length does not match outer length", + InvalidArgument: "ChunkedArray length does not match outer length", ); for (idx, (start, end)) in data .chunk_offsets @@ -127,12 +127,12 @@ impl VTable for Chunked { vortex_ensure_eq!( chunk.dtype(), dtype, - "ChunkedArray chunk dtype does not match outer dtype", + MismatchedTypes: "ChunkedArray chunk dtype does not match outer dtype", ); vortex_ensure_eq!( chunk.len(), end - start, - "ChunkedArray chunk {idx} len does not match offsets span", + InvalidArgument: "ChunkedArray chunk {idx} len does not match offsets span", ); } Ok(()) @@ -143,11 +143,11 @@ impl VTable for Chunked { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ChunkedArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ChunkedArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("ChunkedArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ChunkedArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -176,12 +176,12 @@ impl VTable for Chunked { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "ChunkedArray expects empty metadata, got {} bytes", + InvalidArgument: "ChunkedArray expects empty metadata, got {} bytes", metadata.len() ); } if children.is_empty() { - vortex_bail!("Chunked array needs at least one child"); + vortex_bail!(InvalidArgument: "Chunked array needs at least one child"); } let nchunks = children.len() - 1; @@ -200,7 +200,7 @@ impl VTable for Chunked { .copied() .map(|offset| { usize::try_from(offset) - .map_err(|_| vortex_err!("chunk offset {offset} exceeds usize range")) + .map_err(|_| vortex_err!(Overflow: "chunk offset {offset} exceeds usize range")) }) .collect::>>()?; let mut slots = SmallVec::with_capacity(children.len()); @@ -250,7 +250,7 @@ impl VTable for Chunked { match array.dtype() { DType::Union(..) => { vortex_bail!( - "TODO(connor)[Union]: canonicalize chunked Union arrays by packing type IDs \ + NotImplemented: "TODO(connor)[Union]: canonicalize chunked Union arrays by packing type IDs \ and every sparse child along identical chunk boundaries" ) } diff --git a/vortex-array/src/arrays/chunked/vtable/operations.rs b/vortex-array/src/arrays/chunked/vtable/operations.rs index f228228acf4..ef9c7f9b8e5 100644 --- a/vortex-array/src/arrays/chunked/vtable/operations.rs +++ b/vortex-array/src/arrays/chunked/vtable/operations.rs @@ -25,7 +25,7 @@ impl OperationsVTable for Chunked { let slot = ChunkedSlots::CHUNKS_OFFSET + chunk_index; state .slot(slot)? - .ok_or_else(|| vortex_err!("Chunked chunk slot {slot} is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "Chunked chunk slot {slot} is missing"))? .execute_scalar(chunk_offset, ctx) } diff --git a/vortex-array/src/arrays/constant/compute/uncompressed_size.rs b/vortex-array/src/arrays/constant/compute/uncompressed_size.rs index 380adde03ab..1f2cc803674 100644 --- a/vortex-array/src/arrays/constant/compute/uncompressed_size.rs +++ b/vortex-array/src/arrays/constant/compute/uncompressed_size.rs @@ -41,7 +41,9 @@ mod tests { acc.finish()? .as_primitive() .typed_value::() - .ok_or_else(|| vortex_err!("uncompressed size result should not be null")) + .ok_or_else( + || vortex_err!(AssertionFailed: "uncompressed size result should not be null"), + ) } #[test] diff --git a/vortex-array/src/arrays/constant/vtable/canonical.rs b/vortex-array/src/arrays/constant/vtable/canonical.rs index bbea85c4077..cd70452d5a9 100644 --- a/vortex-array/src/arrays/constant/vtable/canonical.rs +++ b/vortex-array/src/arrays/constant/vtable/canonical.rs @@ -333,7 +333,7 @@ fn flat_elements( DType::Bool(nullability) => { let bits = BitBuffer::from_iter(elements.iter().map(|element| match element { Some(ScalarValue::Bool(value)) => *value, - Some(_) => vortex_panic!("bool list holds a non-bool element"), + Some(_) => vortex_panic!(AssertionFailed: "bool list holds a non-bool element"), None => false, })); BoolArray::new(bits, element_validity(elements, *nullability)).into_array() @@ -345,7 +345,7 @@ fn flat_elements( Some(ScalarValue::Primitive(value)) => value .cast::() .vortex_expect("list element of the list's element ptype"), - Some(_) => vortex_panic!("primitive list holds a non-primitive element"), + Some(_) => vortex_panic!(AssertionFailed: "primitive list holds a non-primitive element"), None => T::default(), } })); @@ -362,7 +362,7 @@ fn flat_elements( Some(ScalarValue::Decimal(value)) => value .cast::() .vortex_expect("list element fits the list's decimal type"), - Some(_) => vortex_panic!("decimal list holds a non-decimal element"), + Some(_) => vortex_panic!(AssertionFailed: "decimal list holds a non-decimal element"), None => T::default(), } })); @@ -385,7 +385,7 @@ fn flat_elements( None => builder.append_null(), Some(ScalarValue::Utf8(value)) => builder.append_value(value.as_bytes()), Some(ScalarValue::Binary(value)) => builder.append_value(value.as_slice()), - Some(_) => vortex_panic!("byte list holds a non-byte element"), + Some(_) => vortex_panic!(AssertionFailed: "byte list holds a non-byte element"), } } builder.finish() @@ -1200,7 +1200,7 @@ mod tests { fn date_elements() -> ArrayRef { let date = Scalar::extension::(TimeUnit::Days, Scalar::from(Some(42i32))); let DType::Extension(ext_dtype) = date.dtype().clone() else { - vortex_panic!("a date is an extension value"); + vortex_panic!(AssertionFailed: "a date is an extension value"); }; ExtensionArray::new( ext_dtype, diff --git a/vortex-array/src/arrays/constant/vtable/mod.rs b/vortex-array/src/arrays/constant/vtable/mod.rs index 3b55071ffb8..29150b24138 100644 --- a/vortex-array/src/arrays/constant/vtable/mod.rs +++ b/vortex-array/src/arrays/constant/vtable/mod.rs @@ -96,7 +96,7 @@ impl VTable for Constant { vortex_ensure_eq!( data.scalar.dtype(), dtype, - "ConstantArray scalar dtype does not match outer dtype", + MismatchedTypes: "ConstantArray scalar dtype does not match outer dtype", ); Ok(()) } @@ -110,7 +110,7 @@ impl VTable for Constant { 0 => BufferHandle::new_host( ScalarValue::to_proto_bytes::>(array.scalar.value()).into(), ), - _ => vortex_panic!("ConstantArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "ConstantArray buffer index {idx} out of bounds"), } } @@ -130,7 +130,7 @@ impl VTable for Constant { } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { - vortex_panic!("ConstantArray slot_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ConstantArray slot_name index {idx} out of bounds") } fn serialize( @@ -152,7 +152,7 @@ impl VTable for Constant { _children: &dyn ArrayChildren, session: &VortexSession, ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1); + vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); let buffer = buffers[0].clone().try_to_host_sync()?; let bytes: &[u8] = buffer.as_ref(); diff --git a/vortex-array/src/arrays/datetime/mod.rs b/vortex-array/src/arrays/datetime/mod.rs index 25913deb8b2..d4eb347f1ff 100644 --- a/vortex-array/src/arrays/datetime/mod.rs +++ b/vortex-array/src/arrays/datetime/mod.rs @@ -176,10 +176,10 @@ impl TryFrom for TemporalData { fn try_from(value: ArrayRef) -> Result { let ext = value .as_opt::() - .ok_or_else(|| vortex_err!("array must be an ExtensionArray"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "array must be an ExtensionArray"))?; if !ext.ext_dtype().is::() { vortex_bail!( - "array extension dtype {} is not a temporal type", + MismatchedTypes: "array extension dtype {} is not a temporal type", ext.ext_dtype() ); } @@ -208,7 +208,7 @@ impl TryFrom for TemporalData { fn try_from(ext: ExtensionArray) -> Result { if !ext.ext_dtype().is::() { vortex_bail!( - "array extension dtype {} is not a temporal type", + MismatchedTypes: "array extension dtype {} is not a temporal type", ext.ext_dtype() ); } diff --git a/vortex-array/src/arrays/decimal/array.rs b/vortex-array/src/arrays/decimal/array.rs index eff2e5c8688..4bd549f055a 100644 --- a/vortex-array/src/arrays/decimal/array.rs +++ b/vortex-array/src/arrays/decimal/array.rs @@ -360,7 +360,7 @@ impl DecimalData { pub fn buffer(&self) -> Buffer { if self.values_type != T::DECIMAL_TYPE { vortex_panic!( - "Cannot extract Buffer<{:?}> for DecimalArray with values_type {:?}", + MismatchedTypes: "Cannot extract Buffer<{:?}> for DecimalArray with values_type {:?}", T::DECIMAL_TYPE, self.values_type, ); @@ -593,7 +593,7 @@ where { if !ValuesDVT::DECIMAL_TYPE.is_compatible_decimal_value_type(decimal_dtype) { vortex_panic!( - "patch_typed: {:?} cannot represent every value in {}.", + Overflow: "patch_typed: {:?} cannot represent every value in {}.", ValuesDVT::DECIMAL_TYPE, decimal_dtype ) diff --git a/vortex-array/src/arrays/decimal/compute/cast.rs b/vortex-array/src/arrays/decimal/compute/cast.rs index 29b38ce9406..cbe747acfa5 100644 --- a/vortex-array/src/arrays/decimal/compute/cast.rs +++ b/vortex-array/src/arrays/decimal/compute/cast.rs @@ -51,7 +51,7 @@ impl CastReduce for Decimal { }; let DType::Decimal(from_decimal_dtype, _) = array.dtype() else { vortex_panic!( - "DecimalArray must have decimal dtype, got {:?}", + MismatchedTypes: "DecimalArray must have decimal dtype, got {:?}", array.dtype() ); }; @@ -90,7 +90,7 @@ impl CastKernel for Decimal { ) -> VortexResult> { let DType::Decimal(from_decimal_dtype, _) = array.dtype() else { vortex_panic!( - "DecimalArray must have decimal dtype, got {:?}", + MismatchedTypes: "DecimalArray must have decimal dtype, got {:?}", array.dtype() ); }; @@ -318,7 +318,7 @@ where .and_then(|value| { value.cast::().ok_or_else(|| { vortex_err!( - "decimal value cannot be represented as {} after casting to {}", + InvalidArgument: "decimal value cannot be represented as {} after casting to {}", T::DECIMAL_TYPE, to_decimal_dtype ) @@ -334,7 +334,7 @@ where (from {from_decimal_dtype} to {to_decimal_dtype})" ); vortex_err!( - "decimal value cannot be represented as {} after casting from {} to {}", + InvalidArgument: "decimal value cannot be represented as {} after casting from {} to {}", T::DECIMAL_TYPE, from_decimal_dtype, to_decimal_dtype @@ -461,7 +461,7 @@ pub fn upcast_decimal_values( // Only allow upcasting (widening) if to_values_type < from_values_type { vortex_bail!( - "Cannot downcast decimal values from {:?} to {:?}. Only upcasting is supported.", + InvalidArgument: "Cannot downcast decimal values from {:?} to {:?}. Only upcasting is supported.", from_values_type, to_values_type ); diff --git a/vortex-array/src/arrays/decimal/compute/rules.rs b/vortex-array/src/arrays/decimal/compute/rules.rs index 8f1d09ea92a..805bee61102 100644 --- a/vortex-array/src/arrays/decimal/compute/rules.rs +++ b/vortex-array/src/arrays/decimal/compute/rules.rs @@ -133,14 +133,14 @@ mod tests { } fn copy_to_host_sync(&self, _alignment: Alignment) -> VortexResult { - vortex_bail!("decimal slicing must not copy device values to the host") + vortex_bail!(InvalidArgument: "decimal slicing must not copy device values to the host") } fn copy_to_host( &self, _alignment: Alignment, ) -> VortexResult>> { - vortex_bail!("decimal slicing must not copy device values to the host") + vortex_bail!(InvalidArgument: "decimal slicing must not copy device values to the host") } fn slice(&self, range: Range) -> Arc { @@ -202,7 +202,7 @@ mod tests { .as_device() .as_any() .downcast_ref::() - .ok_or_else(|| vortex_err!("expected TestDeviceBuffer"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "expected TestDeviceBuffer"))? .0; assert_eq!(actual_bytes, &expected_bytes); assert_eq!(actual_bytes.as_ptr(), expected_bytes.as_ptr()); diff --git a/vortex-array/src/arrays/decimal/utils.rs b/vortex-array/src/arrays/decimal/utils.rs index 3c7304e6fda..73bd6ec944c 100644 --- a/vortex-array/src/arrays/decimal/utils.rs +++ b/vortex-array/src/arrays/decimal/utils.rs @@ -59,7 +59,7 @@ pub fn converted_buffer( .find(|&(_, v)| W::from(*v).is_none()) .vortex_expect("overflow scan found an overflowing value"); vortex_bail!( - "decimal value {v} at index {i} does not fit {}", + Overflow: "decimal value {v} at index {i} does not fit {}", W::DECIMAL_TYPE ); } @@ -71,7 +71,7 @@ pub fn converted_buffer( for (i, v) in src.iter().enumerate() { if values.value(i) && W::from(*v).is_none() { vortex_bail!( - "decimal value {v} at index {i} does not fit {}", + Overflow: "decimal value {v} at index {i} does not fit {}", W::DECIMAL_TYPE ); } diff --git a/vortex-array/src/arrays/decimal/vtable/mod.rs b/vortex-array/src/arrays/decimal/vtable/mod.rs index fe4d8ddeea7..0407161abe2 100644 --- a/vortex-array/src/arrays/decimal/vtable/mod.rs +++ b/vortex-array/src/arrays/decimal/vtable/mod.rs @@ -128,7 +128,7 @@ impl VTable for Decimal { slots: &[Option], ) -> VortexResult<()> { let DType::Decimal(_, nullability) = dtype else { - vortex_bail!("Expected decimal dtype, got {dtype:?}"); + vortex_bail!(MismatchedTypes: "Expected decimal dtype, got {dtype:?}"); }; vortex_ensure_eq!( data.len(), @@ -163,7 +163,7 @@ impl VTable for Decimal { let validity = fixed_width::deserialize_validity(dtype.nullability(), len, children)?; let Some(decimal_dtype) = dtype.as_decimal_opt() else { - vortex_bail!("Expected Decimal dtype, got {:?}", dtype) + vortex_bail!(MismatchedTypes: "Expected Decimal dtype, got {:?}", dtype) }; let slots = DecimalData::make_slots(&validity, len); @@ -171,7 +171,7 @@ impl VTable for Decimal { // Check and reinterpret-cast the buffer vortex_ensure!( values.is_aligned_to(Alignment::of::()), - "DecimalArray buffer not aligned for values type {:?}", + InvalidArgument: "DecimalArray buffer not aligned for values type {:?}", D::DECIMAL_TYPE ); DecimalData::try_new_handle(values, metadata.values_type(), *decimal_dtype) @@ -199,7 +199,7 @@ impl VTable for Decimal { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for Decimal requires a DecimalBuilder"); + vortex_bail!(InvalidArgument: "append_to_builder for Decimal requires a DecimalBuilder"); }; builder.append_decimal_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/dict/array.rs b/vortex-array/src/arrays/dict/array.rs index 79f5ac8be33..80aba23d40a 100644 --- a/vortex-array/src/arrays/dict/array.rs +++ b/vortex-array/src/arrays/dict/array.rs @@ -116,7 +116,7 @@ impl DictData { /// It is an error to provide a nullable `codes` with non-nullable `values`. pub(crate) fn try_new(codes_dtype: &DType) -> VortexResult { if !codes_dtype.is_int() { - vortex_bail!(MismatchedTypes: "int", codes_dtype); + vortex_bail!(MismatchedTypes: "expected type: int but instead got {}", codes_dtype); } Ok(unsafe { Self::new_unchecked() }) @@ -138,7 +138,7 @@ pub trait DictArrayExt: TypedArrayRef + DictArraySlotsExt { let referenced_mask = self.compute_referenced_values_mask(true, ctx)?; let all_referenced = referenced_mask.true_count() == referenced_mask.len(); - vortex_ensure!(all_referenced, "value in dict not referenced"); + vortex_ensure!(all_referenced, InvalidArgument: "value in dict not referenced"); } Ok(()) @@ -409,7 +409,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!("Expected indices from mask") + vortex_panic!(AssertionFailed: "Expected indices from mask") }; assert_eq!(indices, [0, 2, 4]); } @@ -432,7 +432,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!("Expected indices from mask") + vortex_panic!(AssertionFailed: "Expected indices from mask") }; assert_eq!(indices, [0]); } @@ -459,7 +459,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!("Expected indices from mask") + vortex_panic!(AssertionFailed: "Expected indices from mask") }; assert_eq!(indices, [2, 4]); } @@ -482,7 +482,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!("Expected indices from mask") + vortex_panic!(AssertionFailed: "Expected indices from mask") }; assert_eq!(indices, [0, 2, 4]); } diff --git a/vortex-array/src/arrays/dict/vtable/mod.rs b/vortex-array/src/arrays/dict/vtable/mod.rs index a2ba1487a59..475d242dd2e 100644 --- a/vortex-array/src/arrays/dict/vtable/mod.rs +++ b/vortex-array/src/arrays/dict/vtable/mod.rs @@ -104,13 +104,13 @@ impl VTable for Dict { let view = DictSlotsView::from_slots(slots); let codes = view.codes; let values = view.values; - vortex_ensure_eq!(codes.len(), len, "DictArray codes length mismatch"); + vortex_ensure_eq!(codes.len(), len, InvalidArgument: "DictArray codes length mismatch"); vortex_ensure_eq!( values .dtype() .union_nullability(codes.dtype().nullability()), *dtype, - "DictArray dtype does not match codes/values dtype", + MismatchedTypes: "DictArray dtype does not match codes/values dtype", ); Ok(()) } @@ -120,7 +120,7 @@ impl VTable for Dict { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("DictArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "DictArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -144,7 +144,7 @@ impl VTable for Dict { codes_ptype: PType::try_from(array.codes().dtype())? as i32, values_len: u32::try_from(array.values().len()).map_err(|_| { vortex_err!( - "Dictionary values size {} overflowed u32", + Overflow: "Dictionary values size {} overflowed u32", array.values().len() ) })?, @@ -167,7 +167,7 @@ impl VTable for Dict { let metadata = DictMetadata::decode(metadata)?; if children.len() != 2 { vortex_bail!( - "Expected 2 children for dict encoding, found {}", + InvalidArgument: "Expected 2 children for dict encoding, found {}", children.len() ) } diff --git a/vortex-array/src/arrays/dict/vtable/operations.rs b/vortex-array/src/arrays/dict/vtable/operations.rs index 139a23ef05e..1e4aa4f429b 100644 --- a/vortex-array/src/arrays/dict/vtable/operations.rs +++ b/vortex-array/src/arrays/dict/vtable/operations.rs @@ -24,7 +24,7 @@ impl OperationsVTable for Dict { let dtype = state.array().dtype().clone(); let code = state .slot(DictSlots::CODES)? - .ok_or_else(|| vortex_err!("Dict codes slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "Dict codes slot is missing"))? .execute_scalar(index, ctx)?; let Some(dict_index) = code.as_primitive().as_::() else { return Ok(Scalar::null(dtype)); @@ -32,7 +32,7 @@ impl OperationsVTable for Dict { Ok(state .slot(DictSlots::VALUES)? - .ok_or_else(|| vortex_err!("Dict values slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "Dict values slot is missing"))? .execute_scalar(dict_index, ctx)? .cast(&dtype) .vortex_expect("Array dtype will only differ by nullability")) diff --git a/vortex-array/src/arrays/extension/array.rs b/vortex-array/src/arrays/extension/array.rs index 841d35dbbea..2412b051d27 100644 --- a/vortex-array/src/arrays/extension/array.rs +++ b/vortex-array/src/arrays/extension/array.rs @@ -53,7 +53,7 @@ impl Array { vortex_ensure_eq!( ext_dtype.storage_dtype(), storage_array.dtype(), - "Tried to create an `ExtensionArray` with an incompatible storage array" + MismatchedTypes: "Tried to create an `ExtensionArray` with an incompatible storage array" ); let dtype = DType::Extension(ext_dtype); diff --git a/vortex-array/src/arrays/extension/vtable/mod.rs b/vortex-array/src/arrays/extension/vtable/mod.rs index 6069d945efe..75598e99ea5 100644 --- a/vortex-array/src/arrays/extension/vtable/mod.rs +++ b/vortex-array/src/arrays/extension/vtable/mod.rs @@ -106,18 +106,18 @@ impl VTable for Extension { vortex_ensure_eq!( storage.len(), len, - "ExtensionArray length does not match outer length", + InvalidArgument: "ExtensionArray length does not match outer length", ); let ext_dtype = dtype .as_extension_opt() - .ok_or_else(|| vortex_err!("not an extension dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "not an extension dtype"))?; let actual_dtype = DType::Extension(ext_dtype.clone()); vortex_ensure_eq!( &actual_dtype, dtype, - "ExtensionArray dtype does not match outer dtype", + MismatchedTypes: "ExtensionArray dtype does not match outer dtype", ); Ok(()) @@ -128,7 +128,7 @@ impl VTable for Extension { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ExtensionArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ExtensionArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -162,15 +162,15 @@ impl VTable for Extension { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "ExtensionArray expects empty metadata, got {} bytes", + InvalidArgument: "ExtensionArray expects empty metadata, got {} bytes", metadata.len() ); } let DType::Extension(ext_dtype) = dtype else { - vortex_bail!("Not an extension DType"); + vortex_bail!(MismatchedTypes: "Not an extension DType"); }; if children.len() != 1 { - vortex_bail!("Expected 1 child, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 1 child, got {}", children.len()); } let storage = children.get(0, ext_dtype.storage_dtype(), len)?; Ok(ArrayParts::new( @@ -196,7 +196,7 @@ impl VTable for Extension { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for Extension requires an ExtensionBuilder"); + vortex_bail!(InvalidArgument: "append_to_builder for Extension requires an ExtensionBuilder"); }; builder.append_extension_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/extension/vtable/operations.rs b/vortex-array/src/arrays/extension/vtable/operations.rs index 14d21988dd7..92e4f75668c 100644 --- a/vortex-array/src/arrays/extension/vtable/operations.rs +++ b/vortex-array/src/arrays/extension/vtable/operations.rs @@ -24,7 +24,7 @@ impl OperationsVTable for Extension { let ext_dtype = state.array().ext_dtype().clone(); let storage = state .slot(ExtensionSlots::STORAGE)? - .ok_or_else(|| vortex_err!("Extension storage slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "Extension storage slot is missing"))? .execute_scalar(index, ctx)?; Ok(Scalar::extension_ref(ext_dtype, storage)) } diff --git a/vortex-array/src/arrays/filter/array.rs b/vortex-array/src/arrays/filter/array.rs index e7c1f4efb1a..5b8edd1da62 100644 --- a/vortex-array/src/arrays/filter/array.rs +++ b/vortex-array/src/arrays/filter/array.rs @@ -51,7 +51,7 @@ impl FilterData { vortex_ensure_eq!( array_len, mask.len(), - "FilterArray array and mask lengths must match", + InvalidArgument: "FilterArray array and mask lengths must match", ); Ok(Self { mask }) diff --git a/vortex-array/src/arrays/filter/execute/take.rs b/vortex-array/src/arrays/filter/execute/take.rs index 0a4b0d70238..edc32c37493 100644 --- a/vortex-array/src/arrays/filter/execute/take.rs +++ b/vortex-array/src/arrays/filter/execute/take.rs @@ -134,7 +134,7 @@ impl TakeExecute for Filter { } let DType::Primitive(ptype, nullability) = indices.dtype() else { - vortex_bail!("Invalid indices dtype: {}", indices.dtype()) + vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) }; if should_materialize_big_take(array, indices) { diff --git a/vortex-array/src/arrays/filter/execute/take/rank.rs b/vortex-array/src/arrays/filter/execute/take/rank.rs index 7bfb9b24773..061f991ca10 100644 --- a/vortex-array/src/arrays/filter/execute/take/rank.rs +++ b/vortex-array/src/arrays/filter/execute/take/rank.rs @@ -60,7 +60,7 @@ fn sequential_take_len_typed( } if ranks.len() > filtered_len { - vortex_bail!(OutOfBounds: ranks.len() - 1, 0, filtered_len); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", ranks.len() - 1, 0, filtered_len); } Ok(Some(ranks.len())) @@ -141,7 +141,7 @@ pub(in crate::arrays::filter) fn validate_rank( ) -> VortexResult { let rank: usize = rank.as_(); if rank >= filtered_len { - vortex_bail!(OutOfBounds: rank, 0, filtered_len); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", rank, 0, filtered_len); } Ok(rank) } diff --git a/vortex-array/src/arrays/filter/vtable.rs b/vortex-array/src/arrays/filter/vtable.rs index b7642784fce..68f94c40562 100644 --- a/vortex-array/src/arrays/filter/vtable.rs +++ b/vortex-array/src/arrays/filter/vtable.rs @@ -82,7 +82,7 @@ impl VTable for Filter { ) -> VortexResult<()> { vortex_ensure!( slots[FilterSlots::CHILD].is_some(), - "FilterArray child slot must be present" + InvalidArgument: "FilterArray child slot must be present" ); let child = slots[FilterSlots::CHILD] .as_ref() @@ -90,17 +90,17 @@ impl VTable for Filter { vortex_ensure_eq!( child.dtype(), dtype, - "FilterArray dtype does not match outer dtype", + MismatchedTypes: "FilterArray dtype does not match outer dtype", ); vortex_ensure_eq!( data.len(), len, - "FilterArray length does not match outer length", + InvalidArgument: "FilterArray length does not match outer length", ); vortex_ensure_eq!( child.len(), data.mask.len(), - "FilterArray child length does not match mask length", + InvalidArgument: "FilterArray child length does not match mask length", ); Ok(()) } @@ -110,7 +110,7 @@ impl VTable for Filter { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!("FilterArray has no buffers") + vortex_panic!(OutOfBounds: "FilterArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -134,7 +134,7 @@ impl VTable for Filter { _session: &VortexSession, ) -> VortexResult>> { // TODO(joe): make this configurable - vortex_bail!("Filter array is not serializable") + vortex_bail!(Serde: "Filter array is not serializable") } fn deserialize( @@ -147,7 +147,7 @@ impl VTable for Filter { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("Filter array is not serializable") + vortex_bail!(Serde: "Filter array is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/arrays/fixed_size_list/compute/take.rs b/vortex-array/src/arrays/fixed_size_list/compute/take.rs index acc05cca73d..36a51a52075 100644 --- a/vortex-array/src/arrays/fixed_size_list/compute/take.rs +++ b/vortex-array/src/arrays/fixed_size_list/compute/take.rs @@ -68,14 +68,14 @@ fn take_empty_fsl( let indices_validity = indices.validity()?.execute_mask(new_len, ctx)?; vortex_ensure!( indices_validity.all_false(), - "cannot take valid indices from an empty FixedSizeList" + InvalidArgument: "cannot take valid indices from an empty FixedSizeList" ); } let list_size = array.list_size() as usize; let elements_len = new_len.checked_mul(list_size).ok_or_else(|| { vortex_err!( - "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" + Overflow: "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" ) })?; let new_elements = default_elements(array, elements_len, ctx.allocator()); @@ -102,10 +102,10 @@ fn take_non_empty_fsl( debug_assert!(!array.is_empty()); let DType::Primitive(ptype, _) = indices.dtype() else { - vortex_bail!("Invalid indices dtype: {}", indices.dtype()) + vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) }; if !ptype.is_int() { - vortex_bail!("Invalid indices dtype: {}", indices.dtype()); + vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()); } if array.list_size() == 0 { @@ -141,7 +141,7 @@ fn take_piecewise_fsl( let new_len = indices.as_ref().len(); let elements_len = new_len.checked_mul(list_size).ok_or_else(|| { vortex_err!( - "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" + Overflow: "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" ) })?; @@ -175,20 +175,20 @@ fn take_piecewise_fsl( } let end = start .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"))?; if end > array_len { - vortex_bail!(OutOfBounds: end - 1, 0, array_len); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", end - 1, 0, array_len); } - total_len = total_len - .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + total_len = total_len.checked_add(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; element_starts.push(u64::try_from(start * list_size)?); element_lengths.push(u64::try_from(length * list_size)?); } vortex_ensure_eq!( total_len, new_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); let new_elements = @@ -233,7 +233,7 @@ fn take_non_empty_degenerate_fsl( debug_assert_eq!(array.list_size(), 0); vortex_ensure!( array.elements().is_empty(), - "degenerate list must have empty elements" + InvalidArgument: "degenerate list must have empty elements" ); let indices_array = indices.clone().execute::(ctx)?; @@ -293,7 +293,7 @@ fn take_non_empty_non_degenerate_elements( let new_len = indices.len(); let elements_len = new_len.checked_mul(list_size).ok_or_else(|| { vortex_err!( - "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" + Overflow: "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" ) })?; @@ -308,7 +308,7 @@ fn take_non_empty_non_degenerate_elements( let data_idx: usize = data_idx.as_(); if data_idx >= array_len { - vortex_bail!(OutOfBounds: data_idx, 0, array_len); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", data_idx, 0, array_len); } Ok((data_idx * list_size) as u64) }) @@ -332,7 +332,7 @@ fn bounds_check_valid_indices( if is_index_valid { let data_idx = data_idx.as_(); if data_idx >= array_len { - vortex_bail!(OutOfBounds: data_idx, 0, array_len); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", data_idx, 0, array_len); } } } diff --git a/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs b/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs index 0e140a47998..63cdbe3ad85 100644 --- a/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs +++ b/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs @@ -76,11 +76,11 @@ impl VTable for FixedSizeList { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("FixedSizeListArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "FixedSizeListArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("FixedSizeListArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "FixedSizeListArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -113,9 +113,9 @@ impl VTable for FixedSizeList { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), FixedSizeListSlots::COUNT); + vortex_ensure_eq!(slots.len(), FixedSizeListSlots::COUNT, InvalidArgument); let DType::FixedSizeList(_, list_size, nullability) = dtype else { - vortex_bail!("Expected `DType::FixedSizeList`, got {dtype:?}"); + vortex_bail!(MismatchedTypes: "Expected `DType::FixedSizeList`, got {dtype:?}"); }; let elements = slots[FixedSizeListSlots::ELEMENTS] .as_ref() @@ -126,7 +126,7 @@ impl VTable for FixedSizeList { } else { elements.len() / *list_size as usize == len }, - "FixedSizeListArray length {} does not match outer length {}", + InvalidArgument: "FixedSizeListArray length {} does not match outer length {}", len, len ); @@ -136,7 +136,7 @@ impl VTable for FixedSizeList { vortex_ensure_eq!( &actual_dtype, dtype, - "FixedSizeListArray dtype does not match outer dtype", + MismatchedTypes: "FixedSizeListArray dtype does not match outer dtype", ); Ok(()) @@ -154,22 +154,22 @@ impl VTable for FixedSizeList { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "FixedSizeListArray expects empty metadata, got {} bytes", + InvalidArgument: "FixedSizeListArray expects empty metadata, got {} bytes", metadata.len() ); } vortex_ensure!( buffers.is_empty(), - "`FixedSizeList::build` expects no buffers" + InvalidArgument: "`FixedSizeList::build` expects no buffers" ); let DType::FixedSizeList(element_dtype, list_size, _) = &dtype else { - vortex_bail!("Expected `DType::FixedSizeList`, got {:?}", dtype); + vortex_bail!(MismatchedTypes: "Expected `DType::FixedSizeList`, got {:?}", dtype); }; let validity = { if children.len() > 2 { - vortex_bail!("`FixedSizeList::build` method expected 1 or 2 children") + vortex_bail!(InvalidArgument: "`FixedSizeList::build` method expected 1 or 2 children") } if children.len() == 2 { @@ -210,7 +210,7 @@ impl VTable for FixedSizeList { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for FixedSizeList requires a FixedSizeListBuilder"); + vortex_bail!(InvalidArgument: "append_to_builder for FixedSizeList requires a FixedSizeListBuilder"); }; builder.append_fixed_size_list_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/fixed_width/array.rs b/vortex-array/src/arrays/fixed_width/array.rs index e6eac415664..82a8535e6b2 100644 --- a/vortex-array/src/arrays/fixed_width/array.rs +++ b/vortex-array/src/arrays/fixed_width/array.rs @@ -51,11 +51,11 @@ pub(crate) fn with_values( ) -> VortexResult> { let expected_len = len .checked_mul(V::byte_width(array)) - .ok_or_else(|| vortex_err!("Fixed-width values buffer length overflows usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "Fixed-width values buffer length overflows usize"))?; vortex_ensure_eq!( values.len(), expected_len, - "Fixed-width values buffer length does not match expected length", + InvalidArgument: "Fixed-width values buffer length does not match expected length", ); V::with_values(array, values, len, validity) } diff --git a/vortex-array/src/arrays/fixed_width/take/mod.rs b/vortex-array/src/arrays/fixed_width/take/mod.rs index 2cf9f1f950b..169ebcc6ac8 100644 --- a/vortex-array/src/arrays/fixed_width/take/mod.rs +++ b/vortex-array/src/arrays/fixed_width/take/mod.rs @@ -120,10 +120,10 @@ pub(crate) fn take( } let DType::Primitive(ptype, nullability) = indices.dtype() else { - vortex_bail!("Invalid indices dtype: {}", indices.dtype()) + vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) }; if !ptype.is_int() { - vortex_bail!("Invalid indices dtype: {}", indices.dtype()) + vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) } let indices_validity = indices.validity()?; diff --git a/vortex-array/src/arrays/fixed_width/take/records.rs b/vortex-array/src/arrays/fixed_width/take/records.rs index 692707db9da..6706af2d256 100644 --- a/vortex-array/src/arrays/fixed_width/take/records.rs +++ b/vortex-array/src/arrays/fixed_width/take/records.rs @@ -34,7 +34,7 @@ pub(super) fn take_byte_records( let output_len = indices .len() .checked_mul(byte_width) - .ok_or_else(|| vortex_err!("Fixed-width take output length overflows usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "Fixed-width take output length overflows usize"))?; let mut result = BufferMut::::with_capacity_in(output_len, allocator.clone()); for index in indices { let index = index.as_(); diff --git a/vortex-array/src/arrays/fixed_width/take/slices.rs b/vortex-array/src/arrays/fixed_width/take/slices.rs index 480e0096360..989d88135e4 100644 --- a/vortex-array/src/arrays/fixed_width/take/slices.rs +++ b/vortex-array/src/arrays/fixed_width/take/slices.rs @@ -44,14 +44,13 @@ pub(super) fn take_slices_constant_length( output_len: usize, allocator: &BufferAllocatorRef, ) -> VortexResult { - let computed_len = starts - .len() - .checked_mul(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + let computed_len = starts.len().checked_mul(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; vortex_ensure_eq!( computed_len, output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); copy_slices( values, @@ -73,16 +72,16 @@ fn copy_slices( ) -> VortexResult { let input_byte_len = record_count .checked_mul(byte_width) - .ok_or_else(|| vortex_err!("Fixed-width values buffer length overflows usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "Fixed-width values buffer length overflows usize"))?; vortex_ensure_eq!( values.len(), input_byte_len, - "Fixed-width values buffer length does not match record count", + InvalidArgument: "Fixed-width values buffer length does not match record count", ); - let output_byte_len = output_len - .checked_mul(byte_width) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + let output_byte_len = output_len.checked_mul(byte_width).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; let mut result = BufferMut::::with_capacity_aligned_in( output_byte_len, values.alignment(), @@ -92,12 +91,12 @@ fn copy_slices( let mut cursor = 0usize; for (start, length) in slices { - let end = start - .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray slice end overflows usize"))?; + let end = start.checked_add(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray slice end overflows usize"), + )?; vortex_ensure!( end <= record_count, - "PiecewiseSequenceArray slice {start}..{end} exceeds array length {record_count}" + OutOfBounds: "PiecewiseSequenceArray slice {start}..{end} exceeds array length {record_count}" ); // These multiplications cannot overflow because `end <= record_count` and the complete // values buffer length was checked above. @@ -113,7 +112,7 @@ fn copy_slices( vortex_ensure_eq!( result.len(), output_byte_len, - "PiecewiseSequenceArray expanded byte length does not match declared byte length", + AssertionFailed: "PiecewiseSequenceArray expanded byte length does not match declared byte length", ); Ok(result.freeze().into_byte_buffer()) } diff --git a/vortex-array/src/arrays/fixed_width/vtable.rs b/vortex-array/src/arrays/fixed_width/vtable.rs index b0994013a66..21e209e75e6 100644 --- a/vortex-array/src/arrays/fixed_width/vtable.rs +++ b/vortex-array/src/arrays/fixed_width/vtable.rs @@ -14,7 +14,7 @@ use crate::validity::Validity; pub(crate) fn buffer(array_name: &str, values: &BufferHandle, idx: usize) -> BufferHandle { match idx { 0 => values.clone(), - _ => vortex_panic!("{array_name} buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "{array_name} buffer index {idx} out of bounds"), } } @@ -26,7 +26,7 @@ pub(crate) fn buffer_name(idx: usize) -> Option { } pub(crate) fn single_buffer(buffers: &[BufferHandle]) -> VortexResult { - vortex_ensure_eq!(buffers.len(), 1); + vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); Ok(buffers[0].clone()) } @@ -38,6 +38,6 @@ pub(crate) fn deserialize_validity( match children.len() { 0 => Ok(Validity::from(nullability)), 1 => Ok(Validity::Array(children.get(0, &Validity::DTYPE, len)?)), - child_count => vortex_bail!("Expected 0 or 1 child, got {child_count}"), + child_count => vortex_bail!(MismatchedTypes: "Expected 0 or 1 child, got {child_count}"), } } diff --git a/vortex-array/src/arrays/interleave/execute/bool.rs b/vortex-array/src/arrays/interleave/execute/bool.rs index e6f1aa5cbe3..cbb32a8b649 100644 --- a/vortex-array/src/arrays/interleave/execute/bool.rs +++ b/vortex-array/src/arrays/interleave/execute/bool.rs @@ -99,18 +99,18 @@ fn validate_selectors, R: AsPrimitive>( vortex_ensure_eq!( rows.len(), len, - "interleave row_indices length does not match array_indices length", + InvalidArgument: "interleave row_indices length does not match array_indices length", ); for i in 0..len { let branch = branches[i].as_(); vortex_ensure!( branch < value_bits.len(), - "interleave array index out of bounds" + OutOfBounds: "interleave array index out of bounds" ); vortex_ensure!( rows[i].as_() < value_bits[branch].len(), - "interleave row index out of bounds" + OutOfBounds: "interleave row index out of bounds" ); } diff --git a/vortex-array/src/arrays/interleave/execute/mod.rs b/vortex-array/src/arrays/interleave/execute/mod.rs index 558db9e3309..d951cf4422d 100644 --- a/vortex-array/src/arrays/interleave/execute/mod.rs +++ b/vortex-array/src/arrays/interleave/execute/mod.rs @@ -31,7 +31,7 @@ pub(super) fn execute( primitive::execute(array, ctx) } else { vortex_panic!( - "interleave execution is not implemented for value dtype {}", + NotImplemented: "interleave execution is not implemented for value dtype {}", array.dtype() ) } diff --git a/vortex-array/src/arrays/interleave/execute/primitive.rs b/vortex-array/src/arrays/interleave/execute/primitive.rs index c405df102df..bbc8db56170 100644 --- a/vortex-array/src/arrays/interleave/execute/primitive.rs +++ b/vortex-array/src/arrays/interleave/execute/primitive.rs @@ -116,16 +116,16 @@ where vortex_ensure_eq!( rows.len(), branches.len(), - "interleave row_indices length does not match array_indices length", + InvalidArgument: "interleave row_indices length does not match array_indices length", ); let mut output = BufferMut::with_capacity_in(branches.len(), allocator.clone()); output.try_extend_trusted(branches.iter().zip(rows).map(|(branch, row)| { let Some(source) = values.get((*branch).as_()) else { - vortex_bail!("interleave array index out of bounds"); + vortex_bail!(OutOfBounds: "interleave array index out of bounds"); }; let row = (*row).as_(); - vortex_ensure!(row < source.len, "interleave row index out of bounds"); + vortex_ensure!(row < source.len, OutOfBounds: "interleave row index out of bounds"); Ok(source.data[row & source.row_mask]) }))?; Ok(output.freeze()) diff --git a/vortex-array/src/arrays/interleave/mod.rs b/vortex-array/src/arrays/interleave/mod.rs index d5cb8085dbc..28635ea1b1e 100644 --- a/vortex-array/src/arrays/interleave/mod.rs +++ b/vortex-array/src/arrays/interleave/mod.rs @@ -93,7 +93,7 @@ impl Interleave { ) -> VortexResult { vortex_ensure!( values.len() >= 2, - "interleave requires at least 2 values, got {}", + InvalidArgument: "interleave requires at least 2 values, got {}", values.len() ); @@ -107,12 +107,12 @@ impl Interleave { DType::Primitive(ptype, nullability) if ptype.is_unsigned_int() => { vortex_ensure!( !nullability.is_nullable(), - "interleave {name} must be non-nullable, got {}", + InvalidArgument: "interleave {name} must be non-nullable, got {}", selector.dtype() ); } other => vortex_bail!( - "interleave {name} must be a non-nullable unsigned integer, got {other}" + InvalidArgument: "interleave {name} must be a non-nullable unsigned integer, got {other}" ), } } @@ -120,7 +120,7 @@ impl Interleave { vortex_ensure_eq!( array_indices.len(), row_indices.len(), - "interleave selectors must have equal length", + InvalidArgument: "interleave selectors must have equal length", ); let base_dtype = values[0].dtype(); @@ -128,7 +128,7 @@ impl Interleave { for value in values { vortex_ensure!( value.dtype().eq_ignore_nullability(base_dtype), - "interleave values must share a dtype up to nullability: {} vs {}", + MismatchedTypes: "interleave values must share a dtype up to nullability: {} vs {}", base_dtype, value.dtype() ); @@ -159,11 +159,11 @@ impl VTable for Interleave { vortex_ensure_eq!( slots.len(), data.num_values + InterleaveSlots::FIXED_COUNT, - "InterleaveArray expects values + array_indices + row_indices slots", + InvalidArgument: "InterleaveArray expects values + array_indices + row_indices slots", ); vortex_ensure!( slots.iter().all(|s| s.is_some()), - "InterleaveArray slots must all be present" + InvalidArgument: "InterleaveArray slots must all be present" ); let array_indices = slots[InterleaveSlots::ARRAY_INDICES] @@ -183,12 +183,12 @@ impl VTable for Interleave { vortex_ensure_eq!( dtype, &expected_dtype, - "InterleaveArray dtype does not match the dtype implied by its children", + MismatchedTypes: "InterleaveArray dtype does not match the dtype implied by its children", ); vortex_ensure_eq!( len, array_indices.len(), - "InterleaveArray length does not match array_indices length", + InvalidArgument: "InterleaveArray length does not match array_indices length", ); Ok(()) } @@ -198,7 +198,7 @@ impl VTable for Interleave { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!("InterleaveArray has no buffers") + vortex_panic!(OutOfBounds: "InterleaveArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -221,7 +221,7 @@ impl VTable for Interleave { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!("Interleave array is not serializable") + vortex_bail!(Serde: "Interleave array is not serializable") } fn deserialize( @@ -233,7 +233,7 @@ impl VTable for Interleave { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("Interleave array is not serializable") + vortex_bail!(Serde: "Interleave array is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/arrays/list/array.rs b/vortex-array/src/arrays/list/array.rs index 377499faea6..f516150bcce 100644 --- a/vortex-array/src/arrays/list/array.rs +++ b/vortex-array/src/arrays/list/array.rs @@ -249,7 +249,7 @@ impl ListData { vortex_ensure!( max <= P::try_from(elements.len()).unwrap_or_else(|_| vortex_panic!( - "Offsets type {} must be able to fit elements length {}", + Overflow: "Offsets type {} must be able to fit elements length {}",

::PTYPE, elements.len() )), @@ -301,7 +301,7 @@ pub trait ListArrayExt: ListArraySlotsExt { fn offset_at(&self, index: usize, ctx: &mut ExecutionCtx) -> VortexResult { vortex_ensure!( index <= self.len(), - "Index {index} out of bounds 0..={}", + OutOfBounds: "Index {index} out of bounds 0..={}", self.len() ); @@ -314,7 +314,9 @@ pub trait ListArrayExt: ListArraySlotsExt { .execute_scalar(index, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_error::vortex_err!("offset value does not fit in usize")) + .ok_or_else( + || vortex_error::vortex_err!(Overflow: "offset value does not fit in usize"), + ) } } diff --git a/vortex-array/src/arrays/list/compute/filter.rs b/vortex-array/src/arrays/list/compute/filter.rs index 95f9fd57993..087c343140c 100644 --- a/vortex-array/src/arrays/list/compute/filter.rs +++ b/vortex-array/src/arrays/list/compute/filter.rs @@ -219,7 +219,7 @@ mod tests { #[test] fn element_mask_excludes_unselected_prefix_and_suffix() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [2]) else { - vortex_bail!("a partially selective mask uses Mask::Values") + vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20010, 40010, 60010, 80010, 100010]; @@ -236,7 +236,7 @@ mod tests { #[test] fn element_mask_retains_gaps_between_selected_lists() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [1, 3]) else { - vortex_bail!("a partially selective mask uses Mask::Values") + vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20010, 40010, 60010, 80010, 100010]; @@ -257,7 +257,7 @@ mod tests { #[test] fn element_range_preserves_complete_range_for_short_lists() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [2]) else { - vortex_bail!("a partially selective mask uses Mask::Values") + vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20, 30, 40, 50, 60]; @@ -275,7 +275,7 @@ mod tests { #[test] fn element_range_requires_minimum_savings() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(2, [0]) else { - vortex_bail!("a partially selective mask uses Mask::Values") + vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") }; let offsets = [0u32, 512, 1024]; @@ -289,7 +289,7 @@ mod tests { #[test] fn element_range_requires_sufficient_savings_ratio() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_slices(100, vec![(0, 96)]) else { - vortex_bail!("a partially selective mask uses Mask::Values") + vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") }; let offsets = (0..=100).map(|index| index * 1000).collect::>(); @@ -303,7 +303,7 @@ mod tests { #[test] fn element_range_crops_at_sufficient_savings_ratio() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_slices(100, vec![(0, 95)]) else { - vortex_bail!("a partially selective mask uses Mask::Values") + vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") }; let offsets = (0..=100).map(|index| index * 1000).collect::>(); @@ -317,7 +317,7 @@ mod tests { #[test] fn element_mask_preserves_complete_range_for_edge_spanning_selection() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [0, 4]) else { - vortex_bail!("a partially selective mask uses Mask::Values") + vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20010, 40010, 60010, 80010, 100010]; diff --git a/vortex-array/src/arrays/list/compute/take.rs b/vortex-array/src/arrays/list/compute/take.rs index 591e1cf638d..aff159c153e 100644 --- a/vortex-array/src/arrays/list/compute/take.rs +++ b/vortex-array/src/arrays/list/compute/take.rs @@ -93,7 +93,7 @@ fn take_with_piecewise_elements::with_capacity(offsets_capacity); let mut element_starts = BufferMut::::with_capacity(indices.len()); let mut element_lengths = BufferMut::::with_capacity(indices.len()); @@ -119,7 +119,7 @@ fn take_with_piecewise_elements(current_offset)); element_starts.push(start as u64); element_lengths.push(length as u64); @@ -324,14 +324,13 @@ where S: UnsignedPType, Offset: UnsignedPType, { - let computed_len = starts - .len() - .checked_mul(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + let computed_len = starts.len().checked_mul(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; vortex_ensure_eq!( computed_len, output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); let all_valid = data_validity.all_true(); let total_elements = if all_valid { @@ -390,14 +389,14 @@ where let mut computed_len = 0usize; for &length in lengths { let length: usize = length.as_(); - computed_len = computed_len - .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + computed_len = computed_len.checked_add(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; } vortex_ensure_eq!( computed_len, output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); let all_valid = data_validity.all_true(); let total_elements = if all_valid { @@ -472,7 +471,7 @@ where let element_end: usize = offset_range[length].as_(); total = total .checked_add(element_end - element_start) - .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; } Ok(total) } @@ -497,7 +496,7 @@ where let additional = valid_piece_elements_len(offsets, data_validity, start, length)?; total = total .checked_add(additional) - .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; } Ok(total) } @@ -521,7 +520,7 @@ where let element_end: usize = offset_range[length].as_(); total = total .checked_add(element_end - element_start) - .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; } Ok(total) } @@ -544,7 +543,7 @@ where let additional = valid_piece_elements_len(offsets, data_validity, start, length)?; total = total .checked_add(additional) - .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; } Ok(total) } @@ -568,7 +567,7 @@ where let element_end: usize = window[1].as_(); total = total .checked_add(element_end - element_start) - .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; } Ok(total) } @@ -588,7 +587,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; let mut new_offsets = BufferMut::::with_capacity(offsets_capacity); let mut element_starts = BufferMut::::with_capacity(starts.len()); let mut element_lengths = BufferMut::::with_capacity(starts.len()); @@ -651,7 +650,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; let mut gather = ValidPieceGather { new_offsets: BufferMut::::with_capacity(offsets_capacity), element_starts: BufferMut::::with_capacity(output_len), @@ -704,7 +703,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; let mut new_offsets = BufferMut::::with_capacity(offsets_capacity); let mut element_starts = BufferMut::::with_capacity(starts.len()); let mut element_lengths = BufferMut::::with_capacity(lengths.len()); @@ -769,7 +768,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; let mut gather = ValidPieceGather { new_offsets: BufferMut::::with_capacity(offsets_capacity), element_starts: BufferMut::::with_capacity(output_len), diff --git a/vortex-array/src/arrays/list/vtable/mod.rs b/vortex-array/src/arrays/list/vtable/mod.rs index d04dd4bca07..fbe91491dae 100644 --- a/vortex-array/src/arrays/list/vtable/mod.rs +++ b/vortex-array/src/arrays/list/vtable/mod.rs @@ -78,11 +78,11 @@ impl VTable for List { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ListArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ListArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("ListArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ListArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -121,7 +121,7 @@ impl VTable for List { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), ListSlots::COUNT); + vortex_ensure_eq!(slots.len(), ListSlots::COUNT, InvalidArgument); let elements = slots[ListSlots::ELEMENTS] .as_ref() .vortex_expect("ListArray elements slot"); @@ -131,14 +131,14 @@ impl VTable for List { vortex_ensure_eq!( offsets.len().saturating_sub(1), len, - "ListArray length does not match outer length", + InvalidArgument: "ListArray length does not match outer length", ); let actual_dtype = DType::List(Arc::new(elements.dtype().clone()), dtype.nullability()); vortex_ensure_eq!( &actual_dtype, dtype, - "ListArray dtype does not match outer dtype", + MismatchedTypes: "ListArray dtype does not match outer dtype", ); Ok(()) @@ -161,11 +161,11 @@ impl VTable for List { let validity = children.get(2, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("Expected 2 or 3 children, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 2 or 3 children, got {}", children.len()); }; let DType::List(element_dtype, _) = &dtype else { - vortex_bail!("Expected List dtype, got {:?}", dtype); + vortex_bail!(MismatchedTypes: "Expected List dtype, got {:?}", dtype); }; let elements = children.get( 0, @@ -215,7 +215,7 @@ impl VTable for List { match match_each_list_builder!(&mut *builder, |b| b.append_list_array(array, ctx)) { Some(result) => result, None => vortex_bail!( - "cannot append a List array of dtype {} to a {} builder", + MismatchedTypes: "cannot append a List array of dtype {} to a {} builder", array.dtype(), builder.dtype() ), diff --git a/vortex-array/src/arrays/listview/array.rs b/vortex-array/src/arrays/listview/array.rs index bebd5df30fe..a5db3984e5c 100644 --- a/vortex-array/src/arrays/listview/array.rs +++ b/vortex-array/src/arrays/listview/array.rs @@ -237,12 +237,12 @@ impl ListViewData { // Check that offsets and sizes are integer arrays and non-nullable. vortex_ensure!( offsets.dtype().is_int() && !offsets.dtype().is_nullable(), - "offsets must be non-nullable integer array, got {}", + MismatchedTypes: "offsets must be non-nullable integer array, got {}", offsets.dtype() ); vortex_ensure!( sizes.dtype().is_int() && !sizes.dtype().is_nullable(), - "sizes must be non-nullable integer array, got {}", + MismatchedTypes: "sizes must be non-nullable integer array, got {}", sizes.dtype() ); @@ -250,7 +250,7 @@ impl ListViewData { vortex_ensure_eq!( offsets.len(), sizes.len(), - "offsets and sizes must have the same length", + InvalidArgument: "offsets and sizes must have the same length", ); // If a validity array is present, it must be the same length as the `ListViewArray`. @@ -258,7 +258,7 @@ impl ListViewData { vortex_ensure_eq!( validity_len, offsets.len(), - "validity length does not match array size", + InvalidArgument: "validity length does not match array size", ); } @@ -521,7 +521,7 @@ pub trait ListViewArrayExt: ListViewArraySlotsExt { let n_lists = self.len(); vortex_ensure!( n_lists > 0, - "referenced_element_bounds requires a non-empty array" + InvalidArgument: "referenced_element_bounds requires a non-empty array" ); if self.is_zero_copy_to_list() { @@ -682,33 +682,33 @@ where let offset = offsets_slice[i]; let size = sizes_slice[i]; - vortex_ensure!(offset >= O::zero(), "cannot have negative offsets"); - vortex_ensure!(size >= S::zero(), "cannot have negative size"); + vortex_ensure!(offset >= O::zero(), InvalidArgument: "cannot have negative offsets"); + vortex_ensure!(size >= S::zero(), InvalidArgument: "cannot have negative size"); - let offset_u64 = offset - .to_u64() - .ok_or_else(|| vortex_err!("offset[{i}] = {offset:?} cannot be converted to u64"))?; + let offset_u64 = offset.to_u64().ok_or_else( + || vortex_err!(Overflow: "offset[{i}] = {offset:?} cannot be converted to u64"), + )?; - let size_u64 = size - .to_u64() - .ok_or_else(|| vortex_err!("size[{i}] = {size:?} cannot be converted to u64"))?; + let size_u64 = size.to_u64().ok_or_else( + || vortex_err!(Overflow: "size[{i}] = {size:?} cannot be converted to u64"), + )?; // Check for overflow when adding offset + size. let end = offset_u64.checked_add(size_u64).ok_or_else(|| { - vortex_err!("offset[{i}] ({offset_u64}) + size[{i}] ({size_u64}) would overflow u64") + vortex_err!(Overflow: "offset[{i}] ({offset_u64}) + size[{i}] ({size_u64}) would overflow u64") })?; if offset_u64 == elements_len { vortex_ensure_eq!( size_u64, 0, - "views to the end of the elements array (length {elements_len}) must have size 0", + InvalidArgument: "views to the end of the elements array (length {elements_len}) must have size 0", ); } vortex_ensure!( end <= elements_len, - "offset[{i}] + size[{i}] = {offset_u64} + {size_u64} = {end} \ + OutOfBounds: "offset[{i}] + size[{i}] = {offset_u64} + {size_u64} = {end} \ exceeds elements length {elements_len}", ); } @@ -728,7 +728,7 @@ fn validate_zctl( let offsets_sorted = match_each_integer_ptype!(offsets_primitive.ptype(), |P| { offsets_primitive.as_slice::

().is_sorted() }); - vortex_ensure!(offsets_sorted, "offsets must be sorted"); + vortex_ensure!(offsets_sorted, InvalidArgument: "offsets must be sorted"); // Validate that offset[i] + size[i] <= offset[i+1] for all items // This ensures views are non-overlapping and properly ordered for zero-copy-to-list @@ -746,7 +746,7 @@ fn validate_zctl( // Check that this view starts at or after the previous view ended vortex_ensure!( offset >= max_end, - "Zero-copy-to-list requires views to be non-overlapping and ordered: \ + InvalidArgument: "Zero-copy-to-list requires views to be non-overlapping and ordered: \ view[{}] starts at {} but previous views extend to {}", i, offset, @@ -824,7 +824,7 @@ fn validate_zctl( element_references[first_ref..=last_ref] .iter() .all(|&references| references != 0), - "found gap in elements array between first and last referenced elements" + InvalidArgument: "found gap in elements array between first and last referenced elements" ); } diff --git a/vortex-array/src/arrays/listview/rebuild.rs b/vortex-array/src/arrays/listview/rebuild.rs index 0fe73d4f0ad..3946724c4fb 100644 --- a/vortex-array/src/arrays/listview/rebuild.rs +++ b/vortex-array/src/arrays/listview/rebuild.rs @@ -116,7 +116,7 @@ impl ListViewArray { ListViewRebuildMode::TrimElements => self.rebuild_trim_elements(ctx), ListViewRebuildMode::MakeExact => self.rebuild_make_exact(ctx), ListViewRebuildMode::OverlapCompression => { - vortex_bail!("ListViewRebuildMode::OverlapCompression is not implemented") + vortex_bail!(NotImplemented: "ListViewRebuildMode::OverlapCompression is not implemented") } } } @@ -429,12 +429,12 @@ where let length: usize = size.as_(); start.checked_add(length).ok_or_else(|| { vortex_err!( - "ListView rebuild element range overflow for start {start} and length {length}" + Overflow: "ListView rebuild element range overflow for start {start} and length {length}" ) })?; elements_len = elements_len .checked_add(length) - .ok_or_else(|| vortex_err!("ListView rebuild elements length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "ListView rebuild elements length overflow"))?; new_offsets.push(n_elements); new_sizes.push(size); diff --git a/vortex-array/src/arrays/listview/vtable/mod.rs b/vortex-array/src/arrays/listview/vtable/mod.rs index 9337309c796..21cc7431d6f 100644 --- a/vortex-array/src/arrays/listview/vtable/mod.rs +++ b/vortex-array/src/arrays/listview/vtable/mod.rs @@ -90,11 +90,11 @@ impl VTable for ListView { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ListViewArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ListViewArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("ListViewArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ListViewArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -126,7 +126,7 @@ impl VTable for ListView { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), ListViewSlots::COUNT); + vortex_ensure_eq!(slots.len(), ListViewSlots::COUNT, InvalidArgument); let elements = slots[ListViewSlots::ELEMENTS] .as_ref() .vortex_expect("ListViewArray elements slot"); @@ -138,7 +138,7 @@ impl VTable for ListView { .vortex_expect("ListViewArray sizes slot"); vortex_ensure!( offsets.len() == len && sizes.len() == len, - "ListViewArray length {} does not match outer length {}", + InvalidArgument: "ListViewArray length {} does not match outer length {}", offsets.len(), len ); @@ -147,7 +147,7 @@ impl VTable for ListView { vortex_ensure_eq!( &actual_dtype, dtype, - "ListViewArray dtype does not match outer dtype", + MismatchedTypes: "ListViewArray dtype does not match outer dtype", ); Ok(()) @@ -166,11 +166,11 @@ impl VTable for ListView { let metadata = ListViewMetadata::decode(metadata)?; vortex_ensure!( buffers.is_empty(), - "`ListViewArray::build` expects no buffers" + InvalidArgument: "`ListViewArray::build` expects no buffers" ); let DType::List(element_dtype, _) = dtype else { - vortex_bail!("Expected List dtype, got {:?}", dtype); + vortex_bail!(MismatchedTypes: "Expected List dtype, got {:?}", dtype); }; let validity = if children.len() == 3 { @@ -180,7 +180,7 @@ impl VTable for ListView { Validity::Array(validity) } else { vortex_bail!( - "`ListViewArray::build` expects 3 or 4 children, got {}", + InvalidArgument: "`ListViewArray::build` expects 3 or 4 children, got {}", children.len() ); }; @@ -242,7 +242,7 @@ impl VTable for ListView { match match_each_list_builder!(&mut *builder, |b| b.append_listview_array(array, ctx)) { Some(result) => result, None => vortex_bail!( - "cannot append a ListView array of dtype {} to a {} builder", + MismatchedTypes: "cannot append a ListView array of dtype {} to a {} builder", array.dtype(), builder.dtype() ), diff --git a/vortex-array/src/arrays/map/array.rs b/vortex-array/src/arrays/map/array.rs index c60b6521198..730958d4af3 100644 --- a/vortex-array/src/arrays/map/array.rs +++ b/vortex-array/src/arrays/map/array.rs @@ -173,20 +173,20 @@ pub(super) fn validate_entries( ) -> VortexResult<()> { vortex_ensure!( entries.is::(), - "MapArray entries must use vortex.listview encoding, got {}", + MismatchedTypes: "MapArray entries must use vortex.listview encoding, got {}", entries.encoding_id() ); vortex_ensure_eq!( entries.len(), len, - "MapArray entries length does not match outer length", + InvalidArgument: "MapArray entries length does not match outer length", ); let expected_dtype = expected_entries_dtype(map_dtype, nullability); vortex_ensure_eq!( entries.dtype(), &expected_dtype, - "MapArray entries dtype does not match expected dtype", + MismatchedTypes: "MapArray entries dtype does not match expected dtype", ); Ok(()) diff --git a/vortex-array/src/arrays/map/compute/cast.rs b/vortex-array/src/arrays/map/compute/cast.rs index bfbab6e17e9..c14bb02cc6b 100644 --- a/vortex-array/src/arrays/map/compute/cast.rs +++ b/vortex-array/src/arrays/map/compute/cast.rs @@ -29,7 +29,7 @@ fn prepare_map_cast_target( if target_map_dtype.keys_sorted() && !array.keys_sorted() { vortex_bail!( - "Cannot cast {} to {dtype}: source does not assert sorted map keys", + MismatchedTypes: "Cannot cast {} to {dtype}: source does not assert sorted map keys", array.dtype() ); } diff --git a/vortex-array/src/arrays/map/compute/mod.rs b/vortex-array/src/arrays/map/compute/mod.rs index ea0be66f0e4..be2a49eac24 100644 --- a/vortex-array/src/arrays/map/compute/mod.rs +++ b/vortex-array/src/arrays/map/compute/mod.rs @@ -22,7 +22,7 @@ use crate::dtype::MapDType; fn rebuild_map_from_array(map_dtype: MapDType, entries: ArrayRef) -> VortexResult { let map_entries = entries.try_downcast::().map_err(|arr| { vortex_err!( - "Map entries operation expected vortex.listview/ListView, got {}", + MismatchedTypes: "Map entries operation expected vortex.listview/ListView, got {}", arr.encoding_id() ) })?; diff --git a/vortex-array/src/arrays/map/vtable/mod.rs b/vortex-array/src/arrays/map/vtable/mod.rs index 17980991d3a..7a76a7dbb68 100644 --- a/vortex-array/src/arrays/map/vtable/mod.rs +++ b/vortex-array/src/arrays/map/vtable/mod.rs @@ -67,10 +67,10 @@ impl VTable for Map { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), MapSlots::COUNT); + vortex_ensure_eq!(slots.len(), MapSlots::COUNT, InvalidArgument); let DType::Map(map_dtype, nullability) = dtype else { - vortex_bail!("Expected map dtype, got {dtype}"); + vortex_bail!(MismatchedTypes: "Expected map dtype, got {dtype}"); }; let slots = MapSlotsView::from_slots(slots); validate_entries(map_dtype, *nullability, len, slots.entries) @@ -81,7 +81,7 @@ impl VTable for Map { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("MapArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "MapArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -114,23 +114,23 @@ impl VTable for Map { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "MapArray expects empty metadata, got {} bytes", + InvalidArgument: "MapArray expects empty metadata, got {} bytes", metadata.len() ); } - vortex_ensure!(buffers.is_empty(), "MapArray expects no buffers"); + vortex_ensure!(buffers.is_empty(), InvalidArgument: "MapArray expects no buffers"); let DType::Map(map_dtype, nullability) = dtype else { - vortex_bail!("Expected map dtype, got {dtype}"); + vortex_bail!(MismatchedTypes: "Expected map dtype, got {dtype}"); }; - vortex_ensure_eq!(children.len(), MapSlots::COUNT); + vortex_ensure_eq!(children.len(), MapSlots::COUNT, InvalidArgument); let expected_entries_dtype = DType::List(std::sync::Arc::new(map_dtype.entries_dtype()), *nullability); let entries = children.get(MapSlots::ENTRIES, &expected_entries_dtype, len)?; vortex_ensure!( entries.is::(), - "MapArray entries must use vortex.listview encoding, got {}", + MismatchedTypes: "MapArray entries must use vortex.listview encoding, got {}", entries.encoding_id() ); @@ -160,7 +160,7 @@ impl VTable for Map { match match_each_map_builder!(&mut *builder, |b| b.append_map_array(array, ctx)) { Some(result) => result, None => vortex_bail!( - "cannot append a Map array of dtype {} to a {} builder", + MismatchedTypes: "cannot append a Map array of dtype {} to a {} builder", array.dtype(), builder.dtype() ), diff --git a/vortex-array/src/arrays/masked/array.rs b/vortex-array/src/arrays/masked/array.rs index f1243c8f1a9..3987327d589 100644 --- a/vortex-array/src/arrays/masked/array.rs +++ b/vortex-array/src/arrays/masked/array.rs @@ -55,17 +55,17 @@ impl MaskedData { validity: Validity, ) -> VortexResult { if matches!(validity, Validity::NonNullable) { - vortex_bail!("MaskedArray must have nullable validity, got {validity:?}") + vortex_bail!(InvalidArgument: "MaskedArray must have nullable validity, got {validity:?}") } if !child_all_valid { - vortex_bail!("MaskedArray children must not have nulls"); + vortex_bail!(InvalidArgument: "MaskedArray children must not have nulls"); } if let Some(validity_len) = validity.maybe_len() && validity_len != child_len { - vortex_bail!("Validity must be the same length as a MaskedArray's child"); + vortex_bail!(InvalidArgument: "Validity must be the same length as a MaskedArray's child"); } // MaskedArray's nullability is determined solely by its validity, not the child's dtype. diff --git a/vortex-array/src/arrays/masked/vtable/mod.rs b/vortex-array/src/arrays/masked/vtable/mod.rs index 507223a94a0..d22057f7429 100644 --- a/vortex-array/src/arrays/masked/vtable/mod.rs +++ b/vortex-array/src/arrays/masked/vtable/mod.rs @@ -81,16 +81,16 @@ impl VTable for Masked { ) -> VortexResult<()> { vortex_ensure!( slots[MaskedSlots::CHILD].is_some(), - "MaskedArray child slot must be present" + InvalidArgument: "MaskedArray child slot must be present" ); let child = slots[MaskedSlots::CHILD] .as_ref() .vortex_expect("validated child slot"); - vortex_ensure_eq!(child.len(), len, "MaskedArray child length mismatch"); + vortex_ensure_eq!(child.len(), len, InvalidArgument: "MaskedArray child length mismatch"); vortex_ensure_eq!( child.dtype().as_nullable(), *dtype, - "MaskedArray dtype does not match child and validity", + MismatchedTypes: "MaskedArray dtype does not match child and validity", ); Ok(()) } @@ -100,7 +100,7 @@ impl VTable for Masked { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!("MaskedArray has no buffers") + vortex_panic!(OutOfBounds: "MaskedArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -134,17 +134,17 @@ impl VTable for Masked { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "MaskedArray expects empty metadata, got {} bytes", + InvalidArgument: "MaskedArray expects empty metadata, got {} bytes", metadata.len() ); } if !buffers.is_empty() { - vortex_bail!("Expected 0 buffer, got {}", buffers.len()); + vortex_bail!(MismatchedTypes: "Expected 0 buffer, got {}", buffers.len()); } vortex_ensure!( children.len() == 1 || children.len() == 2, - "`MaskedArray::build` expects 1 or 2 children, got {}", + InvalidArgument: "`MaskedArray::build` expects 1 or 2 children, got {}", children.len() ); diff --git a/vortex-array/src/arrays/masked/vtable/operations.rs b/vortex-array/src/arrays/masked/vtable/operations.rs index 6215bdcc7f2..4450380579d 100644 --- a/vortex-array/src/arrays/masked/vtable/operations.rs +++ b/vortex-array/src/arrays/masked/vtable/operations.rs @@ -25,7 +25,7 @@ impl OperationsVTable for Masked { } Ok(state .slot(MaskedSlots::CHILD)? - .ok_or_else(|| vortex_err!("Masked child slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "Masked child slot is missing"))? .execute_scalar(index, ctx)? .into_nullable()) } diff --git a/vortex-array/src/arrays/null/compute/cast.rs b/vortex-array/src/arrays/null/compute/cast.rs index be9da91131e..33827f8f639 100644 --- a/vortex-array/src/arrays/null/compute/cast.rs +++ b/vortex-array/src/arrays/null/compute/cast.rs @@ -16,7 +16,7 @@ use crate::scalar_fn::fns::cast::CastReduce; impl CastReduce for Null { fn cast(array: ArrayView<'_, Null>, dtype: &DType) -> VortexResult> { if !dtype.is_nullable() { - vortex_bail!("Cannot cast Null to {}", dtype); + vortex_bail!(MismatchedTypes: "Cannot cast Null to {}", dtype); } if dtype == &DType::Null { return Ok(Some(array.array().clone())); diff --git a/vortex-array/src/arrays/null/compute/take.rs b/vortex-array/src/arrays/null/compute/take.rs index 6a60c94a54c..9839c8c3193 100644 --- a/vortex-array/src/arrays/null/compute/take.rs +++ b/vortex-array/src/arrays/null/compute/take.rs @@ -27,7 +27,7 @@ impl TakeExecute for Null { match_each_integer_ptype!(indices.ptype(), |T| { for index in indices.as_slice::() { if (*index as usize) >= array.len() { - vortex_bail!(OutOfBounds: *index as usize, 0, array.len()); + vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", *index as usize, 0, array.len()); } } }); diff --git a/vortex-array/src/arrays/null/mod.rs b/vortex-array/src/arrays/null/mod.rs index 6c0160c4e15..aeff3cf1499 100644 --- a/vortex-array/src/arrays/null/mod.rs +++ b/vortex-array/src/arrays/null/mod.rs @@ -64,7 +64,7 @@ impl VTable for Null { _len: usize, _slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(*dtype, DType::Null, "NullArray dtype must be DType::Null"); + vortex_ensure_eq!(*dtype, DType::Null, MismatchedTypes: "NullArray dtype must be DType::Null"); Ok(()) } @@ -73,7 +73,7 @@ impl VTable for Null { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("NullArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "NullArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -89,7 +89,7 @@ impl VTable for Null { } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { - vortex_panic!("NullArray slot_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "NullArray slot_name index {idx} out of bounds") } fn serialize( @@ -111,7 +111,7 @@ impl VTable for Null { ) -> VortexResult> { vortex_ensure!( metadata.is_empty(), - "NullArray expects empty metadata, got {} bytes", + Serde: "NullArray expects empty metadata, got {} bytes", metadata.len() ); Ok(ArrayParts::new( @@ -141,7 +141,7 @@ impl VTable for Null { _ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for Null requires a NullBuilder"); + vortex_bail!(InvalidArgument: "append_to_builder for Null requires a NullBuilder"); }; builder.append_nulls(array.len()); Ok(()) diff --git a/vortex-array/src/arrays/patched/array.rs b/vortex-array/src/arrays/patched/array.rs index 48e679efb86..17ddecfda62 100644 --- a/vortex-array/src/arrays/patched/array.rs +++ b/vortex-array/src/arrays/patched/array.rs @@ -82,17 +82,17 @@ impl PatchedData { vortex_ensure_eq!( slots.inner.dtype(), dtype, - "PatchedArray base dtype does not match outer dtype", + MismatchedTypes: "PatchedArray base dtype does not match outer dtype", ); vortex_ensure_eq!( slots.inner.len(), len, - "PatchedArray base len does not match outer len", + InvalidArgument: "PatchedArray base len does not match outer len", ); vortex_ensure_eq!( slots.patch_indices.len(), slots.patch_values.len(), - "PatchedArray patch indices len does not match patch values len", + InvalidArgument: "PatchedArray patch indices len does not match patch values len", ); Ok(()) } @@ -129,12 +129,12 @@ pub trait PatchedArrayExt: PatchedArraySlotsExt { let start = start .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("could not cast lane_offset to usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "could not cast lane_offset to usize"))?; let stop = stop .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("could not cast lane_offset to usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "could not cast lane_offset to usize"))?; Ok(start..stop) } @@ -180,22 +180,22 @@ impl Patched { ) -> VortexResult> { vortex_ensure!( inner.dtype().eq_with_nullability_superset(patches.dtype()), - "array DType must match patches DType" + MismatchedTypes: "array DType must match patches DType" ); vortex_ensure!( inner.dtype().is_primitive(), - "Creating PatchedArray from Patches only supported for primitive arrays" + NotImplemented: "Creating PatchedArray from Patches only supported for primitive arrays" ); vortex_ensure!( patches.num_patches() <= u32::MAX as usize, - "PatchedArray does not support > u32::MAX patch values" + Overflow: "PatchedArray does not support > u32::MAX patch values" ); vortex_ensure!( patches.values().all_valid(ctx)?, - "PatchedArray cannot be built from Patches with nulls" + InvalidArgument: "PatchedArray cannot be built from Patches with nulls" ); let values_ptype = patches.dtype().as_ptype(); diff --git a/vortex-array/src/arrays/patched/compute/compare.rs b/vortex-array/src/arrays/patched/compute/compare.rs index 800783b11c5..e66ced14f00 100644 --- a/vortex-array/src/arrays/patched/compute/compare.rs +++ b/vortex-array/src/arrays/patched/compute/compare.rs @@ -273,7 +273,7 @@ mod tests { let lhs = Patched::from_array_and_patches(lhs, &patches, &mut ctx)? .into_array() .try_downcast::() - .map_err(|_| vortex_err!("expected patched array"))?; + .map_err(|_| vortex_err!(InvalidArgument: "expected patched array"))?; let rhs = ConstantArray::new(subnormal, 512).into_array(); @@ -283,7 +283,7 @@ mod tests { CompareOperator::Eq, &mut ctx, )? - .ok_or_else(|| vortex_err!("expected compare result"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected compare result"))?; let expected = BoolArray::from_indices(512, [510], Validity::NonNullable).into_array(); @@ -309,7 +309,7 @@ mod tests { let lhs = Patched::from_array_and_patches(lhs, &patches, &mut ctx)? .into_array() .try_downcast::() - .map_err(|_| vortex_err!("expected patched array"))?; + .map_err(|_| vortex_err!(InvalidArgument: "expected patched array"))?; let rhs = ConstantArray::new(0.0f32, 10).into_array(); @@ -319,7 +319,7 @@ mod tests { CompareOperator::Eq, &mut ctx, )? - .ok_or_else(|| vortex_err!("expected compare result"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected compare result"))?; let expected = BoolArray::from_indices(10, [7], Validity::NonNullable).into_array(); diff --git a/vortex-array/src/arrays/patched/vtable/mod.rs b/vortex-array/src/arrays/patched/vtable/mod.rs index 01c71d52997..e4392ec8c3f 100644 --- a/vortex-array/src/arrays/patched/vtable/mod.rs +++ b/vortex-array/src/arrays/patched/vtable/mod.rs @@ -123,11 +123,11 @@ impl VTable for Patched { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("invalid buffer index for PatchedArray: {idx}"); + vortex_panic!(OutOfBounds: "invalid buffer index for PatchedArray: {idx}"); } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("invalid buffer index for PatchedArray: {idx}"); + vortex_panic!(OutOfBounds: "invalid buffer index for PatchedArray: {idx}"); } fn with_buffers( diff --git a/vortex-array/src/arrays/piecewise_sequence/mod.rs b/vortex-array/src/arrays/piecewise_sequence/mod.rs index 843fe7a01cc..2cda9884f0f 100644 --- a/vortex-array/src/arrays/piecewise_sequence/mod.rs +++ b/vortex-array/src/arrays/piecewise_sequence/mod.rs @@ -48,12 +48,12 @@ pub(crate) fn check_index_arrays( vortex_ensure_eq!( starts.len(), lengths.len(), - "PiecewiseSequenceArray starts length does not match lengths length", + InvalidArgument: "PiecewiseSequenceArray starts length does not match lengths length", ); vortex_ensure_eq!( starts.len(), multipliers.len(), - "PiecewiseSequenceArray starts length does not match multipliers length", + InvalidArgument: "PiecewiseSequenceArray starts length does not match multipliers length", ); Ok(()) } @@ -110,12 +110,12 @@ pub(crate) fn constant_unsigned_usize(array: &ConstantArray) -> usize { fn check_index_array(name: &str, array: &ArrayRef) -> VortexResult<()> { vortex_ensure!( array.dtype().is_unsigned_int(), - "PiecewiseSequenceArray {name} must have unsigned integer dtype, got {}", + MismatchedTypes: "PiecewiseSequenceArray {name} must have unsigned integer dtype, got {}", array.dtype() ); vortex_ensure!( !array.dtype().is_nullable(), - "PiecewiseSequenceArray {name} must be non-nullable, got {}", + InvalidArgument: "PiecewiseSequenceArray {name} must be non-nullable, got {}", array.dtype() ); Ok(()) @@ -144,23 +144,23 @@ where let multiplier: usize = multiplier.as_(); if length != 0 { let last_offset = length - 1; - let last_delta = last_offset - .checked_mul(multiplier) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; - start - .checked_add(last_delta) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; + let last_delta = last_offset.checked_mul(multiplier).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), + )?; + start.checked_add(last_delta).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), + )?; } - computed_len = computed_len - .checked_add(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + computed_len = computed_len.checked_add(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; values.extend((0..length).map(|offset| (start + offset * multiplier) as u64)); } if computed_len != output_len { vortex_bail!( - "PiecewiseSequenceArray expanded length {computed_len} does not match declared length {output_len}" + AssertionFailed: "PiecewiseSequenceArray expanded length {computed_len} does not match declared length {output_len}" ); } Ok(values) diff --git a/vortex-array/src/arrays/piecewise_sequence/vtable.rs b/vortex-array/src/arrays/piecewise_sequence/vtable.rs index db5b33a1081..98c0c2da8f1 100644 --- a/vortex-array/src/arrays/piecewise_sequence/vtable.rs +++ b/vortex-array/src/arrays/piecewise_sequence/vtable.rs @@ -64,19 +64,23 @@ impl VTable for PiecewiseSequence { vortex_ensure_eq!( dtype, &DType::from(PType::U64), - "PiecewiseSequenceArray dtype must be u64", + MismatchedTypes: "PiecewiseSequenceArray dtype must be u64", ); - vortex_ensure_eq!(slots.len(), PiecewiseSequenceSlots::NAMES.len()); - let starts = slots[PiecewiseSequenceSlots::STARTS] - .as_ref() - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray starts slot must be present"))?; - let lengths = slots[PiecewiseSequenceSlots::LENGTHS] - .as_ref() - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray lengths slot must be present"))?; + vortex_ensure_eq!( + slots.len(), + PiecewiseSequenceSlots::NAMES.len(), + InvalidArgument + ); + let starts = slots[PiecewiseSequenceSlots::STARTS].as_ref().ok_or_else( + || vortex_err!(InvalidArgument: "PiecewiseSequenceArray starts slot must be present"), + )?; + let lengths = slots[PiecewiseSequenceSlots::LENGTHS].as_ref().ok_or_else( + || vortex_err!(InvalidArgument: "PiecewiseSequenceArray lengths slot must be present"), + )?; let multipliers = slots[PiecewiseSequenceSlots::MULTIPLIERS] .as_ref() .ok_or_else(|| { - vortex_err!("PiecewiseSequenceArray multipliers slot must be present") + vortex_err!(InvalidArgument: "PiecewiseSequenceArray multipliers slot must be present") })?; check_index_arrays(starts, lengths, multipliers) } @@ -86,7 +90,7 @@ impl VTable for PiecewiseSequence { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!("PiecewiseSequenceArray has no buffers") + vortex_panic!(OutOfBounds: "PiecewiseSequenceArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -121,7 +125,7 @@ impl VTable for PiecewiseSequence { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("PiecewiseSequenceArray is not serializable") + vortex_bail!(Serde: "PiecewiseSequenceArray is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { @@ -189,15 +193,15 @@ where if remaining < length { let start: usize = start.as_(); let multiplier: usize = multiplier.as_(); - let offset = remaining - .checked_mul(multiplier) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; - let value = start - .checked_add(offset) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; + let offset = remaining.checked_mul(multiplier).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), + )?; + let value = start.checked_add(offset).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), + )?; return Ok(value as u64); } remaining -= length; } - vortex_bail!("PiecewiseSequenceArray index {index} out of bounds") + vortex_bail!(OutOfBounds: "PiecewiseSequenceArray index {index} out of bounds") } diff --git a/vortex-array/src/arrays/primitive/array/cast.rs b/vortex-array/src/arrays/primitive/array/cast.rs index 6733c0e4ebd..e5a1c68dc66 100644 --- a/vortex-array/src/arrays/primitive/array/cast.rs +++ b/vortex-array/src/arrays/primitive/array/cast.rs @@ -18,7 +18,7 @@ impl PrimitiveData { pub fn as_slice(&self) -> &[T] { if T::PTYPE != self.ptype() { vortex_panic!( - "Attempted to get slice of type {} from array of type {}", + MismatchedTypes: "Attempted to get slice of type {} from array of type {}", T::PTYPE, self.ptype() ) diff --git a/vortex-array/src/arrays/primitive/array/conversion.rs b/vortex-array/src/arrays/primitive/array/conversion.rs index 444b79dfe41..8a3161e173d 100644 --- a/vortex-array/src/arrays/primitive/array/conversion.rs +++ b/vortex-array/src/arrays/primitive/array/conversion.rs @@ -43,7 +43,7 @@ impl PrimitiveArray { pub fn to_buffer(&self) -> Buffer { if T::PTYPE != self.ptype() { vortex_panic!( - "Attempted to get buffer of type {} from array of type {}", + MismatchedTypes: "Attempted to get buffer of type {} from array of type {}", T::PTYPE, self.ptype() ) diff --git a/vortex-array/src/arrays/primitive/array/mod.rs b/vortex-array/src/arrays/primitive/array/mod.rs index 417f4e184a6..c2d575594d7 100644 --- a/vortex-array/src/arrays/primitive/array/mod.rs +++ b/vortex-array/src/arrays/primitive/array/mod.rs @@ -531,7 +531,7 @@ impl PrimitiveData { pub fn to_buffer(&self) -> Buffer { if T::PTYPE != self.ptype() { vortex_panic!( - "Attempted to get buffer of type {} from array of type {}", + MismatchedTypes: "Attempted to get buffer of type {} from array of type {}", T::PTYPE, self.ptype() ) @@ -543,7 +543,7 @@ impl PrimitiveData { pub fn into_buffer(self) -> Buffer { if T::PTYPE != self.ptype() { vortex_panic!( - "Attempted to get buffer of type {} from array of type {}", + MismatchedTypes: "Attempted to get buffer of type {} from array of type {}", T::PTYPE, self.ptype() ) @@ -565,7 +565,7 @@ impl PrimitiveData { pub fn try_into_buffer_mut(self) -> Result, Buffer> { if T::PTYPE != self.ptype() { vortex_panic!( - "Attempted to get buffer_mut of type {} from array of type {}", + MismatchedTypes: "Attempted to get buffer_mut of type {} from array of type {}", T::PTYPE, self.ptype() ) diff --git a/vortex-array/src/arrays/primitive/compute/cast.rs b/vortex-array/src/arrays/primitive/compute/cast.rs index c937d68d611..5ecd1ba88f6 100644 --- a/vortex-array/src/arrays/primitive/compute/cast.rs +++ b/vortex-array/src/arrays/primitive/compute/cast.rs @@ -107,7 +107,7 @@ impl CastKernel for Primitive { if same_rep { if !values_fit_in(array, new_ptype, ctx, true) { vortex_bail!( - Compute: "Cannot cast {} to {} — values exceed target range", + Overflow: "Cannot cast {} to {} — values exceed target range", src_ptype, new_ptype, ); } @@ -132,7 +132,7 @@ fn cast_to_decimal( ) -> VortexResult { if !array.ptype().is_int() { vortex_bail!( - Compute: "Cannot cast floating primitive {} to decimal {}", + MismatchedTypes: "Cannot cast floating primitive {} to decimal {}", array.ptype(), decimal_dtype ); } @@ -399,7 +399,7 @@ where #[cold] #[inline(never)] fn scale_factor_error(scale: i8) -> VortexError { - vortex_err!(Compute: "Cannot create decimal scale factor for scale {scale}") + vortex_err!(Overflow: "Cannot create decimal scale factor for scale {scale}") } fn decimal_value_fits_precision( @@ -450,7 +450,7 @@ where { let Some(value) = ::from(value) else { return vortex_err!( - Compute: "primitive value cannot be represented while casting to {}", + Overflow: "primitive value cannot be represented while casting to {}", decimal_dtype ); }; @@ -465,7 +465,7 @@ where "primitive-to-decimal fast path rejected a value that the scalar cast accepts" ); vortex_err!( - Compute: "primitive value cannot be represented while casting to {}", + Overflow: "primitive value cannot be represented while casting to {}", decimal_dtype ) } @@ -484,7 +484,7 @@ where { let overflow = || { vortex_err!( - Compute: "Cannot cast {} to {} — value exceeds target range", + Overflow: "Cannot cast {} to {} — value exceeds target range", F::PTYPE, T::PTYPE, ) }; @@ -664,7 +664,7 @@ mod test { use rstest::rstest; use vortex_buffer::BitBuffer; use vortex_buffer::buffer; - use vortex_error::VortexError; + use vortex_error::VortexErrorKind; use vortex_error::VortexResult; use vortex_mask::Mask; use vortex_session::VortexSession; @@ -1093,7 +1093,7 @@ mod test { .map(|c| c.into_array()) }) .unwrap_err(); - assert!(matches!(error, VortexError::Compute(..))); + assert_eq!(error.kind(), VortexErrorKind::Overflow); assert!(error.to_string().contains("values exceed target range")); } @@ -1109,7 +1109,7 @@ mod test { }) .unwrap_err(); - assert!(matches!(err, VortexError::InvalidArgument(..))); + assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); assert!( err.to_string() .contains("Cannot cast array with invalid values to non-nullable type.") @@ -1173,7 +1173,7 @@ mod test { .map(|c| c.into_array()) }) .unwrap_err(); - assert!(matches!(err, VortexError::Compute(..))); + assert_eq!(err.kind(), VortexErrorKind::Overflow); } /// All-null array cast between same-width types should succeed without diff --git a/vortex-array/src/arrays/primitive/compute/zip.rs b/vortex-array/src/arrays/primitive/compute/zip.rs index a653f01099e..b6d574aacd9 100644 --- a/vortex-array/src/arrays/primitive/compute/zip.rs +++ b/vortex-array/src/arrays/primitive/compute/zip.rs @@ -40,7 +40,7 @@ impl ZipKernel for Primitive { if if_true.ptype() != if_false.ptype() { vortex_bail!( - "zip requires if_true and if_false to share a primitive type, got {} and {}", + InvalidArgument: "zip requires if_true and if_false to share a primitive type, got {} and {}", if_true.ptype(), if_false.ptype() ); diff --git a/vortex-array/src/arrays/primitive/vtable/mod.rs b/vortex-array/src/arrays/primitive/vtable/mod.rs index df4006626a2..071d8552283 100644 --- a/vortex-array/src/arrays/primitive/vtable/mod.rs +++ b/vortex-array/src/arrays/primitive/vtable/mod.rs @@ -112,12 +112,12 @@ impl VTable for Primitive { slots: &[Option], ) -> VortexResult<()> { let DType::Primitive(_, nullability) = dtype else { - vortex_bail!("Expected primitive dtype, got {dtype:?}"); + vortex_bail!(MismatchedTypes: "Expected primitive dtype, got {dtype:?}"); }; vortex_ensure_eq!( data.len(), len, - "PrimitiveArray length does not match outer length", + InvalidArgument: "PrimitiveArray length does not match outer length", ); let validity = crate::array::child_to_validity(slots[PrimitiveSlots::VALIDITY].as_ref(), *nullability); @@ -125,7 +125,7 @@ impl VTable for Primitive { vortex_ensure_eq!( validity_len, len, - "PrimitiveArray validity len does not match outer length", + InvalidArgument: "PrimitiveArray validity len does not match outer length", ); } @@ -144,7 +144,7 @@ impl VTable for Primitive { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "PrimitiveArray expects empty metadata, got {} bytes", + InvalidArgument: "PrimitiveArray expects empty metadata, got {} bytes", metadata.len() ); } @@ -156,12 +156,12 @@ impl VTable for Primitive { vortex_ensure!( buffer.is_aligned_to(Alignment::new(ptype.byte_width())), - "Misaligned buffer cannot be used to build PrimitiveArray of {ptype}" + InvalidArgument: "Misaligned buffer cannot be used to build PrimitiveArray of {ptype}" ); if buffer.len() != ptype.byte_width() * len { vortex_bail!( - "Buffer length {} does not match expected length {} for {}, {}", + MismatchedTypes: "Buffer length {} does not match expected length {} for {}, {}", buffer.len(), ptype.byte_width() * len, ptype.byte_width(), @@ -200,7 +200,7 @@ impl VTable for Primitive { } }); - vortex_bail!("append_to_builder for Primitive requires a matching PrimitiveBuilder"); + vortex_bail!(InvalidArgument: "append_to_builder for Primitive requires a matching PrimitiveBuilder"); } fn reduce_parent( diff --git a/vortex-array/src/arrays/scalar_fn/array.rs b/vortex-array/src/arrays/scalar_fn/array.rs index 391ea9a03cd..82f32f74b5c 100644 --- a/vortex-array/src/arrays/scalar_fn/array.rs +++ b/vortex-array/src/arrays/scalar_fn/array.rs @@ -143,7 +143,7 @@ impl Array { #[inline] fn infer_len(slots: &[Option]) -> VortexResult { let Some(child) = slots.first().and_then(Option::as_ref) else { - vortex_bail!("ScalarFnArray length cannot be inferred without children"); + vortex_bail!(InvalidArgument: "ScalarFnArray length cannot be inferred without children"); }; Ok(child.len()) } @@ -159,7 +159,7 @@ impl Array { pub(super) fn validate_not_literal(scalar_fn: &ScalarFnRef) -> VortexResult<()> { vortex_ensure!( !scalar_fn.is::(), - "ScalarFnArray cannot wrap a literal, use ConstantArray instead" + InvalidArgument: "ScalarFnArray cannot wrap a literal, use ConstantArray instead" ); Ok(()) } @@ -169,7 +169,7 @@ impl Array { let arity = scalar_fn.signature().arity(); vortex_ensure!( arity.matches(child_count), - "ScalarFnArray requires {arity} children, got {child_count}" + InvalidArgument: "ScalarFnArray requires {arity} children, got {child_count}" ); Ok(()) } @@ -179,7 +179,7 @@ impl Array { for child in slots.iter().flatten() { vortex_ensure!( child.len() == len, - "ScalarFnArray must have children equal to the array length" + InvalidArgument: "ScalarFnArray must have children equal to the array length" ); } Ok(()) diff --git a/vortex-array/src/arrays/scalar_fn/plugin.rs b/vortex-array/src/arrays/scalar_fn/plugin.rs index 4a4a7d3d5ab..eafbb4c93c7 100644 --- a/vortex-array/src/arrays/scalar_fn/plugin.rs +++ b/vortex-array/src/arrays/scalar_fn/plugin.rs @@ -83,7 +83,7 @@ impl ArrayPlugin for ScalarFnArrayPlugi vortex_ensure_eq!( parts.serialized_id, self.id(), - "scalar function array plugin does not recognize serialized ID", + Serde: "scalar function array plugin does not recognize serialized ID", ); let len = parts.len; let scalar_parts = ::deserialize( diff --git a/vortex-array/src/arrays/scalar_fn/rules.rs b/vortex-array/src/arrays/scalar_fn/rules.rs index 5383a614bd6..3f2b21a8610 100644 --- a/vortex-array/src/arrays/scalar_fn/rules.rs +++ b/vortex-array/src/arrays/scalar_fn/rules.rs @@ -203,13 +203,13 @@ mod tests { let mask = Mask::from_iter((0..100).map(|index| index % 20 == 0)); let values = mask .values() - .ok_or_else(|| vortex_err!("expected mask values"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected mask values"))?; assert!(values.cached_indices().is_none()); let parent = FilterArray::try_new(array.clone().into_array(), mask.clone())?; let result = ScalarFilterPushdownRule .reduce_parent(array.as_view(), parent.as_view(), 0)? - .ok_or_else(|| vortex_err!("expected filter pushdown"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected filter pushdown"))?; assert_eq!(values.cached_indices().is_some(), nchildren > 1); let scalar_fn = result.as_::(); @@ -239,7 +239,7 @@ mod tests { let result = ScalarFilterPushdownRule .reduce_parent(array.as_::(), parent.as_view(), 0)? - .ok_or_else(|| vortex_err!("expected filter pushdown"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected filter pushdown"))?; assert_eq!(result.as_::().nchildren(), 0); assert_eq!(result.len(), 2); diff --git a/vortex-array/src/arrays/scalar_fn/vtable/mod.rs b/vortex-array/src/arrays/scalar_fn/vtable/mod.rs index 43df40e1d2f..df74447618a 100644 --- a/vortex-array/src/arrays/scalar_fn/vtable/mod.rs +++ b/vortex-array/src/arrays/scalar_fn/vtable/mod.rs @@ -87,7 +87,7 @@ impl VTable for ScalarFn { vortex_ensure_eq!( scalar_fn.id(), self.id, - "ScalarFnArray data scalar_fn does not match vtable", + MismatchedTypes: "ScalarFnArray data scalar_fn does not match vtable", ); Array::::validate_not_literal(scalar_fn)?; @@ -96,18 +96,18 @@ impl VTable for ScalarFn { vortex_ensure_eq!( missing_children, 0, - "ScalarFnArray requires every child slot to be present", + InvalidArgument: "ScalarFnArray requires every child slot to be present", ); let arity = scalar_fn.signature().arity(); vortex_ensure!( arity.matches(slots.len()), - "ScalarFnArray requires {arity} children, got {}", + InvalidArgument: "ScalarFnArray requires {arity} children, got {}", slots.len() ); vortex_ensure!( slots.iter().flatten().all(|c| c.len() == len), - "All child arrays must have the same length as the scalar function array" + InvalidArgument: "All child arrays must have the same length as the scalar function array" ); let child_dtypes = slots @@ -118,7 +118,7 @@ impl VTable for ScalarFn { vortex_ensure_eq!( scalar_fn.return_dtype(&child_dtypes)?, *dtype, - "ScalarFnArray dtype does not match scalar function return dtype", + MismatchedTypes: "ScalarFnArray dtype does not match scalar function return dtype", ); Ok(()) } @@ -128,7 +128,7 @@ impl VTable for ScalarFn { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("ScalarFnArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "ScalarFnArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -160,7 +160,7 @@ impl VTable for ScalarFn { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("Deserialization of ScalarFnVTable metadata is not supported"); + vortex_bail!(Serde: "Deserialization of ScalarFnVTable metadata is not supported"); } fn slot_name(array: ArrayView<'_, Self>, idx: usize) -> String { diff --git a/vortex-array/src/arrays/scalar_fn/vtable/validity.rs b/vortex-array/src/arrays/scalar_fn/vtable/validity.rs index 71c5a2985b4..5f0b341b427 100644 --- a/vortex-array/src/arrays/scalar_fn/vtable/validity.rs +++ b/vortex-array/src/arrays/scalar_fn/vtable/validity.rs @@ -81,7 +81,7 @@ impl VTable for ScalarFnValidity { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!("ScalarFnValidity has no buffers") + vortex_panic!(OutOfBounds: "ScalarFnValidity has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -112,7 +112,7 @@ impl VTable for ScalarFnValidity { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("ScalarFnValidity deserialize not supported"); + vortex_bail!(Serde: "ScalarFnValidity deserialize not supported"); } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { diff --git a/vortex-array/src/arrays/slice/array.rs b/vortex-array/src/arrays/slice/array.rs index c9250213c21..1947064e412 100644 --- a/vortex-array/src/arrays/slice/array.rs +++ b/vortex-array/src/arrays/slice/array.rs @@ -40,7 +40,7 @@ impl SliceData { fn try_new(child_len: usize, range: Range) -> VortexResult { if range.end > child_len { vortex_panic!( - "SliceArray range out of bounds: range {:?} exceeds child array length {}", + OutOfBounds: "SliceArray range out of bounds: range {:?} exceeds child array length {}", range, child_len ); diff --git a/vortex-array/src/arrays/slice/vtable.rs b/vortex-array/src/arrays/slice/vtable.rs index 3b2351a065c..27ac72813c9 100644 --- a/vortex-array/src/arrays/slice/vtable.rs +++ b/vortex-array/src/arrays/slice/vtable.rs @@ -81,7 +81,7 @@ impl VTable for Slice { ) -> VortexResult<()> { vortex_ensure!( slots[SliceSlots::CHILD].is_some(), - "SliceArray child slot must be present" + InvalidArgument: "SliceArray child slot must be present" ); let child = slots[SliceSlots::CHILD] .as_ref() @@ -89,16 +89,16 @@ impl VTable for Slice { vortex_ensure_eq!( child.dtype(), dtype, - "SliceArray dtype does not match outer dtype", + MismatchedTypes: "SliceArray dtype does not match outer dtype", ); vortex_ensure_eq!( data.len(), len, - "SliceArray length does not match outer length", + InvalidArgument: "SliceArray length does not match outer length", ); vortex_ensure!( data.range.end <= child.len(), - "SliceArray range {:?} exceeds child length {}", + InvalidArgument: "SliceArray range {:?} exceeds child length {}", data.range, child.len() ); @@ -110,7 +110,7 @@ impl VTable for Slice { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!("SliceArray has no buffers") + vortex_panic!(OutOfBounds: "SliceArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -134,7 +134,7 @@ impl VTable for Slice { _session: &VortexSession, ) -> VortexResult>> { // TODO(joe): make this configurable - vortex_bail!("Slice array is not serializable") + vortex_bail!(Serde: "Slice array is not serializable") } fn deserialize( @@ -147,7 +147,7 @@ impl VTable for Slice { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("Slice array is not serializable") + vortex_bail!(Serde: "Slice array is not serializable") } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { @@ -180,7 +180,7 @@ impl OperationsVTable for Slice { let child_index = state.array().range.start + index; state .slot(SliceSlots::CHILD)? - .ok_or_else(|| vortex_err!("Slice child slot is missing"))? + .ok_or_else(|| vortex_err!(InvalidArgument: "Slice child slot is missing"))? .execute_scalar(child_index, ctx) } diff --git a/vortex-array/src/arrays/struct_/array.rs b/vortex-array/src/arrays/struct_/array.rs index 6d3052f1b25..6a001c186dc 100644 --- a/vortex-array/src/arrays/struct_/array.rs +++ b/vortex-array/src/arrays/struct_/array.rs @@ -253,7 +253,7 @@ pub trait StructArrayExt: StructArraySlotsExt { let name = name.as_ref(); self.unmasked_field_by_name_opt(name).ok_or_else(|| { vortex_err!( - "Field {name} not found in struct array with names {:?}", + NotFound: "Field {name} not found in struct array with names {:?}", self.names() ) }) @@ -366,7 +366,7 @@ impl Array { let len = fields .first() .map(|f| f.len()) - .ok_or_else(|| vortex_err!("StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; Self::try_new(FieldNames::from_iter(names), fields, len, validity) } @@ -382,7 +382,7 @@ impl Array { let len = fields .first() .map(ArrayRef::len) - .ok_or_else(|| vortex_err!("StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; Self::try_new( FieldNames::from_iter(names), @@ -407,7 +407,7 @@ impl Array { let idx = self .struct_fields() .find(f_name.as_ref()) - .ok_or_else(|| vortex_err!("Unknown field {f_name}"))?; + .ok_or_else(|| vortex_err!(NotFound: "Unknown field {f_name}"))?; names.push(self.names()[idx].clone()); children.push(self.unmasked_field(idx).clone()); @@ -496,7 +496,7 @@ impl Array { { let mut it = chunks.into_iter(); let Some(first) = it.next() else { - vortex_bail!("cannot concat empty iterator of arrays"); + vortex_bail!(InvalidArgument: "cannot concat empty iterator of arrays"); }; let first_dtype = first.borrow().dtype().clone(); let struct_fields = first_dtype.as_struct_fields().clone(); @@ -508,7 +508,7 @@ impl Array { let chunk = chunk.borrow(); if &first_dtype != chunk.dtype() { vortex_bail!( - "cannot concatenate struct arrays with differing dtypes: {}, {}", + MismatchedTypes: "cannot concatenate struct arrays with differing dtypes: {}, {}", first_dtype, chunk.dtype(), ); diff --git a/vortex-array/src/arrays/struct_/compute/cast.rs b/vortex-array/src/arrays/struct_/compute/cast.rs index e73ea26446b..3e5e84dfabe 100644 --- a/vortex-array/src/arrays/struct_/compute/cast.rs +++ b/vortex-array/src/arrays/struct_/compute/cast.rs @@ -103,7 +103,7 @@ pub(crate) fn struct_cast_fields( // If the field is nullable, we add a new ConstantArray field with the type. vortex_ensure!( target_type.is_nullable(), - "CAST for struct only supports added nullable fields" + InvalidArgument: "CAST for struct only supports added nullable fields" ); cast_fields.push( diff --git a/vortex-array/src/arrays/struct_/compute/rules.rs b/vortex-array/src/arrays/struct_/compute/rules.rs index f7bcd750030..bc0c4bd8004 100644 --- a/vortex-array/src/arrays/struct_/compute/rules.rs +++ b/vortex-array/src/arrays/struct_/compute/rules.rs @@ -95,7 +95,7 @@ impl ArrayParentReduceRule for StructGetItemRule { .unmasked_field_by_name_opt(field_name) .ok_or_else(|| { vortex_err!( - "Field '{}' missing from struct array {}", + NotFound: "Field '{}' missing from struct array {}", field_name, child.struct_fields().names() ) diff --git a/vortex-array/src/arrays/struct_/vtable/mod.rs b/vortex-array/src/arrays/struct_/vtable/mod.rs index 15cf128b8e9..4e2b4c661c2 100644 --- a/vortex-array/src/arrays/struct_/vtable/mod.rs +++ b/vortex-array/src/arrays/struct_/vtable/mod.rs @@ -63,7 +63,7 @@ impl VTable for Struct { slots: &[Option], ) -> VortexResult<()> { let DType::Struct(struct_dtype, nullability) = dtype else { - vortex_bail!("Expected struct dtype, found {:?}", dtype) + vortex_bail!(MismatchedTypes: "Expected struct dtype, found {:?}", dtype) }; let expected_slots = struct_dtype.nfields() + 1; @@ -93,9 +93,9 @@ impl VTable for Struct { for (idx, (slot, field_dtype)) in field_slots.iter().zip(struct_dtype.fields()).enumerate() { - let field = slot - .as_ref() - .ok_or_else(|| vortex_error::vortex_err!("StructArray missing field slot {idx}"))?; + let field = slot.as_ref().ok_or_else( + || vortex_error::vortex_err!(NotFound: "StructArray missing field slot {idx}"), + )?; if field.len() != len { vortex_bail!( InvalidArgument: "StructArray field {idx} has length {} but expected {}", @@ -116,11 +116,11 @@ impl VTable for Struct { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("StructArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "StructArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("StructArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "StructArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -150,12 +150,12 @@ impl VTable for Struct { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "StructArray expects empty metadata, got {} bytes", + InvalidArgument: "StructArray expects empty metadata, got {} bytes", metadata.len() ); } let DType::Struct(struct_dtype, nullability) = dtype else { - vortex_bail!("Expected struct dtype, found {:?}", dtype) + vortex_bail!(MismatchedTypes: "Expected struct dtype, found {:?}", dtype) }; let (validity, non_data_children) = if children.len() == struct_dtype.nfields() { @@ -165,7 +165,7 @@ impl VTable for Struct { (Validity::Array(validity), 1_usize) } else { vortex_bail!( - "Expected {} or {} children, found {}", + InvalidArgument: "Expected {} or {} children, found {}", struct_dtype.nfields(), struct_dtype.nfields() + 1, children.len() @@ -211,7 +211,7 @@ impl VTable for Struct { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for Struct requires a StructBuilder"); + vortex_bail!(InvalidArgument: "append_to_builder for Struct requires a StructBuilder"); }; builder.append_struct_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/struct_/vtable/operations.rs b/vortex-array/src/arrays/struct_/vtable/operations.rs index 80086b35007..94a701477aa 100644 --- a/vortex-array/src/arrays/struct_/vtable/operations.rs +++ b/vortex-array/src/arrays/struct_/vtable/operations.rs @@ -32,7 +32,7 @@ impl OperationsVTable for Struct { let slot = StructSlots::FIELDS_OFFSET + field; let value = state .slot(slot)? - .ok_or_else(|| vortex_err!("Struct field slot {slot} is absent"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "Struct field slot {slot} is absent"))? .execute_scalar(index, ctx)?; field_values.push(value.into_value()); } diff --git a/vortex-array/src/arrays/union/array.rs b/vortex-array/src/arrays/union/array.rs index bd897f916e9..e9c089c1b55 100644 --- a/vortex-array/src/arrays/union/array.rs +++ b/vortex-array/src/arrays/union/array.rs @@ -105,7 +105,7 @@ pub trait UnionArrayExt: UnionArraySlotsExt { let name = name.as_ref(); self.child_by_name_opt(name).ok_or_else(|| { vortex_err!( - "Variant {name} not found in union array with names {:?}", + NotFound: "Variant {name} not found in union array with names {:?}", self.variants().names() ) }) @@ -144,7 +144,7 @@ impl Array { ) -> VortexResult { vortex_ensure!( matches!(type_ids.dtype(), DType::Primitive(PType::U8, _)), - "UnionArray type_ids must be u8, got {}", + MismatchedTypes: "UnionArray type_ids must be u8, got {}", type_ids.dtype() ); @@ -186,9 +186,9 @@ impl Array { /// /// Returns an error if `scalar` does not have a union dtype. pub fn constant(scalar: &Scalar, len: usize) -> VortexResult { - let union = scalar - .as_union_opt() - .ok_or_else(|| vortex_err!("Expected a union scalar, got {}", scalar.dtype()))?; + let union = scalar.as_union_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected a union scalar, got {}", scalar.dtype()), + )?; let variants = union.variants().clone(); let nullability = union.nullability(); diff --git a/vortex-array/src/arrays/union/tests/mod.rs b/vortex-array/src/arrays/union/tests/mod.rs index 9a677da7366..b4f9e5d1780 100644 --- a/vortex-array/src/arrays/union/tests/mod.rs +++ b/vortex-array/src/arrays/union/tests/mod.rs @@ -293,7 +293,7 @@ fn constant_union_canonicalizes_to_sparse_union() -> VortexResult<()> { let unselected = canonical .iter_children() .find(|child| child.dtype() == &unselected_dtype) - .ok_or_else(|| vortex_err!("No child with dtype {unselected_dtype}"))?; + .ok_or_else(|| vortex_err!(NotFound: "No child with dtype {unselected_dtype}"))?; assert_eq!( unselected.execute_scalar(0, &mut ctx)?, Scalar::default_value(&unselected_dtype) diff --git a/vortex-array/src/arrays/union/tests/take.rs b/vortex-array/src/arrays/union/tests/take.rs index ba0de72c01f..016fe353670 100644 --- a/vortex-array/src/arrays/union/tests/take.rs +++ b/vortex-array/src/arrays/union/tests/take.rs @@ -152,7 +152,7 @@ fn take_from_empty_union_is_all_null() -> VortexResult<()> { .execute::(&mut SESSION.create_execution_ctx())? .into_union(); let via_reduce = ::take(empty.as_::(), &indices)? - .ok_or_else(|| vortex_err!("Union take must never decline"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "Union take must never decline"))? .as_::() .into_owned(); diff --git a/vortex-array/src/arrays/union/vtable/mod.rs b/vortex-array/src/arrays/union/vtable/mod.rs index 7800f9430d2..8b1babe0904 100644 --- a/vortex-array/src/arrays/union/vtable/mod.rs +++ b/vortex-array/src/arrays/union/vtable/mod.rs @@ -65,7 +65,7 @@ impl VTable for Union { let type_ids = slots .get(UnionSlots::TYPE_IDS) .and_then(Option::as_ref) - .ok_or_else(|| vortex_err!("UnionArray is missing its type_ids slot"))?; + .ok_or_else(|| vortex_err!(NotFound: "UnionArray is missing its type_ids slot"))?; let variant_arrays = slots .get(UnionSlots::CHILDREN_OFFSET..) .unwrap_or_default() @@ -73,7 +73,7 @@ impl VTable for Union { .enumerate() .map(|(index, slot)| { slot.as_ref() - .ok_or_else(|| vortex_err!("UnionArray is missing child {index}")) + .ok_or_else(|| vortex_err!(NotFound: "UnionArray is missing child {index}")) }) .collect::>>()?; @@ -85,11 +85,11 @@ impl VTable for Union { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("UnionArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "UnionArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!("UnionArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "UnionArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -116,12 +116,16 @@ impl VTable for Union { children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_ensure!(metadata.is_empty(), "UnionArray expects empty metadata"); - vortex_ensure!(buffers.is_empty(), "UnionArray expects no buffers"); + vortex_ensure!(metadata.is_empty(), Serde: "UnionArray expects empty metadata"); + vortex_ensure!(buffers.is_empty(), InvalidArgument: "UnionArray expects no buffers"); let DType::Union(variants, nullability) = dtype else { - vortex_bail!("Expected union dtype, found {dtype}") + vortex_bail!(InvalidArgument: "Expected union dtype, found {dtype}") }; - vortex_ensure_eq!(children.len(), UnionSlots::CHILDREN_OFFSET + variants.len()); + vortex_ensure_eq!( + children.len(), + UnionSlots::CHILDREN_OFFSET + variants.len(), + InvalidArgument + ); let type_ids = children.get( UnionSlots::TYPE_IDS, @@ -158,7 +162,7 @@ impl VTable for Union { _builder: &mut dyn ArrayBuilder, _ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_bail!("TODO(connor)[Union]: implement append_to_builder for Union arrays") + vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement append_to_builder for Union arrays") } fn reduce_parent( diff --git a/vortex-array/src/arrays/union/vtable/operations.rs b/vortex-array/src/arrays/union/vtable/operations.rs index 78b9759ab1c..5f3dc88ec7b 100644 --- a/vortex-array/src/arrays/union/vtable/operations.rs +++ b/vortex-array/src/arrays/union/vtable/operations.rs @@ -27,11 +27,11 @@ impl OperationsVTable for Union { }; let Some(child_index) = array.variants().tag_to_child_index(type_id) else { - vortex_panic!("Unknown UnionArray type ID {type_id}") + vortex_panic!(NotFound: "Unknown UnionArray type ID {type_id}") }; let child = array .child(child_index) - .ok_or_else(|| vortex_err!("UnionArray is missing child {child_index}"))?; + .ok_or_else(|| vortex_err!(NotFound: "UnionArray is missing child {child_index}"))?; let child_scalar = child.execute_scalar(index, ctx)?; Scalar::union( diff --git a/vortex-array/src/arrays/union/vtable/validate.rs b/vortex-array/src/arrays/union/vtable/validate.rs index 8e232600939..634cfb1eb3e 100644 --- a/vortex-array/src/arrays/union/vtable/validate.rs +++ b/vortex-array/src/arrays/union/vtable/validate.rs @@ -16,24 +16,24 @@ pub(super) fn validate_union_components( len: usize, ) -> VortexResult<()> { let DType::Union(variants, nullability) = dtype else { - vortex_bail!("Expected union dtype, found {dtype}") + vortex_bail!(InvalidArgument: "Expected union dtype, found {dtype}") }; vortex_ensure_eq!( variant_arrays.len(), variants.len(), - "UnionArray variant slot count does not match variant count", + InvalidArgument: "UnionArray variant slot count does not match variant count", ); let expected_union_type_ids_dtype = union_type_ids_dtype(*nullability); vortex_ensure_eq!( type_ids.dtype(), &expected_union_type_ids_dtype, - "UnionArray type_ids has unexpected dtype", + MismatchedTypes: "UnionArray type_ids has unexpected dtype", ); vortex_ensure_eq!( type_ids.len(), len, - "UnionArray type_ids length does not match outer length", + InvalidArgument: "UnionArray type_ids length does not match outer length", ); for (index, (variant_dtype, child)) in @@ -42,12 +42,12 @@ pub(super) fn validate_union_components( vortex_ensure_eq!( child.len(), len, - "UnionArray child {index} length does not match outer length", + InvalidArgument: "UnionArray child {index} length does not match outer length", ); vortex_ensure_eq!( child.dtype(), &variant_dtype, - "UnionArray child {index} has unexpected dtype", + MismatchedTypes: "UnionArray child {index} has unexpected dtype", ); } diff --git a/vortex-array/src/arrays/validation_tests.rs b/vortex-array/src/arrays/validation_tests.rs index 938c0e8a709..ad10bff8158 100644 --- a/vortex-array/src/arrays/validation_tests.rs +++ b/vortex-array/src/arrays/validation_tests.rs @@ -14,7 +14,7 @@ mod tests { use vortex_buffer::Buffer; use vortex_buffer::ByteBuffer; use vortex_buffer::buffer; - use vortex_error::VortexError; + use vortex_error::VortexErrorKind; use vortex_session::VortexSession; use crate::IntoArray; @@ -42,7 +42,7 @@ mod tests { let chunk2 = buffer![4i64, 5, 6].into_array(); let result = ChunkedArray::try_new(vec![chunk1, chunk2], PType::I32.into()); - assert!(matches!(result, Err(VortexError::MismatchedTypes(_, _, _)))); + assert_eq!(result.unwrap_err().kind(), VortexErrorKind::MismatchedTypes); } #[test] @@ -53,7 +53,7 @@ mod tests { let decimal_dtype = crate::dtype::DecimalDType::new(10, 2); let result = DecimalArray::try_new(buffer, decimal_dtype, validity); - assert!(matches!(result, Err(VortexError::InvalidArgument(_, _)))); + assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); } #[test] @@ -63,7 +63,7 @@ mod tests { let validity = Validity::from_iter([true, false]); // Length 2, buffer is length 3. let result = PrimitiveArray::try_new(buffer, validity); - assert!(matches!(result, Err(VortexError::InvalidArgument(_, _)))); + assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); } #[test] @@ -74,7 +74,7 @@ mod tests { let offsets = buffer![0i64, 2, 5].into_array(); // 5 > 3. let result = ListArray::try_new(elements, offsets, Validity::NonNullable, &mut ctx); - assert!(matches!(result, Err(VortexError::InvalidArgument(_, _)))); + assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); } #[test] @@ -83,7 +83,7 @@ mod tests { let elements = buffer![1i32, 2, 3, 4, 5].into_array(); // 5 elements. let result = FixedSizeListArray::try_new(elements, 2, Validity::NonNullable, 3); // Expects 2 * 3 = 6. - assert!(matches!(result, Err(VortexError::InvalidArgument(_, _)))); + assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); } #[test] @@ -122,7 +122,7 @@ mod tests { &mut SESSION.create_execution_ctx(), ); - assert!(matches!(result, Err(VortexError::InvalidArgument(_, _)))); + assert_eq!(result.unwrap_err().kind(), VortexErrorKind::OutOfBounds); } #[test] @@ -134,7 +134,7 @@ mod tests { let names = ["a", "b"]; let result = StructArray::try_new(names.into(), fields, 3, Validity::NonNullable); - assert!(matches!(result, Err(VortexError::InvalidArgument(_, _)))); + assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); } #[rstest::rstest] diff --git a/vortex-array/src/arrays/varbin/array.rs b/vortex-array/src/arrays/varbin/array.rs index e9f4e913955..cfcdcfe412b 100644 --- a/vortex-array/src/arrays/varbin/array.rs +++ b/vortex-array/src/arrays/varbin/array.rs @@ -236,13 +236,15 @@ impl VarBinData { // Check offsets are non-nullable integer vortex_ensure!( offsets.dtype().is_int() && !offsets.dtype().is_nullable(), - MismatchedTypes: "non nullable int", offsets.dtype() + MismatchedTypes: "expected type: non nullable int but instead got {}", + offsets.dtype() ); // Check dtype is Binary or Utf8 vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - MismatchedTypes: "utf8 or binary", dtype + MismatchedTypes: "expected type: utf8 or binary but instead got {}", + dtype ); // Check nullability matches @@ -264,7 +266,7 @@ impl VarBinData { vortex_ensure_eq!( validity_len, offsets.len() - 1, - "Validity length doesn't match array length", + InvalidArgument: "Validity length doesn't match array length", ); } @@ -352,7 +354,7 @@ impl VarBinData { #[expect(clippy::unwrap_used)] // run validation using `compat` package to get more detailed error message let err = simdutf8::compat::from_utf8(string_bytes).unwrap_err(); - vortex_err!("invalid utf-8: {err} at index {i}") + vortex_err!(InvalidArgument: "invalid utf-8: {err} at index {i}") })?; Ok(()) }; diff --git a/vortex-array/src/arrays/varbin/builder.rs b/vortex-array/src/arrays/varbin/builder.rs index 47e7e4e025d..b2a78511b3c 100644 --- a/vortex-array/src/arrays/varbin/builder.rs +++ b/vortex-array/src/arrays/varbin/builder.rs @@ -157,7 +157,7 @@ impl VarBinBuilder { pub fn append_n_values(&mut self, value: impl AsRef<[u8]>, n: usize) -> VortexResult<()> { let value = value.as_ref(); let Some(num_bytes) = value.len().checked_mul(n) else { - vortex_bail!("Byte count overflow: {} values of {} bytes", n, value.len()); + vortex_bail!(Overflow: "Byte count overflow: {} values of {} bytes", n, value.len()); }; // Checking the total up front is what keeps `push_value` below from panicking. self.check_offset_limit(self.data.len(), num_bytes)?; @@ -197,7 +197,7 @@ impl VarBinBuilder { vortex_ensure_eq!( scalar.dtype(), &self.dtype, - "VarBinBuilder scalar dtype does not match builder dtype", + MismatchedTypes: "VarBinBuilder scalar dtype does not match builder dtype", ); match &self.dtype { DType::Utf8(_) => match scalar.as_utf8().value() { @@ -208,7 +208,9 @@ impl VarBinBuilder { Some(value) => self.append_n_values(value, n)?, None => self.push_nulls(n), }, - dtype => vortex_bail!("VarBinBuilder cannot append scalar of dtype {dtype}"), + dtype => { + vortex_bail!(MismatchedTypes: "VarBinBuilder cannot append scalar of dtype {dtype}") + } } Ok(()) } @@ -278,7 +280,7 @@ impl VarBinBuilder { usize: AsPrimitive, { let Some(capacity) = num_bytes.checked_add(slack) else { - vortex_bail!("Decoded size overflow: {num_bytes} + {slack}"); + vortex_bail!(Overflow: "Decoded size overflow: {num_bytes} + {slack}"); }; // Checked before decoding: an `i32` builder that the decoded bytes would overflow should // not pay for the decompression first. @@ -290,7 +292,7 @@ impl VarBinBuilder { vortex_ensure_eq!( written, num_bytes, - "Decoded byte count does not match expected byte count", + InvalidArgument: "Decoded byte count does not match expected byte count", ); // The decoded bytes live in spare capacity until `set_len` below, so an invalid `lengths` @@ -492,12 +494,12 @@ impl VarBinBuilder { let mut previous = 0usize; for slot in spare.iter_mut() { let Some(end) = end_offsets.next() else { - vortex_bail!("End offset count is less than the validity length {count}"); + vortex_bail!(InvalidArgument: "End offset count is less than the validity length {count}"); }; let end = end.as_(); vortex_ensure!( end >= previous && end <= num_bytes, - "End offsets must be monotonically increasing within {num_bytes} bytes, \ + InvalidArgument: "End offsets must be monotonically increasing within {num_bytes} bytes, \ got {end} after {previous}" ); slot.write((data_start + end).as_()); @@ -505,12 +507,12 @@ impl VarBinBuilder { } vortex_ensure!( end_offsets.next().is_none(), - "End offset count exceeds the validity length {count}" + InvalidArgument: "End offset count exceeds the validity length {count}" ); vortex_ensure_eq!( previous, num_bytes, - "Final end offset does not match the value byte count", + InvalidArgument: "Final end offset does not match the value byte count", ); // SAFETY: the loop initialized the first `count` spare slots. @@ -572,7 +574,7 @@ impl VarBinBuilder { vortex_ensure_eq!( data.len(), data_start + num_bytes, - "Value slices byte count does not match expected byte count", + InvalidArgument: "Value slices byte count does not match expected byte count", ); // SAFETY: every branch above initialized all `count` spare slots. @@ -583,11 +585,11 @@ impl VarBinBuilder { /// Checks that an offset past `num_bytes` more bytes is representable as an `O`. fn check_offset_limit(&self, data_start: usize, num_bytes: usize) -> VortexResult<()> { let Some(limit) = data_start.checked_add(num_bytes) else { - vortex_bail!("Byte offset overflow: {data_start} + {num_bytes}"); + vortex_bail!(Overflow: "Byte offset overflow: {data_start} + {num_bytes}"); }; vortex_ensure!( u64::try_from(limit).is_ok_and(|limit| limit <= O::max_value_as_u64()), - "Byte offset {limit} does not fit in {}", + Overflow: "Byte offset {limit} does not fit in {}", std::any::type_name::() ); Ok(()) @@ -700,7 +702,7 @@ macro_rules! __match_varbin_builder_arms { #[inline(never)] fn offset_overflow(data_len: usize, value_len: usize, offset_type: &'static str) -> ! { vortex_panic!( - "Failed to convert sum of {data_len} and {value_len} to offset of type {offset_type}" + Overflow: "Failed to convert sum of {data_len} and {value_len} to offset of type {offset_type}" ) } diff --git a/vortex-array/src/arrays/varbin/compute/compare.rs b/vortex-array/src/arrays/varbin/compute/compare.rs index ab2abce91c9..907b97f6be1 100644 --- a/vortex-array/src/arrays/varbin/compute/compare.rs +++ b/vortex-array/src/arrays/varbin/compute/compare.rs @@ -51,7 +51,7 @@ impl CompareKernel for VarBin { .vortex_expect("RHS should not be null") .as_str() .as_bytes(), - _ => vortex_bail!("VarBinArray can only have type of Binary or Utf8"), + _ => vortex_bail!(MismatchedTypes: "VarBinArray can only have type of Binary or Utf8"), }; let buffer = if rhs_bytes.is_empty() { diff --git a/vortex-array/src/arrays/varbin/compute/filter.rs b/vortex-array/src/arrays/varbin/compute/filter.rs index 47f740b46ac..c3399067bd3 100644 --- a/vortex-array/src/arrays/varbin/compute/filter.rs +++ b/vortex-array/src/arrays/varbin/compute/filter.rs @@ -116,13 +116,13 @@ where if valid { let s = offsets[idx + start].to_usize().ok_or_else(|| { vortex_err!( - "Failed to convert offset to usize: {}", + Overflow: "Failed to convert offset to usize: {}", offsets[idx + start] ) })?; let e = offsets[idx + start + 1].to_usize().ok_or_else(|| { vortex_err!( - "Failed to convert offset to usize: {}", + Overflow: "Failed to convert offset to usize: {}", offsets[idx + start + 1] ) })?; @@ -150,12 +150,12 @@ where B: OffsetBuilderPType, usize: AsPrimitive, { - let offset_start = offsets[start] - .to_usize() - .ok_or_else(|| vortex_err!("Failed to convert offset to usize: {}", offsets[start]))?; - let offset_end = offsets[end] - .to_usize() - .ok_or_else(|| vortex_err!("Failed to convert offset to usize: {}", offsets[end]))?; + let offset_start = offsets[start].to_usize().ok_or_else( + || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[start]), + )?; + let offset_end = offsets[end].to_usize().ok_or_else( + || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[end]), + )?; let new_data = &data[offset_start..offset_end]; let new_offsets = offsets[start..end + 1] .iter() @@ -199,12 +199,12 @@ fn filter_select_var_bin_by_index_primitive_offset VortexResult { let value_at = |idx: usize| -> VortexResult<&[u8]> { - let start = offsets[idx] - .to_usize() - .ok_or_else(|| vortex_err!("Failed to convert offset to usize: {}", offsets[idx]))?; - let end = offsets[idx + 1].to_usize().ok_or_else(|| { - vortex_err!("Failed to convert offset to usize: {}", offsets[idx + 1]) - })?; + let start = offsets[idx].to_usize().ok_or_else( + || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[idx]), + )?; + let end = offsets[idx + 1].to_usize().ok_or_else( + || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[idx + 1]), + )?; Ok(&data[start..end]) }; diff --git a/vortex-array/src/arrays/varbin/compute/take.rs b/vortex-array/src/arrays/varbin/compute/take.rs index d6993d18fc8..bde9573261a 100644 --- a/vortex-array/src/arrays/varbin/compute/take.rs +++ b/vortex-array/src/arrays/varbin/compute/take.rs @@ -366,9 +366,9 @@ fn take( let mut current_offset = 0usize; for &idx in indices { - let idx = idx - .to_usize() - .unwrap_or_else(|| vortex_panic!("Failed to convert index to usize: {}", idx)); + let idx = idx.to_usize().unwrap_or_else( + || vortex_panic!(Overflow: "Failed to convert index to usize: {}", idx), + ); let start = offsets[idx]; let stop = offsets[idx + 1]; @@ -381,9 +381,9 @@ fn take( let mut new_data = ByteBufferMut::with_capacity(current_offset); for idx in indices { - let idx = idx - .to_usize() - .unwrap_or_else(|| vortex_panic!("Failed to convert index to usize: {}", idx)); + let idx = idx.to_usize().unwrap_or_else( + || vortex_panic!(Overflow: "Failed to convert index to usize: {}", idx), + ); let start = offsets[idx] .to_usize() .vortex_expect("Failed to cast max offset to usize"); @@ -585,14 +585,13 @@ where S: UnsignedPType, Offset: IntegerPType, { - let computed_len = starts - .len() - .checked_mul(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + let computed_len = starts.len().checked_mul(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; vortex_ensure_eq!( computed_len, output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); let mut new_offsets = Offsets::with_capacity(out_offset_ptype, output_len + 1); @@ -610,24 +609,24 @@ where let byte_end = offset_range[length].as_(); vortex_ensure!( byte_start <= byte_end && byte_end <= data.len(), - "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", + InvalidArgument: "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", data.len() ); for &offset in &offset_range[1..] { let offset = offset.as_(); - let relative = offset.checked_sub(byte_start).ok_or_else(|| { - vortex_err!("VarBin offsets are not monotonic at offset {offset}") - })?; - let output_offset = output_bytes.checked_add(relative).ok_or_else(|| { - vortex_err!("PiecewiseSequence VarBin output byte length overflow") - })?; + let relative = offset.checked_sub(byte_start).ok_or_else( + || vortex_err!(Serde: "VarBin offsets are not monotonic at offset {offset}"), + )?; + let output_offset = output_bytes.checked_add(relative).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), + )?; new_offsets.push(output_offset); } - output_bytes = output_bytes - .checked_add(byte_end - byte_start) - .ok_or_else(|| vortex_err!("PiecewiseSequence VarBin output byte length overflow"))?; + output_bytes = output_bytes.checked_add(byte_end - byte_start).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), + )?; } let mut new_data = ByteBufferMut::with_capacity(output_bytes); @@ -651,7 +650,7 @@ where vortex_ensure_eq!( new_data.len(), output_bytes, - "PiecewiseSequenceArray gathered byte length does not match declared byte length", + AssertionFailed: "PiecewiseSequenceArray gathered byte length does not match declared byte length", ); let offsets = new_offsets.into_array(); @@ -690,29 +689,29 @@ where let byte_end = offset_range[length].as_(); vortex_ensure!( byte_start <= byte_end && byte_end <= data.len(), - "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", + InvalidArgument: "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", data.len() ); for &offset in &offset_range[1..] { let offset = offset.as_(); - let relative = offset.checked_sub(byte_start).ok_or_else(|| { - vortex_err!("VarBin offsets are not monotonic at offset {offset}") - })?; - let output_offset = output_bytes.checked_add(relative).ok_or_else(|| { - vortex_err!("PiecewiseSequence VarBin output byte length overflow") - })?; + let relative = offset.checked_sub(byte_start).ok_or_else( + || vortex_err!(Serde: "VarBin offsets are not monotonic at offset {offset}"), + )?; + let output_offset = output_bytes.checked_add(relative).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), + )?; new_offsets.push(output_offset); } - output_bytes = output_bytes - .checked_add(byte_end - byte_start) - .ok_or_else(|| vortex_err!("PiecewiseSequence VarBin output byte length overflow"))?; + output_bytes = output_bytes.checked_add(byte_end - byte_start).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), + )?; } vortex_ensure_eq!( new_offsets.len(), output_len + 1, - "PiecewiseSequenceArray expanded offsets length does not match declared length plus one", + AssertionFailed: "PiecewiseSequenceArray expanded offsets length does not match declared length plus one", ); let mut new_data = ByteBufferMut::with_capacity(output_bytes); @@ -737,7 +736,7 @@ where vortex_ensure_eq!( new_data.len(), output_bytes, - "PiecewiseSequenceArray gathered byte length does not match declared byte length", + AssertionFailed: "PiecewiseSequenceArray gathered byte length does not match declared byte length", ); let offsets = new_offsets.into_array(); @@ -772,9 +771,9 @@ fn take_nullable( new_offsets.push(current_offset); continue; } - let data_idx_usize = data_idx - .to_usize() - .unwrap_or_else(|| vortex_panic!("Failed to convert index to usize: {}", data_idx)); + let data_idx_usize = data_idx.to_usize().unwrap_or_else( + || vortex_panic!(Overflow: "Failed to convert index to usize: {}", data_idx), + ); if data_validity.value(data_idx_usize) { validity_buffer.append(true); let start = offsets[data_idx_usize]; diff --git a/vortex-array/src/arrays/varbin/mod.rs b/vortex-array/src/arrays/varbin/mod.rs index 6bc9a4eda82..2f3f3cdc2c3 100644 --- a/vortex-array/src/arrays/varbin/mod.rs +++ b/vortex-array/src/arrays/varbin/mod.rs @@ -26,7 +26,6 @@ pub mod builder; use vortex_buffer::BufferString; use vortex_buffer::ByteBuffer; use vortex_error::VortexExpect; -use vortex_error::vortex_err; use crate::dtype::DType; use crate::scalar::Scalar; @@ -35,7 +34,7 @@ use crate::scalar::ScalarValue; pub fn varbin_scalar(value: ByteBuffer, dtype: &DType) -> Scalar { if matches!(dtype, DType::Utf8(_)) { Scalar::try_utf8(value, dtype.nullability()) - .map_err(|err| vortex_err!("Failed to create scalar from utf8 buffer: {}", err)) + .map_err(|err| err.with_context("Failed to create scalar from utf8 buffer")) .vortex_expect("UTF-8 scalar creation should succeed") } else { Scalar::binary(value, dtype.nullability()) diff --git a/vortex-array/src/arrays/varbin/vtable/mod.rs b/vortex-array/src/arrays/varbin/vtable/mod.rs index 74d8812565f..8eae8b91709 100644 --- a/vortex-array/src/arrays/varbin/vtable/mod.rs +++ b/vortex-array/src/arrays/varbin/vtable/mod.rs @@ -96,18 +96,18 @@ impl VTable for VarBin { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), VarBinSlots::COUNT); + vortex_ensure_eq!(slots.len(), VarBinSlots::COUNT, InvalidArgument); let offsets = slots[VarBinSlots::OFFSETS] .as_ref() .vortex_expect("VarBinArray offsets slot"); vortex_ensure_eq!( offsets.len().saturating_sub(1), len, - "VarBinArray length does not match outer length", + InvalidArgument: "VarBinArray length does not match outer length", ); vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - "VarBinArray dtype must be binary or utf8, got {dtype}" + MismatchedTypes: "VarBinArray dtype must be binary or utf8, got {dtype}" ); Ok(()) } @@ -115,14 +115,14 @@ impl VTable for VarBin { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.bytes_handle().clone(), - _ => vortex_panic!("VarBinArray buffer index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "VarBinArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("bytes".to_string()), - _ => vortex_panic!("VarBinArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "VarBinArray buffer_name index {idx} out of bounds"), } } @@ -131,7 +131,7 @@ impl VTable for VarBin { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1); + vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); let mut data = array.data().clone(); data.bytes = buffers[0].clone(); Ok(ArrayParts::new( @@ -172,7 +172,7 @@ impl VTable for VarBin { let validity = children.get(1, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("Expected 1 or 2 children, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 1 or 2 children, got {}", children.len()); }; let offsets = children.get( @@ -182,7 +182,7 @@ impl VTable for VarBin { )?; if buffers.len() != 1 { - vortex_bail!("Expected 1 buffer, got {}", buffers.len()); + vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); } let bytes = buffers[0].clone().try_to_host_sync()?; @@ -229,7 +229,7 @@ impl VTable for VarBin { // The two arms here are every builder a `Utf8`/`Binary` dtype has: all four // `VarBinBuilder` widths above, and `VarBinViewBuilder` below. let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!("append_to_builder for VarBin requires a variable-binary builder") + vortex_bail!(InvalidArgument: "append_to_builder for VarBin requires a variable-binary builder") }; append_to_varbinview(array, builder, ctx) } diff --git a/vortex-array/src/arrays/varbinview/array.rs b/vortex-array/src/arrays/varbinview/array.rs index 32ee555ceca..99c0c1b260e 100644 --- a/vortex-array/src/arrays/varbinview/array.rs +++ b/vortex-array/src/arrays/varbinview/array.rs @@ -257,7 +257,7 @@ impl VarBinViewData { let views_nbytes = views.len(); vortex_ensure!( views_nbytes.is_multiple_of(size_of::()), - "Expected views buffer length ({views_nbytes}) to be a multiple of {}", + InvalidArgument: "Expected views buffer length ({views_nbytes}) to be a multiple of {}", size_of::() ); @@ -265,7 +265,7 @@ impl VarBinViewData { if let Some(host) = views.as_host_opt() { vortex_ensure!( host.is_aligned(Alignment::of::()), - "Views on host must be 16 byte aligned" + InvalidArgument: "Views on host must be 16 byte aligned" ); } @@ -508,18 +508,18 @@ impl VarBinViewData { let end_offset = start_offset.saturating_add(view.size as usize); let buf = buffers.get(buf_index).ok_or_else(|| - vortex_err!(InvalidArgument: "view at index {idx} references invalid buffer: {buf_index} out of bounds for VarBinViewData with {} buffers", + vortex_err!(OutOfBounds: "view at index {idx} references invalid buffer: {buf_index} out of bounds for VarBinViewData with {} buffers", buffers.len()))?; vortex_ensure!( start_offset < buf.len(), - InvalidArgument: "start offset {start_offset} out of bounds for buffer {buf_index} with size {}", + OutOfBounds: "start offset {start_offset} out of bounds for buffer {buf_index} with size {}", buf.len(), ); vortex_ensure!( end_offset <= buf.len(), - InvalidArgument: "end offset {end_offset} out of bounds for buffer {buf_index} with size {}", + OutOfBounds: "end offset {end_offset} out of bounds for buffer {buf_index} with size {}", buf.len(), ); @@ -609,7 +609,7 @@ impl VarBinViewData { pub fn buffer(&self, idx: usize) -> &ByteBuffer { if idx >= self.data_buffers().len() { vortex_panic!( - "{idx} buffer index out of bounds, there are {} buffers", + OutOfBounds: "{idx} buffer index out of bounds, there are {} buffers", self.data_buffers().len() ); } diff --git a/vortex-array/src/arrays/varbinview/compute/fill_null.rs b/vortex-array/src/arrays/varbinview/compute/fill_null.rs index cd3c9bfd10e..929d4cfbbef 100644 --- a/vortex-array/src/arrays/varbinview/compute/fill_null.rs +++ b/vortex-array/src/arrays/varbinview/compute/fill_null.rs @@ -40,7 +40,9 @@ impl FillNullKernel for VarBinView { DType::Binary(_) => fill_value.as_binary().value().cloned(), _ => None, } - .ok_or_else(|| vortex_err!("Fill value must be a non-null utf8 or binary scalar"))?; + .ok_or_else( + || vortex_err!(MismatchedTypes: "Fill value must be a non-null utf8 or binary scalar"), + )?; let Validity::Array(is_valid) = array.validity()? else { unreachable!("checked in entry point"); diff --git a/vortex-array/src/arrays/varbinview/compute/take.rs b/vortex-array/src/arrays/varbinview/compute/take.rs index 77c0ce44d08..659c71e0179 100644 --- a/vortex-array/src/arrays/varbinview/compute/take.rs +++ b/vortex-array/src/arrays/varbinview/compute/take.rs @@ -164,14 +164,13 @@ fn gather_view_slices_constant_length( where S: UnsignedPType, { - let computed_len = starts - .len() - .checked_mul(length) - .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; + let computed_len = starts.len().checked_mul(length).ok_or_else( + || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), + )?; vortex_ensure_eq!( computed_len, output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); let mut views = BufferMut::::with_capacity(output_len); @@ -188,7 +187,7 @@ where vortex_ensure_eq!( views.len(), output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); Ok(views.freeze()) } @@ -218,7 +217,7 @@ where vortex_ensure_eq!( views.len(), output_len, - "PiecewiseSequenceArray expanded length does not match declared length", + AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", ); Ok(views.freeze()) } diff --git a/vortex-array/src/arrays/varbinview/compute/zip.rs b/vortex-array/src/arrays/varbinview/compute/zip.rs index fdcfccbd0d5..529a6e11b84 100644 --- a/vortex-array/src/arrays/varbinview/compute/zip.rs +++ b/vortex-array/src/arrays/varbinview/compute/zip.rs @@ -36,7 +36,7 @@ impl ZipKernel for VarBinView { }; if !if_true.dtype().eq_ignore_nullability(if_false.dtype()) { - vortex_bail!("input arrays to zip must have the same dtype"); + vortex_bail!(MismatchedTypes: "input arrays to zip must have the same dtype"); } let len = if_true.len(); diff --git a/vortex-array/src/arrays/varbinview/tests.rs b/vortex-array/src/arrays/varbinview/tests.rs index 54435775859..d759d1722ab 100644 --- a/vortex-array/src/arrays/varbinview/tests.rs +++ b/vortex-array/src/arrays/varbinview/tests.rs @@ -145,7 +145,7 @@ pub fn deserialize_null_views() -> VortexResult<()> { let decoded = decoded .as_opt::() - .ok_or_else(|| vortex_err!("expected VarBinView"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected VarBinView"))?; assert_eq!(decoded.views()[0], views[0]); assert_eq!(decoded.views()[1], BinaryView::empty_view()); assert_arrays_eq!( diff --git a/vortex-array/src/arrays/varbinview/vtable/mod.rs b/vortex-array/src/arrays/varbinview/vtable/mod.rs index f3d8d4147ed..57e54c33ea7 100644 --- a/vortex-array/src/arrays/varbinview/vtable/mod.rs +++ b/vortex-array/src/arrays/varbinview/vtable/mod.rs @@ -94,15 +94,15 @@ impl VTable for VarBinView { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), VarBinViewSlots::COUNT); + vortex_ensure_eq!(slots.len(), VarBinViewSlots::COUNT, InvalidArgument); vortex_ensure_eq!( data.len(), len, - "VarBinViewArray length does not match outer length", + InvalidArgument: "VarBinViewArray length does not match outer length", ); vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - "VarBinViewArray dtype must be binary or utf8, got {dtype}" + MismatchedTypes: "VarBinViewArray dtype must be binary or utf8, got {dtype}" ); Ok(()) } @@ -114,7 +114,7 @@ impl VTable for VarBinView { } else if idx == ndata { array.views_handle().clone() } else { - vortex_panic!("VarBinViewArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "VarBinViewArray buffer index {idx} out of bounds") } } @@ -125,7 +125,7 @@ impl VTable for VarBinView { } else if idx == ndata { Some("views".to_string()) } else { - vortex_panic!("VarBinViewArray buffer_name index {idx} out of bounds") + vortex_panic!(OutOfBounds: "VarBinViewArray buffer_name index {idx} out of bounds") } } @@ -135,7 +135,7 @@ impl VTable for VarBinView { buffers: &[BufferHandle], ) -> VortexResult> { let Some((views, data_buffers)) = buffers.split_last() else { - vortex_bail!("Expected at least 1 buffer, got 0"); + vortex_bail!(MismatchedTypes: "Expected at least 1 buffer, got 0"); }; let data = VarBinViewData::try_new_handle( views.clone(), @@ -171,12 +171,12 @@ impl VTable for VarBinView { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - "VarBinViewArray expects empty metadata, got {} bytes", + InvalidArgument: "VarBinViewArray expects empty metadata, got {} bytes", metadata.len() ); } let Some((views_handle, data_handles)) = buffers.split_last() else { - vortex_bail!("Expected at least 1 buffer, got 0"); + vortex_bail!(MismatchedTypes: "Expected at least 1 buffer, got 0"); }; let validity = if children.is_empty() { @@ -185,16 +185,16 @@ impl VTable for VarBinView { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!("Expected 0 or 1 children, got {}", children.len()); + vortex_bail!(MismatchedTypes: "Expected 0 or 1 children, got {}", children.len()); }; let views_nbytes = views_handle.len(); let expected_views_nbytes = len .checked_mul(size_of::()) - .ok_or_else(|| vortex_err!("views byte length overflow for len={len}"))?; + .ok_or_else(|| vortex_err!(Overflow: "views byte length overflow for len={len}"))?; if views_nbytes != expected_views_nbytes { vortex_bail!( - "Expected views buffer length {} bytes, got {} bytes", + MismatchedTypes: "Expected views buffer length {} bytes, got {} bytes", expected_views_nbytes, views_nbytes ); @@ -266,7 +266,7 @@ impl VTable for VarBinView { { return result; } - vortex_bail!("append_to_builder for VarBinView requires a variable-binary builder") + vortex_bail!(InvalidArgument: "append_to_builder for VarBinView requires a variable-binary builder") } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/arrays/variant/mod.rs b/vortex-array/src/arrays/variant/mod.rs index 3a44a11019d..7190581337e 100644 --- a/vortex-array/src/arrays/variant/mod.rs +++ b/vortex-array/src/arrays/variant/mod.rs @@ -55,7 +55,7 @@ impl Array { let dtype = core_storage.dtype().clone(); vortex_ensure!( matches!(dtype, DType::Variant(_)), - "VariantArray core_storage dtype must be Variant, found {dtype}" + MismatchedTypes: "VariantArray core_storage dtype must be Variant, found {dtype}" ); let len = core_storage.len(); let stats = core_storage.statistics().to_owned(); @@ -142,7 +142,7 @@ mod tests { fn execute_variant(array: ArrayRef) -> VortexResult { let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(variant) = array.execute::(&mut ctx)? else { - return Err(vortex_err!("expected canonical variant array")); + return Err(vortex_err!(MismatchedTypes: "expected canonical variant array")); }; Ok(variant) } @@ -157,7 +157,7 @@ mod tests { let shredded = array .shredded() - .ok_or_else(|| vortex_err!("expected shredded child"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected shredded child"))?; let mut ctx = SESSION.create_execution_ctx(); let expected_shredded_array = if let Some(values) = expected_shredded .iter() @@ -185,9 +185,9 @@ mod tests { let variant = scalar.as_variant(); match expected { Some(expected) => { - let value = variant - .value() - .ok_or_else(|| vortex_err!("expected non-null variant row"))?; + let value = variant.value().ok_or_else( + || vortex_err!(InvalidArgument: "expected non-null variant row"), + )?; assert_eq!(value.as_primitive().typed_value::(), Some(*expected)); } None => assert!(variant.is_null()), @@ -279,9 +279,9 @@ mod tests { let variant = scalar.as_variant(); match expected { Some(expected) => { - let value = variant - .value() - .ok_or_else(|| vortex_err!("expected non-null variant row"))?; + let value = variant.value().ok_or_else( + || vortex_err!(InvalidArgument: "expected non-null variant row"), + )?; assert_eq!(value.as_primitive().typed_value::(), Some(expected)); } None => assert!(variant.is_null()), diff --git a/vortex-array/src/arrays/variant/vtable/mod.rs b/vortex-array/src/arrays/variant/vtable/mod.rs index 9e07169012a..58955e1a7f7 100644 --- a/vortex-array/src/arrays/variant/vtable/mod.rs +++ b/vortex-array/src/arrays/variant/vtable/mod.rs @@ -73,33 +73,33 @@ impl VTable for Variant { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), VariantSlots::COUNT); + vortex_ensure_eq!(slots.len(), VariantSlots::COUNT, InvalidArgument); vortex_ensure!( slots[VariantSlots::CORE_STORAGE].is_some(), - "VariantArray core_storage slot must be present" + InvalidArgument: "VariantArray core_storage slot must be present" ); let core_storage = slots[VariantSlots::CORE_STORAGE] .as_ref() .vortex_expect("validated core_storage slot presence"); vortex_ensure!( matches!(dtype, DType::Variant(_)), - "Expected Variant DType, got {dtype}" + MismatchedTypes: "Expected Variant DType, got {dtype}" ); vortex_ensure_eq!( core_storage.dtype(), dtype, - "VariantArray core_storage dtype does not match outer dtype", + MismatchedTypes: "VariantArray core_storage dtype does not match outer dtype", ); vortex_ensure_eq!( core_storage.len(), len, - "VariantArray core_storage length does not match outer length", + InvalidArgument: "VariantArray core_storage length does not match outer length", ); if let Some(shredded) = slots[VariantSlots::SHREDDED].as_ref() { vortex_ensure_eq!( shredded.len(), len, - "VariantArray shredded length does not match outer length", + InvalidArgument: "VariantArray shredded length does not match outer length", ); } Ok(()) @@ -110,7 +110,7 @@ impl VTable for Variant { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("VariantArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "VariantArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -149,7 +149,7 @@ impl VTable for Variant { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - "VariantArray expects 0 buffers, got {}", + InvalidArgument: "VariantArray expects 0 buffers, got {}", buffers.len() ); let proto = VariantMetadataProto::decode(metadata)?; @@ -158,9 +158,9 @@ impl VTable for Variant { .as_ref() .map(|dtype| DType::from_proto(dtype, session)) .transpose()?; - vortex_ensure!(matches!(dtype, DType::Variant(_)), "Expected Variant DType"); + vortex_ensure!(matches!(dtype, DType::Variant(_)), MismatchedTypes: "Expected Variant DType"); let expected_children = 1 + usize::from(shredded_dtype.is_some()); - vortex_ensure_eq!(children.len(), expected_children); + vortex_ensure_eq!(children.len(), expected_children, InvalidArgument); let core_storage = children.get(0, dtype, len)?; let shredded = shredded_dtype .map(|dtype| children.get(1, &dtype, len)) @@ -181,7 +181,7 @@ impl VTable for Variant { fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { match VariantSlots::NAMES.get(idx) { Some(name) => (*name).to_string(), - None => vortex_panic!("VariantArray slot_name index {idx} out of bounds"), + None => vortex_panic!(OutOfBounds: "VariantArray slot_name index {idx} out of bounds"), } } diff --git a/vortex-array/src/builders/bool.rs b/vortex-array/src/builders/bool.rs index 7a718e9244b..d6ff316cf35 100644 --- a/vortex-array/src/builders/bool.rs +++ b/vortex-array/src/builders/bool.rs @@ -128,7 +128,7 @@ impl ArrayBuilder for BoolBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "BoolBuilder received a scalar with the wrong dtype" + MismatchedTypes: "BoolBuilder received a scalar with the wrong dtype" ); match scalar.as_bool().value() { diff --git a/vortex-array/src/builders/child.rs b/vortex-array/src/builders/child.rs index 923b7f76114..e28a529e70e 100644 --- a/vortex-array/src/builders/child.rs +++ b/vortex-array/src/builders/child.rs @@ -77,7 +77,7 @@ impl ChildBuilder { vortex_ensure_eq!( array.dtype(), &self.dtype, - "Cannot append an array to a child builder of a different dtype", + MismatchedTypes: "Cannot append an array to a child builder of a different dtype", ); if array.is_empty() { diff --git a/vortex-array/src/builders/decimal.rs b/vortex-array/src/builders/decimal.rs index 2a664f17398..bde9c0798ea 100644 --- a/vortex-array/src/builders/decimal.rs +++ b/vortex-array/src/builders/decimal.rs @@ -191,7 +191,7 @@ impl DecimalBuilder { /// The [`DecimalDType`] of this builder. pub fn decimal_dtype(&self) -> &DecimalDType { let DType::Decimal(decimal_dtype, _) = &self.dtype else { - vortex_panic!("`DecimalBuilder` somehow had dtype {}", self.dtype); + vortex_panic!(AssertionFailed: "`DecimalBuilder` somehow had dtype {}", self.dtype); }; decimal_dtype @@ -229,7 +229,7 @@ impl ArrayBuilder for DecimalBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "DecimalBuilder received a scalar with the wrong dtype" + MismatchedTypes: "DecimalBuilder received a scalar with the wrong dtype" ); match scalar.as_decimal().decimal_value() { @@ -267,7 +267,7 @@ impl DecimalBuffer { ::from(value) .ok_or_else(|| { vortex_err!( - "decimal conversion failure {:?}, type: {:?} to {:?}", + Overflow: "decimal conversion failure {:?}, type: {:?} to {:?}", value, V::DECIMAL_TYPE, T::DECIMAL_TYPE, diff --git a/vortex-array/src/builders/dict/bytes.rs b/vortex-array/src/builders/dict/bytes.rs index 4614181a707..75c1f41a916 100644 --- a/vortex-array/src/builders/dict/bytes.rs +++ b/vortex-array/src/builders/dict/bytes.rs @@ -159,9 +159,9 @@ impl BytesDictBuilder { self.values.extend_from_slice(val); } - let next_code = Code::from_usize(next_code).unwrap_or_else(|| { - vortex_panic!("{next_code} has to fit into {}", Code::PTYPE) - }); + let next_code = Code::from_usize(next_code).unwrap_or_else( + || vortex_panic!(Overflow: "{next_code} has to fit into {}", Code::PTYPE), + ); Some(*vacant.insert(next_code).get()) } } @@ -185,7 +185,7 @@ impl BytesDictBuilder { self.views.push(BinaryView::default()); self.values_nulls.append_false(); let code = Code::from_usize(code) - .unwrap_or_else(|| vortex_panic!("{} has to fit into {}", code, Code::PTYPE)); + .unwrap_or_else(|| vortex_panic!(Overflow: "{} has to fit into {}", code, Code::PTYPE)); self.null_code .set(code) .ok() diff --git a/vortex-array/src/builders/dict/mod.rs b/vortex-array/src/builders/dict/mod.rs index 988bf3f7295..318681e2116 100644 --- a/vortex-array/src/builders/dict/mod.rs +++ b/vortex-array/src/builders/dict/mod.rs @@ -70,7 +70,7 @@ pub fn dict_encoder_in( } else if let Some(vb) = array.as_opt::() { bytes_dict_builder(vb.dtype().clone(), constraints, allocator) } else { - vortex_panic!("Can only encode primitive or varbin/view arrays") + vortex_panic!(MismatchedTypes: "Can only encode primitive or varbin/view arrays") }; dict_builder } @@ -100,7 +100,7 @@ pub fn dict_encode(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult u16::MAX as u64, 32 => u32::MAX as u64, 64 => u64::MAX, - width => vortex_panic!("invalid bit_width: {width}"), + width => vortex_panic!(InvalidArgument: "invalid bit_width: {width}"), }); match max_possible_len { max if max <= u8::MAX as u64 => Box::new(PrimitiveDictBuilder::::new_in( @@ -106,7 +106,7 @@ where return None; } let next_code = Code::from_usize(self.values.len()).unwrap_or_else(|| { - vortex_panic!("{} has to fit into {}", self.values.len(), Code::PTYPE) + vortex_panic!(Overflow: "{} has to fit into {}", self.values.len(), Code::PTYPE) }); self.values.push(v); self.values_nulls.append_true(); @@ -126,9 +126,9 @@ where return None; } - let code = Code::from_usize(self.values.len()).unwrap_or_else(|| { - vortex_panic!("{} has to fit into {}", self.values.len(), Code::PTYPE) - }); + let code = Code::from_usize(self.values.len()).unwrap_or_else( + || vortex_panic!(Overflow: "{} has to fit into {}", self.values.len(), Code::PTYPE), + ); self.values.push(T::default()); self.values_nulls.append_false(); self.null_code diff --git a/vortex-array/src/builders/extension.rs b/vortex-array/src/builders/extension.rs index d0edb237b99..48cd073205c 100644 --- a/vortex-array/src/builders/extension.rs +++ b/vortex-array/src/builders/extension.rs @@ -119,7 +119,7 @@ impl ArrayBuilder for ExtensionBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "ExtensionBuilder received a scalar with the wrong dtype" + MismatchedTypes: "ExtensionBuilder received a scalar with the wrong dtype" ); self.append_value(scalar.as_extension()) diff --git a/vortex-array/src/builders/fixed_size_list.rs b/vortex-array/src/builders/fixed_size_list.rs index 0584e138b5b..3c37af51b8b 100644 --- a/vortex-array/src/builders/fixed_size_list.rs +++ b/vortex-array/src/builders/fixed_size_list.rs @@ -122,8 +122,8 @@ impl FixedSizeListBuilder { array: &ArrayRef, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype()); - vortex_ensure_eq!(array.len(), self.list_size() as usize); + vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); + vortex_ensure_eq!(array.len(), self.list_size() as usize, InvalidArgument); self.elements_builder.append_array(array, ctx)?; self.nulls.append_non_null(); @@ -147,8 +147,8 @@ impl FixedSizeListBuilder { n: usize, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype()); - vortex_ensure_eq!(array.len(), self.list_size() as usize); + vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); + vortex_ensure_eq!(array.len(), self.list_size() as usize, InvalidArgument); if n == 0 { return Ok(()); @@ -200,7 +200,7 @@ impl FixedSizeListBuilder { if value.len() != self.list_size() as usize { vortex_bail!( - "Tried to append a `ListScalar` with length {} to a `FixedSizeListScalar` \ + InvalidArgument: "Tried to append a `ListScalar` with length {} to a `FixedSizeListScalar` \ with fixed size of {}", value.len(), self.list_size() @@ -241,7 +241,7 @@ impl FixedSizeListBuilder { pub fn element_dtype(&self) -> &DType { let DType::FixedSizeList(element_dtype, ..) = &self.dtype else { vortex_panic!( - "`FixedSizeListBuilder` has an incorrect dtype: {}", + AssertionFailed: "`FixedSizeListBuilder` has an incorrect dtype: {}", self.dtype ); }; @@ -253,7 +253,7 @@ impl FixedSizeListBuilder { pub fn list_size(&self) -> u32 { let DType::FixedSizeList(_, list_size, _) = self.dtype else { vortex_panic!( - "`FixedSizeListBuilder` has an incorrect dtype: {}", + AssertionFailed: "`FixedSizeListBuilder` has an incorrect dtype: {}", self.dtype ); }; @@ -308,7 +308,7 @@ impl ArrayBuilder for FixedSizeListBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "FixedSizeListBuilder received a scalar with the wrong dtype" + MismatchedTypes: "FixedSizeListBuilder received a scalar with the wrong dtype" ); let list_scalar = scalar.as_list(); diff --git a/vortex-array/src/builders/lazy_null_builder.rs b/vortex-array/src/builders/lazy_null_builder.rs index d46d731cf25..0da2bb36d7f 100644 --- a/vortex-array/src/builders/lazy_null_builder.rs +++ b/vortex-array/src/builders/lazy_null_builder.rs @@ -124,7 +124,7 @@ impl LazyBitBufferBuilder { (NonNullable, None) => Validity::NonNullable, (Nullable, None) => Validity::AllValid, (Nullable, Some(arr)) => Validity::from(arr), - _ => vortex_panic!("Invalid nullability/nulls combination"), + _ => vortex_panic!(AssertionFailed: "Invalid nullability/nulls combination"), } } diff --git a/vortex-array/src/builders/list.rs b/vortex-array/src/builders/list.rs index 7cd7c2ee868..56a7c414850 100644 --- a/vortex-array/src/builders/list.rs +++ b/vortex-array/src/builders/list.rs @@ -137,7 +137,7 @@ impl ListBuilder { array: &ArrayRef, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype()); + vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); self.elements_builder.append_array(array, ctx)?; self.nulls.append_non_null(); @@ -154,7 +154,7 @@ impl ListBuilder { match value.elements() { None => { if self.dtype.nullability() == NonNullable { - vortex_bail!("Cannot append null value to non-nullable list"); + vortex_bail!(InvalidArgument: "Cannot append null value to non-nullable list"); } self.append_null(); } @@ -199,7 +199,7 @@ impl ListBuilder { /// the outer `List`. pub fn element_dtype(&self) -> &DType { let DType::List(element_dtype, _) = &self.dtype else { - vortex_panic!("`ListBuilder` has an incorrect dtype: {}", self.dtype); + vortex_panic!(AssertionFailed: "`ListBuilder` has an incorrect dtype: {}", self.dtype); }; element_dtype @@ -393,7 +393,7 @@ impl ArrayBuilder for ListBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "ListBuilder received a scalar with the wrong dtype" + MismatchedTypes: "ListBuilder received a scalar with the wrong dtype" ); self.append_value(scalar.as_list()) diff --git a/vortex-array/src/builders/listview.rs b/vortex-array/src/builders/listview.rs index bafc1a4c575..475c8b1ba75 100644 --- a/vortex-array/src/builders/listview.rs +++ b/vortex-array/src/builders/listview.rs @@ -170,7 +170,7 @@ impl ListViewBuilder { array: &ArrayRef, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype()); + vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); let curr_offset = self.elements_builder.len(); let num_elements = array.len(); @@ -204,7 +204,7 @@ impl ListViewBuilder { // If `elements` is `None`, then the `value` is a null value. vortex_ensure!( self.dtype.is_nullable(), - "Cannot append null value to non-nullable list builder" + InvalidArgument: "Cannot append null value to non-nullable list builder" ); self.append_null(); return Ok(()); @@ -250,7 +250,7 @@ impl ListViewBuilder { n: usize, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype()); + vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); if n == 0 { return Ok(()); @@ -315,7 +315,7 @@ impl ListViewBuilder { /// the outer `FixedSizeList`. pub fn element_dtype(&self) -> &DType { let DType::List(element_dtype, ..) = &self.dtype else { - vortex_panic!("`ListViewBuilder` has an incorrect dtype: {}", self.dtype); + vortex_panic!(AssertionFailed: "`ListViewBuilder` has an incorrect dtype: {}", self.dtype); }; element_dtype @@ -511,7 +511,7 @@ impl ArrayBuilder for ListViewBuil vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "ListViewBuilder received a scalar with the wrong dtype" + MismatchedTypes: "ListViewBuilder received a scalar with the wrong dtype" ); let list_scalar = scalar.as_list(); diff --git a/vortex-array/src/builders/map.rs b/vortex-array/src/builders/map.rs index ce39bee96bf..3175424741c 100644 --- a/vortex-array/src/builders/map.rs +++ b/vortex-array/src/builders/map.rs @@ -92,7 +92,7 @@ impl MapBuilder { vortex_ensure_eq!( value.dtype(), &self.dtype, - "MapBuilder received a map scalar with the wrong dtype" + MismatchedTypes: "MapBuilder received a map scalar with the wrong dtype" ); if value.is_null() { @@ -126,7 +126,7 @@ impl MapBuilder { vortex_ensure_eq!( array.dtype(), self.dtype(), - "MapBuilder received a map array with the wrong dtype" + MismatchedTypes: "MapBuilder received a map array with the wrong dtype" ); self.entries_builder .append_listview_array(array.entries().as_::(), ctx) @@ -162,7 +162,7 @@ impl ArrayBuilder for MapBuilder vortex_panic!("TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), DType::Variant(_) => { - vortex_panic!("Variant builders are not implemented") + vortex_panic!(NotImplemented: "Variant builders are not implemented") } DType::Extension(ext_dtype) => Box::new(ExtensionBuilder::with_capacity_in( ext_dtype.clone(), diff --git a/vortex-array/src/builders/null.rs b/vortex-array/src/builders/null.rs index 3ca65919cae..a93b0bfc397 100644 --- a/vortex-array/src/builders/null.rs +++ b/vortex-array/src/builders/null.rs @@ -61,7 +61,7 @@ impl ArrayBuilder for NullBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "NullBuilder received a scalar with the wrong dtype" + MismatchedTypes: "NullBuilder received a scalar with the wrong dtype" ); self.append_null(); diff --git a/vortex-array/src/builders/primitive.rs b/vortex-array/src/builders/primitive.rs index 266ac7ce1c8..d97e20aaaf0 100644 --- a/vortex-array/src/builders/primitive.rs +++ b/vortex-array/src/builders/primitive.rs @@ -202,7 +202,7 @@ impl ArrayBuilder for PrimitiveBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "PrimitiveBuilder received a scalar with the wrong dtype" + MismatchedTypes: "PrimitiveBuilder received a scalar with the wrong dtype" ); if let Some(pv) = scalar.as_primitive().pvalue() { diff --git a/vortex-array/src/builders/struct_.rs b/vortex-array/src/builders/struct_.rs index c437c2de024..9a1cdbb9ba9 100644 --- a/vortex-array/src/builders/struct_.rs +++ b/vortex-array/src/builders/struct_.rs @@ -92,12 +92,12 @@ impl StructBuilder { /// Appends a struct `value` to the builder. pub fn append_value(&mut self, struct_scalar: StructScalar) -> VortexResult<()> { if !self.dtype.is_nullable() && struct_scalar.is_null() { - vortex_bail!("Tried to append a null `StructScalar` to a non-nullable struct builder",); + vortex_bail!(InvalidArgument: "Tried to append a null `StructScalar` to a non-nullable struct builder",); } if struct_scalar.struct_fields() != self.struct_fields() { vortex_bail!( - "Tried to append a `StructScalar` with fields {} to a \ + MismatchedTypes: "Tried to append a `StructScalar` with fields {} to a \ struct builder with fields {}", struct_scalar.struct_fields(), self.struct_fields() @@ -145,7 +145,7 @@ impl StructBuilder { /// The [`StructFields`] of this struct builder. pub fn struct_fields(&self) -> &StructFields { let DType::Struct(struct_fields, _) = &self.dtype else { - vortex_panic!("`StructBuilder` somehow had dtype {}", self.dtype); + vortex_panic!(AssertionFailed: "`StructBuilder` somehow had dtype {}", self.dtype); }; struct_fields @@ -207,7 +207,7 @@ impl ArrayBuilder for StructBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "StructBuilder received a scalar with the wrong dtype" + MismatchedTypes: "StructBuilder received a scalar with the wrong dtype" ); self.append_value(scalar.as_struct()) diff --git a/vortex-array/src/builders/tests.rs b/vortex-array/src/builders/tests.rs index 0271837c8e5..cf4d224443d 100644 --- a/vortex-array/src/builders/tests.rs +++ b/vortex-array/src/builders/tests.rs @@ -862,7 +862,7 @@ fn create_test_scalars_for_dtype(dtype: &DType, count: usize) -> Vec { .collect(); Scalar::struct_(DType::Struct(fields.clone(), *n), field_values) } - DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), DType::Variant(_) => continue, DType::Extension(ext_dtype) => { // Create extension scalars with storage values. diff --git a/vortex-array/src/builders/validity.rs b/vortex-array/src/builders/validity.rs index 358473b603a..e69239a2433 100644 --- a/vortex-array/src/builders/validity.rs +++ b/vortex-array/src/builders/validity.rs @@ -112,7 +112,7 @@ impl ValidityBuilder { let validity = Validity::concat(runs).vortex_expect("runs is not empty"); if nullability == NonNullable { - vortex_panic!("cannot finish a non-nullable builder holding {validity:?} validity"); + vortex_panic!(AssertionFailed: "cannot finish a non-nullable builder holding {validity:?} validity"); } validity } diff --git a/vortex-array/src/builders/varbinview.rs b/vortex-array/src/builders/varbinview.rs index 8751802aeb0..f17d4a9fb12 100644 --- a/vortex-array/src/builders/varbinview.rs +++ b/vortex-array/src/builders/varbinview.rs @@ -838,7 +838,7 @@ impl ArrayBuilder for VarBinViewBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - "VarBinViewBuilder received a scalar with the wrong dtype" + MismatchedTypes: "VarBinViewBuilder received a scalar with the wrong dtype" ); match self.dtype() { @@ -851,7 +851,7 @@ impl ArrayBuilder for VarBinViewBuilder { None => self.append_null(), }, _ => vortex_bail!( - "VarBinViewBuilder can only handle Utf8 or Binary scalars, got {:?}", + MismatchedTypes: "VarBinViewBuilder can only handle Utf8 or Binary scalars, got {:?}", scalar.dtype() ), } diff --git a/vortex-array/src/canonical.rs b/vortex-array/src/canonical.rs index 4b437da716a..2b36b64cd96 100644 --- a/vortex-array/src/canonical.rs +++ b/vortex-array/src/canonical.rs @@ -312,7 +312,7 @@ impl Canonical { if let Canonical::Null(a) = self { a } else { - vortex_panic!("Cannot get NullArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get NullArray from {:?}", &self) } } @@ -320,7 +320,7 @@ impl Canonical { if let Canonical::Null(a) = self { a } else { - vortex_panic!("Cannot unwrap NullArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap NullArray from {:?}", &self) } } @@ -328,7 +328,7 @@ impl Canonical { if let Canonical::Bool(a) = self { a } else { - vortex_panic!("Cannot get BoolArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get BoolArray from {:?}", &self) } } @@ -336,7 +336,7 @@ impl Canonical { if let Canonical::Bool(a) = self { a } else { - vortex_panic!("Cannot unwrap BoolArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap BoolArray from {:?}", &self) } } @@ -344,7 +344,7 @@ impl Canonical { if let Canonical::Primitive(a) = self { a } else { - vortex_panic!("Cannot get PrimitiveArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get PrimitiveArray from {:?}", &self) } } @@ -352,7 +352,7 @@ impl Canonical { if let Canonical::Primitive(a) = self { a } else { - vortex_panic!("Cannot unwrap PrimitiveArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap PrimitiveArray from {:?}", &self) } } @@ -360,7 +360,7 @@ impl Canonical { if let Canonical::Decimal(a) = self { a } else { - vortex_panic!("Cannot get DecimalArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get DecimalArray from {:?}", &self) } } @@ -368,7 +368,7 @@ impl Canonical { if let Canonical::Decimal(a) = self { a } else { - vortex_panic!("Cannot unwrap DecimalArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap DecimalArray from {:?}", &self) } } @@ -376,7 +376,7 @@ impl Canonical { if let Canonical::VarBinView(a) = self { a } else { - vortex_panic!("Cannot get VarBinViewArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get VarBinViewArray from {:?}", &self) } } @@ -384,7 +384,7 @@ impl Canonical { if let Canonical::VarBinView(a) = self { a } else { - vortex_panic!("Cannot unwrap VarBinViewArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap VarBinViewArray from {:?}", &self) } } @@ -392,7 +392,7 @@ impl Canonical { if let Canonical::List(a) = self { a } else { - vortex_panic!("Cannot get ListArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get ListArray from {:?}", &self) } } @@ -400,7 +400,7 @@ impl Canonical { if let Canonical::List(a) = self { a } else { - vortex_panic!("Cannot unwrap ListArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap ListArray from {:?}", &self) } } @@ -408,7 +408,7 @@ impl Canonical { if let Canonical::Map(a) = self { a } else { - vortex_panic!("Cannot get MapArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get MapArray from {:?}", &self) } } @@ -416,7 +416,7 @@ impl Canonical { if let Canonical::Map(a) = self { a } else { - vortex_panic!("Cannot unwrap MapArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap MapArray from {:?}", &self) } } @@ -424,7 +424,7 @@ impl Canonical { if let Canonical::FixedSizeList(a) = self { a } else { - vortex_panic!("Cannot get FixedSizeListArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get FixedSizeListArray from {:?}", &self) } } @@ -432,7 +432,7 @@ impl Canonical { if let Canonical::FixedSizeList(a) = self { a } else { - vortex_panic!("Cannot unwrap FixedSizeListArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap FixedSizeListArray from {:?}", &self) } } @@ -440,7 +440,7 @@ impl Canonical { if let Canonical::Struct(a) = self { a } else { - vortex_panic!("Cannot get StructArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get StructArray from {:?}", &self) } } @@ -448,7 +448,7 @@ impl Canonical { if let Canonical::Struct(a) = self { a } else { - vortex_panic!("Cannot unwrap StructArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap StructArray from {:?}", &self) } } @@ -457,7 +457,7 @@ impl Canonical { if let Canonical::Union(a) = self { a } else { - vortex_panic!("Cannot get UnionArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get UnionArray from {:?}", &self) } } @@ -466,7 +466,7 @@ impl Canonical { if let Canonical::Union(a) = self { a } else { - vortex_panic!("Cannot unwrap UnionArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap UnionArray from {:?}", &self) } } @@ -474,7 +474,7 @@ impl Canonical { if let Canonical::Extension(a) = self { a } else { - vortex_panic!("Cannot get ExtensionArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot get ExtensionArray from {:?}", &self) } } @@ -482,7 +482,7 @@ impl Canonical { if let Canonical::Extension(a) = self { a } else { - vortex_panic!("Cannot unwrap ExtensionArray from {:?}", &self) + vortex_panic!(MismatchedTypes: "Cannot unwrap ExtensionArray from {:?}", &self) } } } @@ -889,7 +889,7 @@ impl Executable for Buffer { array.validity()?, Validity::NonNullable | Validity::AllValid ), - "Cannot execute to native buffer: array is not all-valid." + InvalidArgument: "Cannot execute to native buffer: array is not all-valid." ); Ok(array.into_buffer()) } @@ -1050,7 +1050,9 @@ impl Executable for VariantArray { Ok(variant_array) => Ok(variant_array), Err(array) => match Canonical::execute(array, ctx)? { Canonical::Variant(variant_array) => Ok(variant_array), - canonical => vortex_panic!("Cannot unwrap VariantArray from {:?}", canonical), + canonical => { + vortex_panic!(MismatchedTypes: "Cannot unwrap VariantArray from {:?}", canonical) + } }, } } @@ -1340,17 +1342,19 @@ mod tests { .execute::(&mut ctx)? .0 else { - return Err(vortex_err!("expected canonical variant")); + return Err(vortex_err!(MismatchedTypes: "expected canonical variant")); }; let nested_variant = canonical .shredded() .and_then(|shredded| shredded.as_opt::()) - .ok_or_else(|| vortex_err!("expected nested variant shredded child"))?; + .ok_or_else( + || vortex_err!(InvalidArgument: "expected nested variant shredded child"), + )?; let nested_struct = nested_variant .shredded() .and_then(|shredded| shredded.as_opt::()) - .ok_or_else(|| vortex_err!("expected nested struct shredded child"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected nested struct shredded child"))?; let value = nested_struct.unmasked_field_by_name("value")?; assert!(value.is::()); diff --git a/vortex-array/src/compute/conformance/binary_numeric.rs b/vortex-array/src/compute/conformance/binary_numeric.rs index 29f3c3a6531..acbf0a8c97a 100644 --- a/vortex-array/src/compute/conformance/binary_numeric.rs +++ b/vortex-array/src/compute/conformance/binary_numeric.rs @@ -140,7 +140,7 @@ pub fn test_binary_numeric_array(array: &ArrayRef, ctx: &mut ExecutionCtx) { test_binary_numeric_conformance_decimal(array, *decimal_dtype, ctx) } dtype => vortex_panic!( - "Binary numeric tests are only supported for primitive and decimal types, got {dtype}", + NotImplemented: "Binary numeric tests are only supported for primitive and decimal types, got {dtype}", ), } } @@ -327,8 +327,9 @@ fn assert_decimal_results( let result = result.unwrap_or_else(|err| { vortex_panic!( + err, "Decimal binary numeric operation unexpectedly failed for encoding {}: \ - {operator:?} {scalar} (lhs_is_array: {lhs_is_array}): {err}", + {operator:?} {scalar} (lhs_is_array: {lhs_is_array})", array.encoding_id(), ) }); @@ -376,7 +377,7 @@ fn test_binary_numeric_edge_cases(array: &ArrayRef, ctx: &mut ExecutionCtx) { PType::F64 => test_binary_numeric_edge_cases_float::(array, ctx), }, dtype => vortex_panic!( - "Binary numeric edge case tests are only supported for primitive numeric types, got {dtype}" + NotImplemented: "Binary numeric edge case tests are only supported for primitive numeric types, got {dtype}" ), } } diff --git a/vortex-array/src/compute/conformance/cast.rs b/vortex-array/src/compute/conformance/cast.rs index 32d194edf41..bb4527564bd 100644 --- a/vortex-array/src/compute/conformance/cast.rs +++ b/vortex-array/src/compute/conformance/cast.rs @@ -172,7 +172,7 @@ fn test_cast_to_non_nullable(array: &ArrayRef, ctx: &mut ExecutionCtx) { .err() .unwrap_or_else(|| { vortex_panic!( - "arrays with nulls should error when casting to non-nullable {}", + AssertionFailed: "arrays with nulls should error when casting to non-nullable {}", array, ) }); @@ -273,7 +273,7 @@ fn test_cast_to_primitive( .err() .unwrap_or_else(|| { vortex_panic!( - "Cast must fail because some values are out of bounds. {} {:?} {:?} {} {}", + AssertionFailed: "Cast must fail because some values are out of bounds. {} {:?} {:?} {} {}", target_ptype, min, max, @@ -288,7 +288,8 @@ fn test_cast_to_primitive( let target_dtype = DType::Primitive(target_ptype, array.dtype().nullability()); let casted = cast_and_execute(array, target_dtype.clone(), ctx).unwrap_or_else(|e| { vortex_panic!( - "Cast must succeed because all values are within bounds. {} {}: {e}", + e, + "Cast must succeed because all values are within bounds. {} {}", target_ptype, array.display_values(ctx), ) diff --git a/vortex-array/src/compute/conformance/consistency.rs b/vortex-array/src/compute/conformance/consistency.rs index 6d1b919e51d..f07fc87f019 100644 --- a/vortex-array/src/compute/conformance/consistency.rs +++ b/vortex-array/src/compute/conformance/consistency.rs @@ -1046,8 +1046,10 @@ fn slice_cast_targets(dtype: &DType) -> Vec { }; vec![DType::Struct(fields.clone(), opposite)] } - DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), - DType::Variant(_) => vortex_panic!("Variant conformance casting is not implemented"), + DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Variant(_) => { + vortex_panic!(NotImplemented: "Variant conformance casting is not implemented") + } DType::Extension(_) => vec![], // Extension types typically only cast to themselves } } diff --git a/vortex-array/src/dtype/decimal/mod.rs b/vortex-array/src/dtype/decimal/mod.rs index 10396eab24d..2de3eb90bcc 100644 --- a/vortex-array/src/dtype/decimal/mod.rs +++ b/vortex-array/src/dtype/decimal/mod.rs @@ -48,26 +48,26 @@ impl DecimalDType { pub fn try_new(precision: u8, scale: i8) -> VortexResult { let precision = NonZero::new(precision).ok_or_else(|| { vortex_err!( - "decimal precision must be between 1 and {} (inclusive)", + InvalidArgument: "decimal precision must be between 1 and {} (inclusive)", MAX_PRECISION ) })?; if precision.get() > MAX_PRECISION { vortex_bail!( - "decimal precision {} exceeds MAX_PRECISION {}", + InvalidArgument: "decimal precision {} exceeds MAX_PRECISION {}", precision, MAX_PRECISION ); } if scale > MAX_SCALE { - vortex_bail!("decimal scale {} exceeds MAX_SCALE {}", scale, MAX_SCALE); + vortex_bail!(InvalidArgument: "decimal scale {} exceeds MAX_SCALE {}", scale, MAX_SCALE); } if scale > 0 && scale as u8 > precision.get() { vortex_bail!( - "decimal scale {} is greater than precision {}", + InvalidArgument: "decimal scale {} is greater than precision {}", scale, precision ); @@ -122,7 +122,7 @@ impl TryFrom<&DType> for DecimalDType { if let DType::Decimal(dt, _) = value { Ok(*dt) } else { - vortex_bail!("Cannot convert DType {value} into DecimalType") + vortex_bail!(MismatchedTypes: "Cannot convert DType {value} into DecimalType") } } } diff --git a/vortex-array/src/dtype/decimal/precision.rs b/vortex-array/src/dtype/decimal/precision.rs index 9785828b2f6..136a6d5bcd4 100644 --- a/vortex-array/src/dtype/decimal/precision.rs +++ b/vortex-array/src/dtype/decimal/precision.rs @@ -49,23 +49,23 @@ impl PrecisionScale { pub fn try_new(precision: u8, scale: i8) -> VortexResult { let precision = NonZero::new(precision).ok_or_else(|| { vortex_err!( - "precision cannot be 0, has to be between [1, {}]", + InvalidArgument: "precision cannot be 0, has to be between [1, {}]", D::MAX_PRECISION ) })?; if precision.get() > D::MAX_PRECISION { vortex_bail!( - "Precision {} is greater than max {}", + InvalidArgument: "Precision {} is greater than max {}", precision, D::MAX_PRECISION ); } if scale > D::MAX_SCALE { - vortex_bail!("Scale {} is greater than max {}", scale, D::MAX_SCALE); + vortex_bail!(InvalidArgument: "Scale {} is greater than max {}", scale, D::MAX_SCALE); } if scale > 0 && scale as u8 > precision.get() { - vortex_bail!("Scale {} is greater than precision {}", scale, precision); + vortex_bail!(InvalidArgument: "Scale {} is greater than precision {}", scale, precision); } Ok(Self { precision, diff --git a/vortex-array/src/dtype/decimal/types.rs b/vortex-array/src/dtype/decimal/types.rs index 4aec9a8fb5b..8435e200a33 100644 --- a/vortex-array/src/dtype/decimal/types.rs +++ b/vortex-array/src/dtype/decimal/types.rs @@ -256,7 +256,9 @@ impl TryFrom for DecimalType { | PType::U64 | PType::F16 | PType::F32 - | PType::F64) => vortex_bail!("cannot convert ptype {p} to DecimalType"), + | PType::F64) => { + vortex_bail!(MismatchedTypes: "cannot convert ptype {p} to DecimalType") + } }) } } diff --git a/vortex-array/src/dtype/dtype_impl.rs b/vortex-array/src/dtype/dtype_impl.rs index 27d083edff8..192f7a8a30d 100644 --- a/vortex-array/src/dtype/dtype_impl.rs +++ b/vortex-array/src/dtype/dtype_impl.rs @@ -91,7 +91,7 @@ impl DType { pub fn with_nullability(&self, nullability: Nullability) -> Self { match self { Null if nullability == Nullability::NonNullable => { - vortex_panic!("DType::Null cannot be made non-nullable") + vortex_panic!(InvalidArgument: "DType::Null cannot be made non-nullable") } Null => Null, Bool(_) => Bool(nullability), @@ -210,7 +210,7 @@ impl DType { if let Primitive(ptype, _) = self { *ptype } else { - vortex_panic!("DType {self} is not a primitive type") + vortex_panic!(MismatchedTypes: "DType {self} is not a primitive type") } } @@ -448,7 +448,7 @@ impl DType { if let Struct(f, _) = self { return f; } - vortex_panic!("DType is not a Struct") + vortex_panic!(MismatchedTypes: "DType is not a Struct") } /// Owned version of [Self::as_struct_fields]. @@ -456,7 +456,7 @@ impl DType { if let Struct(f, _) = self { return f; } - vortex_panic!("DType is not a Struct") + vortex_panic!(MismatchedTypes: "DType is not a Struct") } /// Get the `StructDType` if `self` is a `StructDType`, otherwise `None` @@ -501,7 +501,7 @@ impl DType { /// Downcast a `DType` to an `ExtDType` pub fn as_extension(&self) -> &ExtDTypeRef { let Extension(ext) = self else { - vortex_panic!("DType is not an Extension") + vortex_panic!(MismatchedTypes: "DType is not an Extension") }; ext } diff --git a/vortex-array/src/dtype/extension/erased.rs b/vortex-array/src/dtype/extension/erased.rs index b2f49974247..8cd55baac27 100644 --- a/vortex-array/src/dtype/extension/erased.rs +++ b/vortex-array/src/dtype/extension/erased.rs @@ -152,7 +152,7 @@ impl ExtDTypeRef { self.try_downcast::() .map_err(|this| { vortex_err!( - "Failed to downcast ExtDTypeRef {} to {}", + MismatchedTypes: "Failed to downcast ExtDTypeRef {} to {}", this.0.id(), type_name::(), ) diff --git a/vortex-array/src/dtype/field_mask.rs b/vortex-array/src/dtype/field_mask.rs index 7920746f830..b7c770f7d80 100644 --- a/vortex-array/src/dtype/field_mask.rs +++ b/vortex-array/src/dtype/field_mask.rs @@ -40,7 +40,7 @@ impl FieldMask { if let Some(stepped_fp) = fp.step_into() { Ok(FieldMask::Exact(stepped_fp)) } else { - vortex_bail!("Cannot step into exact root field path"); + vortex_bail!(InvalidArgument: "Cannot step into exact root field path"); } } } @@ -49,7 +49,9 @@ impl FieldMask { /// Returns the first field explicit select mask, if there is one, failing if mask = `All`. pub fn starting_field(&self) -> VortexResult> { match self { - FieldMask::All => vortex_bail!("Cannot get starting field from All mask"), + FieldMask::All => { + vortex_bail!(InvalidArgument: "Cannot get starting field from All mask") + } // We know that fp is non-empty FieldMask::Prefix(fp) | FieldMask::Exact(fp) => Ok(fp.parts().first()), } diff --git a/vortex-array/src/dtype/map.rs b/vortex-array/src/dtype/map.rs index e138cea6545..fc4a77e02ff 100644 --- a/vortex-array/src/dtype/map.rs +++ b/vortex-array/src/dtype/map.rs @@ -108,7 +108,7 @@ impl MapDType { ) -> VortexResult { vortex_ensure!( !key.value()?.is_nullable(), - "map key dtype must be non-nullable" + InvalidArgument: "map key dtype must be non-nullable" ); Ok(Self(Arc::new(MapDTypeInner { diff --git a/vortex-array/src/dtype/ptype.rs b/vortex-array/src/dtype/ptype.rs index 03a0a9d1da8..808e0486fd8 100644 --- a/vortex-array/src/dtype/ptype.rs +++ b/vortex-array/src/dtype/ptype.rs @@ -891,7 +891,7 @@ impl TryFrom<&DType> for PType { if let DType::Primitive(p, _) = value { Ok(*p) } else { - vortex_bail!("Cannot convert DType {value} into PType") + vortex_bail!(MismatchedTypes: "Cannot convert DType {value} into PType") } } } @@ -948,7 +948,7 @@ macro_rules! try_from_bytes { impl TryFromBytes for $T { fn try_from_le_bytes(bytes: &[u8]) -> VortexResult { Ok(<$T>::from_le_bytes(bytes.try_into().map_err(|_| { - vortex_err!("Failed to convert bytes into {}", stringify!($T)) + vortex_err!(InvalidArgument: "Failed to convert bytes into {}", stringify!($T)) })?)) } } diff --git a/vortex-array/src/dtype/serde/flatbuffers.rs b/vortex-array/src/dtype/serde/flatbuffers.rs index baabcf10ce4..7467ec435fa 100644 --- a/vortex-array/src/dtype/serde/flatbuffers.rs +++ b/vortex-array/src/dtype/serde/flatbuffers.rs @@ -72,13 +72,13 @@ impl StructFields { ) -> VortexResult { let names: FieldNames = fb_struct .names() - .ok_or_else(|| vortex_err!("failed to parse struct names from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse struct names from flatbuffer"))? .iter() .collect(); let dtypes = fb_struct .dtypes() - .ok_or_else(|| vortex_err!("failed to parse struct dtypes from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse struct dtypes from flatbuffer"))? .iter() .map(|dt| { FieldDType::from(ViewedDType::from_fb_loc( @@ -91,7 +91,7 @@ impl StructFields { if names.len() != dtypes.len() { vortex_bail!( - "length mismatch between struct names ({}) and dtypes ({})", + MismatchedTypes: "length mismatch between struct names ({}) and dtypes ({})", names.len(), dtypes.len() ); @@ -110,13 +110,13 @@ impl UnionVariants { ) -> VortexResult { let names = fb_union .names() - .ok_or_else(|| vortex_err!("failed to parse union names from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse union names from flatbuffer"))? .iter() .collect(); let dtypes = fb_union .dtypes() - .ok_or_else(|| vortex_err!("failed to parse union dtypes from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse union dtypes from flatbuffer"))? .iter() .map(|dt| { FieldDType::from(ViewedDType::from_fb_loc( @@ -129,7 +129,7 @@ impl UnionVariants { let type_ids: Vec = fb_union .type_ids() - .ok_or_else(|| vortex_err!("failed to parse union type_ids from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse union type_ids from flatbuffer"))? .iter() .map(i8::cast_unsigned) .collect(); @@ -147,10 +147,10 @@ impl MapDType { ) -> VortexResult { let key = fb_map .key_type() - .ok_or_else(|| vortex_err!("failed to parse map key type from flatbuffer"))?; + .ok_or_else(|| vortex_err!(Serde: "failed to parse map key type from flatbuffer"))?; let value = fb_map .value_type() - .ok_or_else(|| vortex_err!("failed to parse map value type from flatbuffer"))?; + .ok_or_else(|| vortex_err!(Serde: "failed to parse map value type from flatbuffer"))?; MapDType::try_from_fields( FieldDType::from(ViewedDType::from_fb_loc( @@ -185,23 +185,23 @@ impl TryFrom for DType { fb::Type::Null => Ok(Self::Null), fb::Type::Bool => Ok(Self::Bool( fb.type__as_bool() - .ok_or_else(|| vortex_err!("failed to parse bool from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse bool from flatbuffer"))? .nullable() .into(), )), fb::Type::Primitive => { - let fb_primitive = fb - .type__as_primitive() - .ok_or_else(|| vortex_err!("failed to parse primitive from flatbuffer"))?; + let fb_primitive = fb.type__as_primitive().ok_or_else( + || vortex_err!(Serde: "failed to parse primitive from flatbuffer"), + )?; Ok(Self::Primitive( fb_primitive.ptype().try_into()?, fb_primitive.nullable().into(), )) } fb::Type::Decimal => { - let fb_decimal = fb - .type__as_decimal() - .ok_or_else(|| vortex_err!("failed to parse decimal dtype from flatbuffer"))?; + let fb_decimal = fb.type__as_decimal().ok_or_else( + || vortex_err!(Serde: "failed to parse decimal dtype from flatbuffer"), + )?; Ok(Self::Decimal( DecimalDType::try_new(fb_decimal.precision(), fb_decimal.scale())?, fb_decimal.nullable().into(), @@ -209,24 +209,24 @@ impl TryFrom for DType { } fb::Type::Utf8 => Ok(Self::Utf8( fb.type__as_utf_8() - .ok_or_else(|| vortex_err!("failed to parse utf-8 from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse utf-8 from flatbuffer"))? .nullable() .into(), )), fb::Type::Binary => Ok(Self::Binary( fb.type__as_binary() - .ok_or_else(|| vortex_err!("failed to parse binary from flatbuffer"))? + .ok_or_else(|| vortex_err!(Serde: "failed to parse binary from flatbuffer"))? .nullable() .into(), )), fb::Type::List => { let fb_list = fb .type__as_list() - .ok_or_else(|| vortex_err!("failed to parse list from flatbuffer"))?; + .ok_or_else(|| vortex_err!(Serde: "failed to parse list from flatbuffer"))?; - let list_element = fb_list.element_type().ok_or_else(|| { - vortex_err!("failed to parse list element type from flatbuffer") - })?; + let list_element = fb_list.element_type().ok_or_else( + || vortex_err!(Serde: "failed to parse list element type from flatbuffer"), + )?; let element_dtype = Self::try_from(ViewedDType::from_fb_loc( list_element._tab.loc(), vfdt.buffer().clone(), @@ -238,13 +238,13 @@ impl TryFrom for DType { )) } fb::Type::FixedSizeList => { - let fb_fixed_size_list = fb.type__as_fixed_size_list().ok_or_else(|| { - vortex_err!("failed to parse fixed-size list from flatbuffer") - })?; + let fb_fixed_size_list = fb.type__as_fixed_size_list().ok_or_else( + || vortex_err!(Serde: "failed to parse fixed-size list from flatbuffer"), + )?; - let list_element = fb_fixed_size_list.element_type().ok_or_else(|| { - vortex_err!("failed to parse list element type from flatbuffer") - })?; + let list_element = fb_fixed_size_list.element_type().ok_or_else( + || vortex_err!(Serde: "failed to parse list element type from flatbuffer"), + )?; let element_dtype = Self::try_from(ViewedDType::from_fb_loc( list_element._tab.loc(), vfdt.buffer().clone(), @@ -259,14 +259,14 @@ impl TryFrom for DType { fb::Type::Map => { let fb_map = fb .type__as_map() - .ok_or_else(|| vortex_err!("failed to parse map from flatbuffer"))?; + .ok_or_else(|| vortex_err!(Serde: "failed to parse map from flatbuffer"))?; let map = MapDType::from_fb(fb_map, vfdt.buffer().clone(), vfdt.session.clone())?; Ok(Self::Map(map, fb_map.nullable().into())) } fb::Type::Struct_ => { let fb_struct = fb .type__as_struct_() - .ok_or_else(|| vortex_err!("failed to parse struct from flatbuffer"))?; + .ok_or_else(|| vortex_err!(Serde: "failed to parse struct from flatbuffer"))?; let struct_dtype = StructFields::from_fb(fb_struct, vfdt.buffer().clone(), vfdt.session.clone())?; @@ -275,7 +275,7 @@ impl TryFrom for DType { fb::Type::Union => { let fb_union = fb .type__as_union() - .ok_or_else(|| vortex_err!("failed to parse union from flatbuffer"))?; + .ok_or_else(|| vortex_err!(Serde: "failed to parse union from flatbuffer"))?; let variants = UnionVariants::from_fb(fb_union, vfdt.buffer().clone(), vfdt.session.clone())?; Ok(Self::Union(variants, fb_union.nullable().into())) @@ -283,18 +283,17 @@ impl TryFrom for DType { fb::Type::Variant => { let fb_variant = fb .type__as_variant() - .ok_or_else(|| vortex_err!("failed to parse variant from flatbuffer"))?; + .ok_or_else(|| vortex_err!(Serde: "failed to parse variant from flatbuffer"))?; Ok(Self::Variant(fb_variant.nullable().into())) } fb::Type::Extension => { - let fb_ext = fb - .type__as_extension() - .ok_or_else(|| vortex_err!("failed to parse extension from flatbuffer"))?; + let fb_ext = fb.type__as_extension().ok_or_else( + || vortex_err!(Serde: "failed to parse extension from flatbuffer"), + )?; #[expect(clippy::disallowed_methods, reason = "interning a dynamic id")] - let id = - ExtId::new(fb_ext.id().ok_or_else(|| { - vortex_err!("failed to parse extension id from flatbuffer") - })?); + let id = ExtId::new(fb_ext.id().ok_or_else( + || vortex_err!(Serde: "failed to parse extension id from flatbuffer"), + )?); let storage_dtype = fb_ext.storage_dtype().ok_or_else(|| { vortex_err!( Serde: "storage_dtype must be present on DType fbs message") @@ -305,25 +304,25 @@ impl TryFrom for DType { vfdt.session.clone(), ); let storage_dtype = DType::try_from(storage_view) - .map_err(|e| vortex_err!("failed to create DType from fbs message: {e}"))?; + .map_err(|e| e.with_context("failed to create DType from fbs message"))?; let metadata = fb_ext .metadata() - .ok_or_else(|| { - vortex_err!("failed to parse extension metadata from flatbuffer") - })? + .ok_or_else( + || vortex_err!(Serde: "failed to parse extension metadata from flatbuffer"), + )? .bytes(); let ext_dtype = if let Some(vtable) = vfdt.session.dtypes().registry().get(&id) { vtable.deserialize(metadata, storage_dtype)? } else if vfdt.session.allows_unknown() { ForeignExtDType::from_parts(id, metadata.to_vec(), storage_dtype)? } else { - return Err(vortex_err!("No such DType extension ID: {}", id)); + return Err(vortex_err!(NotFound: "No such DType extension ID: {}", id)); }; Ok(Self::Extension(ext_dtype)) } - _ => Err(vortex_err!("Unknown DType variant")), + _ => Err(vortex_err!(Serde: "Unknown DType variant")), } } } diff --git a/vortex-array/src/dtype/serde/proto.rs b/vortex-array/src/dtype/serde/proto.rs index 99a3fd7801f..67820140d14 100644 --- a/vortex-array/src/dtype/serde/proto.rs +++ b/vortex-array/src/dtype/serde/proto.rs @@ -36,12 +36,12 @@ impl DType { DtypeType::Primitive(p) => Ok(Self::Primitive(p.r#type().into(), p.nullable.into())), DtypeType::Decimal(d) => Ok(Self::Decimal( DecimalDType::try_new( - d.precision - .try_into() - .map_err(|_| vortex_err!("proto precision could not be downcast to u8"))?, - d.scale - .try_into() - .map_err(|_| vortex_err!("proto scale could not be downcast to i8"))?, + d.precision.try_into().map_err( + |_| vortex_err!(Serde: "proto precision could not be downcast to u8"), + )?, + d.scale.try_into().map_err( + |_| vortex_err!(Serde: "proto scale could not be downcast to i8"), + )?, )?, d.nullable.into(), )), @@ -120,7 +120,7 @@ impl DType { .iter() .map(|t| { u8::try_from(*t).map_err(|_| { - vortex_err!("Union type_id {t} somehow does not fit in u8") + vortex_err!(Overflow: "Union type_id {t} somehow does not fit in u8") }) }) .collect::>>()?; @@ -132,9 +132,9 @@ impl DType { #[expect(clippy::disallowed_methods, reason = "interning a dynamic id")] let id = ExtId::new(e.id.as_str()); let storage_dtype = DType::from_proto( - e.storage_dtype - .as_ref() - .ok_or_else(|| vortex_err!("Extension DType missing storage proto"))?, + e.storage_dtype.as_ref().ok_or_else( + || vortex_err!(Serde: "Extension DType missing storage proto"), + )?, session, )?; let ext_dtype = if let Some(vtable) = session.dtypes().registry().get(&id) { diff --git a/vortex-array/src/dtype/struct_.rs b/vortex-array/src/dtype/struct_.rs index 1482f4cee59..464946f9ae7 100644 --- a/vortex-array/src/dtype/struct_.rs +++ b/vortex-array/src/dtype/struct_.rs @@ -327,7 +327,7 @@ impl StructFields { pub fn new(names: FieldNames, dtypes: Vec) -> Self { if names.len() != dtypes.len() { vortex_panic!( - "length mismatch between names ({}) and dtypes ({})", + InvalidArgument: "length mismatch between names ({}) and dtypes ({})", names.len(), dtypes.len() ); @@ -347,7 +347,7 @@ impl StructFields { pub fn from_fields(names: FieldNames, dtypes: Vec) -> Self { if names.len() != dtypes.len() { vortex_panic!( - "length mismatch between names ({}) and dtypes ({})", + InvalidArgument: "length mismatch between names ({}) and dtypes ({})", names.len(), dtypes.len() ); @@ -434,7 +434,7 @@ impl StructFields { for field in projection { let idx = self .find(field) - .ok_or_else(|| vortex_err!("{field} not found"))?; + .ok_or_else(|| vortex_err!(NotFound: "{field} not found"))?; names.push(self.0.names[idx].clone()); dtypes.push(self.0.dtypes[idx].clone()); } @@ -449,7 +449,7 @@ impl StructFields { pub fn without_field(&self, index: usize) -> VortexResult { if index >= self.nfields() { vortex_bail!( - "index {} out of bounds for struct with {} fields", + OutOfBounds: "index {} out of bounds for struct with {} fields", index, self.nfields() ); @@ -491,7 +491,7 @@ impl StructFields { .collect::(); if !names.iter().all_unique() { - vortex_bail!("Can't merge struct fields with duplicate names"); + vortex_bail!(InvalidArgument: "Can't merge struct fields with duplicate names"); } let dtypes = self diff --git a/vortex-array/src/dtype/union.rs b/vortex-array/src/dtype/union.rs index 7174ab2d988..af5b037da2a 100644 --- a/vortex-array/src/dtype/union.rs +++ b/vortex-array/src/dtype/union.rs @@ -171,32 +171,32 @@ impl UnionVariants { vortex_ensure_eq!( names.len(), n_dtypes, - "union names and dtypes length mismatch" + InvalidArgument: "union names and dtypes length mismatch" ); vortex_ensure_eq!( names.len(), type_ids.len(), - "union names and type_ids length mismatch" + InvalidArgument: "union names and type_ids length mismatch" ); vortex_ensure!( !names.is_empty(), - "union must have at least one variant (for now)" + InvalidArgument: "union must have at least one variant (for now)" ); vortex_ensure!( type_ids.iter().all_unique(), - "type_ids must be distinct, got {:?}", + InvalidArgument: "type_ids must be distinct, got {:?}", type_ids ); vortex_ensure!( type_ids.len() <= u8::MAX as usize + 1, - "union supports at most {} variants, got {}", + InvalidArgument: "union supports at most {} variants, got {}", u8::MAX as usize + 1, type_ids.len() ); vortex_ensure!( names.iter().all_unique(), - "union variant names must be distinct, got {:?}", + InvalidArgument: "union variant names must be distinct, got {:?}", names ); @@ -231,7 +231,7 @@ impl UnionVariants { const MAX_VARIANTS: usize = u8::MAX as usize + 1; vortex_ensure!( names.len() <= MAX_VARIANTS, - "union supports at most {} consecutive variants, got {}", + InvalidArgument: "union supports at most {} consecutive variants, got {}", MAX_VARIANTS, names.len() ); diff --git a/vortex-array/src/executor.rs b/vortex-array/src/executor.rs index afc5464b03e..db2b61483ff 100644 --- a/vortex-array/src/executor.rs +++ b/vortex-array/src/executor.rs @@ -53,16 +53,17 @@ use crate::trace_op; /// Returns the maximum number of iterations to attempt when executing an array before giving up and returning /// an error, can be by the `VORTEX_MAX_ITERATIONS` env variables, otherwise defaults to 2^22. pub(crate) fn max_iterations() -> usize { - static MAX_ITERATIONS: LazyLock = - LazyLock::new(|| match std::env::var("VORTEX_MAX_ITERATIONS") { - Ok(val) => val.parse::().unwrap_or_else(|e| { - vortex_panic!("VORTEX_MAX_ITERATIONS is not a valid usize: {e}") + static MAX_ITERATIONS: LazyLock = LazyLock::new(|| { + match std::env::var("VORTEX_MAX_ITERATIONS") { + Ok(val) => val.parse::().unwrap_or_else(|e| { + vortex_panic!(InvalidArgument: "VORTEX_MAX_ITERATIONS is not a valid usize: {e}") }), Err(VarError::NotPresent) => 2 << 21, // 2 ^ 22 Err(VarError::NotUnicode(_)) => { - vortex_panic!("VORTEX_MAX_ITERATIONS is not a valid unicode string") + vortex_panic!(InvalidArgument: "VORTEX_MAX_ITERATIONS is not a valid unicode string") } - }); + } + }); *MAX_ITERATIONS } @@ -337,7 +338,7 @@ impl ArrayRef { } vortex_bail!( - "Exceeded maximum execution iterations ({}) while executing array", + AssertionFailed: "Exceeded maximum execution iterations ({}) while executing array", max_iterations, ) } @@ -632,13 +633,13 @@ fn finalize_done( vortex_ensure_eq!( output.len(), expected_len, - "Result length mismatch for {:?}", + AssertionFailed: "Result length mismatch for {:?}", encoding_id ); vortex_ensure_eq!( output.dtype(), &expected_dtype, - "Executed canonical dtype mismatch for {:?}", + AssertionFailed: "Executed canonical dtype mismatch for {:?}", encoding_id ); } @@ -664,12 +665,12 @@ fn execute_parent_for_child( vortex_ensure_eq!( result.len(), parent.len(), - "Executed parent canonical length mismatch" + AssertionFailed: "Executed parent canonical length mismatch" ); vortex_ensure_eq!( result.dtype(), parent.dtype(), - "Executed parent canonical dtype mismatch" + AssertionFailed: "Executed parent canonical dtype mismatch" ); } log_parent_rewrite(ctx, phase, slot_idx, parent, child, &result); diff --git a/vortex-array/src/expr/bound_expression.rs b/vortex-array/src/expr/bound_expression.rs index 035ca91f404..12a8d9eab14 100644 --- a/vortex-array/src/expr/bound_expression.rs +++ b/vortex-array/src/expr/bound_expression.rs @@ -127,7 +127,7 @@ impl BoundExpression { fn try_new_vec(scalar_fn: ScalarFnRef, children: Vec) -> VortexResult { vortex_ensure!( scalar_fn.signature().arity().matches(children.len()), - "Expression arity mismatch: expected {} children but got {}", + InvalidArgument: "Expression arity mismatch: expected {} children but got {}", scalar_fn.signature().arity(), children.len() ); @@ -155,7 +155,7 @@ impl BoundExpression { let BoundExpression::Scalar { scalar_fn, .. } = &self else { vortex_ensure!( children.is_empty(), - "Root expression cannot have {} children", + InvalidArgument: "Root expression cannot have {} children", children.len() ); return Ok(self); diff --git a/vortex-array/src/expr/expression.rs b/vortex-array/src/expr/expression.rs index ded8e2c87d7..0a7e105a0de 100644 --- a/vortex-array/src/expr/expression.rs +++ b/vortex-array/src/expr/expression.rs @@ -63,7 +63,7 @@ impl Expression { vortex_ensure!( scalar_fn.signature().arity().matches(children.len()), - "Expression arity mismatch: expected {} children but got {}", + InvalidArgument: "Expression arity mismatch: expected {} children but got {}", scalar_fn.signature().arity(), children.len() ); @@ -130,7 +130,7 @@ impl Expression { Self::Root => { vortex_ensure!( children.is_empty(), - "Expression arity mismatch: root expects 0 children but got {}", + InvalidArgument: "Expression arity mismatch: root expects 0 children but got {}", children.len() ); Ok(Self::Root) @@ -138,7 +138,7 @@ impl Expression { Self::Variable(name) => { vortex_ensure!( children.is_empty(), - "Expression arity mismatch: variable expects 0 children but got {}", + InvalidArgument: "Expression arity mismatch: variable expects 0 children but got {}", children.len() ); Ok(Self::Variable(name.clone())) @@ -146,7 +146,7 @@ impl Expression { Self::Scalar { scalar_fn, .. } => { vortex_ensure!( scalar_fn.signature().arity().matches(children.len()), - "Expression arity mismatch: expected {} children but got {}", + InvalidArgument: "Expression arity mismatch: expected {} children but got {}", scalar_fn.signature().arity(), children.len() ); @@ -271,7 +271,7 @@ impl Expression { /// The error for a variable that no enclosing lambda declares. pub(crate) fn unbound_variable(name: &FieldName) -> VortexError { - vortex_err!("variable @{name} is not a parameter of an enclosing lambda") + vortex_err!(NotFound: "variable @{name} is not a parameter of an enclosing lambda") } /// The default display implementation for expressions uses the 'SQL'-style format. diff --git a/vortex-array/src/expr/exprs.rs b/vortex-array/src/expr/exprs.rs index 8634ae901b3..430f4863c96 100644 --- a/vortex-array/src/expr/exprs.rs +++ b/vortex-array/src/expr/exprs.rs @@ -267,7 +267,7 @@ pub fn nested_case_when( } let Ok(num_when_then_pairs) = u32::try_from(when_then_pairs.len()) else { - vortex_panic!("nested_case_when has too many when/then pairs"); + vortex_panic!(InvalidArgument: "nested_case_when has too many when/then pairs"); }; let options = CaseWhenOptions { num_when_then_pairs, @@ -287,7 +287,7 @@ pub fn bound_nested_case_when( ); let Ok(num_when_then_pairs) = u32::try_from(when_then_pairs.len()) else { - vortex_panic!("nested_case_when has too many when/then pairs"); + vortex_panic!(InvalidArgument: "nested_case_when has too many when/then pairs"); }; let has_else = else_value.is_some(); let mut children = Vec::with_capacity(when_then_pairs.len() * 2 + usize::from(has_else)); @@ -1216,7 +1216,7 @@ pub fn in_list_of( vortex_ensure!( element.dtype() == &DType::Null || element.dtype().eq_ignore_nullability(&element_dtype), - "IN list element {element} is not of type {element_dtype}" + MismatchedTypes: "IN list element {element} is not of type {element_dtype}" ); element.cast(&element_dtype) }) diff --git a/vortex-array/src/expr/lambda/mod.rs b/vortex-array/src/expr/lambda/mod.rs index 198226622a3..c82ee659034 100644 --- a/vortex-array/src/expr/lambda/mod.rs +++ b/vortex-array/src/expr/lambda/mod.rs @@ -73,12 +73,12 @@ impl Lambda { ) -> VortexResult { let params: FieldNames = params.into_iter().map(Into::into).collect(); if let Some(param) = params.iter().duplicates().next() { - vortex_bail!("lambda parameter {param} is declared more than once"); + vortex_bail!(InvalidArgument: "lambda parameter {param} is declared more than once"); } pre_order_visit_down(&body, |node: &Expression| { vortex_ensure!( !reads_outside_lambda(node, params.as_ref()), - "lambda ({}) can only read its parameters, not {node}; reading anything else is \ + InvalidArgument: "lambda ({}) can only read its parameters, not {node}; reading anything else is \ not supported yet", params.iter().format(", ") ); @@ -138,7 +138,7 @@ impl Lambda { fn param_fields(&self, param_dtypes: &[DType]) -> VortexResult { vortex_ensure!( param_dtypes.len() == self.params.len(), - "lambda {self} needs one dtype per parameter, got {}", + InvalidArgument: "lambda {self} needs one dtype per parameter, got {}", param_dtypes.len() ); Ok(StructFields::new( @@ -236,7 +236,7 @@ impl BoundLambda { pub fn evaluate(&self, args: Vec, len: usize) -> VortexResult { vortex_ensure!( args.len() == self.params.nfields(), - "lambda {self} needs one array per parameter, got {}", + InvalidArgument: "lambda {self} needs one array per parameter, got {}", args.len() ); for ((name, dtype), arg) in self @@ -248,7 +248,7 @@ impl BoundLambda { { vortex_ensure!( arg.dtype() == &dtype, - "lambda {self}: parameter {name} is bound to {dtype}, not {}", + MismatchedTypes: "lambda {self}: parameter {name} is bound to {dtype}, not {}", arg.dtype() ); } diff --git a/vortex-array/src/expr/lambda/tests.rs b/vortex-array/src/expr/lambda/tests.rs index d09592bdf11..47adba0a7c2 100644 --- a/vortex-array/src/expr/lambda/tests.rs +++ b/vortex-array/src/expr/lambda/tests.rs @@ -102,7 +102,7 @@ impl ScalarFnVTable for Apply { ApplyOptions::Bound(lambda) => { vortex_ensure!( lambda.is_bound_to(args), - "{lambda} is bound to other dtypes" + AssertionFailed: "{lambda} is bound to other dtypes" ); Ok(None) } @@ -116,7 +116,7 @@ impl ScalarFnVTable for Apply { _ctx: &mut ExecutionCtx, ) -> VortexResult { let ApplyOptions::Bound(lambda) = options else { - vortex_bail!("apply's lambda is not bound"); + vortex_bail!(AssertionFailed: "apply's lambda is not bound"); }; lambda.evaluate(vec![args.get(0)?], args.row_count()) } diff --git a/vortex-array/src/expr/optimize.rs b/vortex-array/src/expr/optimize.rs index ac4356892b6..108a36d5799 100644 --- a/vortex-array/src/expr/optimize.rs +++ b/vortex-array/src/expr/optimize.rs @@ -47,7 +47,7 @@ impl BoundExpression { loop { if loop_counter > 100 { vortex_error::vortex_bail!( - "Exceeded maximum optimization iterations (possible infinite loop)" + AssertionFailed: "Exceeded maximum optimization iterations (possible infinite loop)" ); } loop_counter += 1; @@ -204,10 +204,9 @@ mod tests { // Prune rules pattern-match a bare Literal on the comparison RHS; a cast wrapper // silently disables pruning. - let rhs = optimized - .child(1) - .as_opt::() - .ok_or_else(|| vortex_err!("expected a bare literal RHS, got {optimized}"))?; + let rhs = optimized.child(1).as_opt::().ok_or_else( + || vortex_err!(MismatchedTypes: "expected a bare literal RHS, got {optimized}"), + )?; assert_eq!(rhs, &Scalar::primitive(3.0f64, Nullability::NonNullable)); Ok(()) } diff --git a/vortex-array/src/expr/proto.rs b/vortex-array/src/expr/proto.rs index 273bb0d1166..ef0fa41c062 100644 --- a/vortex-array/src/expr/proto.rs +++ b/vortex-array/src/expr/proto.rs @@ -44,7 +44,7 @@ impl ExprSerializeProtoExt for Expression { let metadata = scalar_fn.options().serialize()?.ok_or_else(|| { vortex_err!( - "Expression '{}' is not serializable: {}", + Serde: "Expression '{}' is not serializable: {}", scalar_fn.id(), self ) @@ -64,7 +64,7 @@ impl Expression { if expr.id == ROOT_ID { vortex_ensure!( expr.children.is_empty(), - "root expression must have no children, got {}", + Serde: "root expression must have no children, got {}", expr.children.len() ); return Ok(Expression::Root); @@ -83,7 +83,7 @@ impl Expression { } else if session.allows_unknown() { ForeignScalarFnVTable::make_scalar_fn(expr_id, expr.metadata().to_vec(), children.len()) } else { - return Err(vortex_err!("unknown expression id: {}", expr_id)); + return Err(vortex_err!(NotFound: "unknown expression id: {}", expr_id)); }; Expression::try_new(scalar_fn, children) diff --git a/vortex-array/src/expr/traversal/fold.rs b/vortex-array/src/expr/traversal/fold.rs index 5b6c7c94944..44bc12d8196 100644 --- a/vortex-array/src/expr/traversal/fold.rs +++ b/vortex-array/src/expr/traversal/fold.rs @@ -132,10 +132,10 @@ mod tests { if *operator == Operator::Add { Ok(FoldUp::Continue(children[0] + children[1])) } else { - vortex_bail!("not a valid operator") + vortex_bail!(InvalidArgument: "not a valid operator") } } else { - vortex_bail!("not a valid type") + vortex_bail!(InvalidArgument: "not a valid type") } } } diff --git a/vortex-array/src/extension/datetime/date.rs b/vortex-array/src/extension/datetime/date.rs index 1920af1a85f..033643df65d 100644 --- a/vortex-array/src/extension/datetime/date.rs +++ b/vortex-array/src/extension/datetime/date.rs @@ -43,8 +43,9 @@ impl Date { /// /// Note that only Milliseconds and Days time units are supported for Date. pub fn try_new(time_unit: TimeUnit, nullability: Nullability) -> VortexResult> { - let ptype = date_ptype(&time_unit) - .ok_or_else(|| vortex_err!("Date type does not support time unit {}", time_unit))?; + let ptype = date_ptype(&time_unit).ok_or_else( + || vortex_err!(InvalidArgument: "Date type does not support time unit {}", time_unit), + )?; ExtDType::try_new(time_unit, DType::Primitive(ptype, nullability)) } @@ -90,20 +91,21 @@ impl ExtVTable for Date { } fn deserialize_metadata(&self, metadata: &[u8]) -> VortexResult { - vortex_ensure!(!metadata.is_empty(), "Date metadata must not be empty"); + vortex_ensure!(!metadata.is_empty(), Serde: "Date metadata must not be empty"); let tag = metadata[0]; TimeUnit::try_from(tag) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { let metadata = ext_dtype.metadata(); - let ptype = date_ptype(metadata) - .ok_or_else(|| vortex_err!("Date type does not support time unit {}", metadata))?; + let ptype = date_ptype(metadata).ok_or_else( + || vortex_err!(InvalidArgument: "Date type does not support time unit {}", metadata), + )?; vortex_ensure_eq!( ext_dtype.storage_dtype().as_ptype(), ptype, - "Date storage dtype for {} has the wrong ptype", + MismatchedTypes: "Date storage dtype for {} has the wrong ptype", metadata ); @@ -120,7 +122,7 @@ impl ExtVTable for Date { storage_value.as_primitive().cast::()?, )), TimeUnit::Days => Ok(DateValue::Days(storage_value.as_primitive().cast::()?)), - _ => vortex_bail!("Date type does not support time unit {}", metadata), + _ => vortex_bail!(InvalidArgument: "Date type does not support time unit {}", metadata), } } } diff --git a/vortex-array/src/extension/datetime/time.rs b/vortex-array/src/extension/datetime/time.rs index 750a1a183f7..d065dccb62d 100644 --- a/vortex-array/src/extension/datetime/time.rs +++ b/vortex-array/src/extension/datetime/time.rs @@ -38,8 +38,9 @@ impl Time { /// /// Note that Days units are not supported for Time. pub fn try_new(time_unit: TimeUnit, nullability: Nullability) -> VortexResult> { - let ptype = time_ptype(&time_unit) - .ok_or_else(|| vortex_err!("Time type does not support time unit {}", time_unit))?; + let ptype = time_ptype(&time_unit).ok_or_else( + || vortex_err!(InvalidArgument: "Time type does not support time unit {}", time_unit), + )?; ExtDType::try_new(time_unit, DType::Primitive(ptype, nullability)) } @@ -91,20 +92,21 @@ impl ExtVTable for Time { } fn deserialize_metadata(&self, data: &[u8]) -> VortexResult { - vortex_ensure!(!data.is_empty(), "Time metadata must not be empty"); + vortex_ensure!(!data.is_empty(), Serde: "Time metadata must not be empty"); let tag = data[0]; TimeUnit::try_from(tag) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { let metadata = ext_dtype.metadata(); - let ptype = time_ptype(metadata) - .ok_or_else(|| vortex_err!("Time type does not support time unit {}", metadata))?; + let ptype = time_ptype(metadata).ok_or_else( + || vortex_err!(InvalidArgument: "Time type does not support time unit {}", metadata), + )?; vortex_ensure_eq!( ext_dtype.storage_dtype().as_ptype(), ptype, - "Time storage dtype for {} has the wrong ptype", + MismatchedTypes: "Time storage dtype for {} has the wrong ptype", metadata ); @@ -119,13 +121,15 @@ impl ExtVTable for Time { let (span, value) = match *ext_dtype.metadata() { TimeUnit::Seconds => { - let v = i32::try_from(length_of_time) - .map_err(|e| vortex_err!("Time seconds value out of i32 range: {e}"))?; + let v = i32::try_from(length_of_time).map_err( + |e| vortex_err!(Overflow: "Time seconds value out of i32 range: {e}"), + )?; (Span::new().seconds(v), TimeValue::Seconds(v)) } TimeUnit::Milliseconds => { - let v = i32::try_from(length_of_time) - .map_err(|e| vortex_err!("Time milliseconds value out of i32 range: {e}"))?; + let v = i32::try_from(length_of_time).map_err( + |e| vortex_err!(Overflow: "Time milliseconds value out of i32 range: {e}"), + )?; (Span::new().milliseconds(v), TimeValue::Milliseconds(v)) } TimeUnit::Microseconds => ( @@ -136,13 +140,15 @@ impl ExtVTable for Time { Span::new().nanoseconds(length_of_time), TimeValue::Nanoseconds(length_of_time), ), - d @ TimeUnit::Days => vortex_bail!("Time type does not support time unit {d}"), + d @ TimeUnit::Days => { + vortex_bail!(InvalidArgument: "Time type does not support time unit {d}") + } }; // Validate the storage value is within the valid range for Time. jiff::civil::Time::MIN .checked_add(span) - .map_err(|e| vortex_err!("Invalid time scalar: {}", e))?; + .map_err(|e| vortex_err!(InvalidArgument: "Invalid time scalar: {}", e))?; Ok(value) } diff --git a/vortex-array/src/extension/datetime/timestamp.rs b/vortex-array/src/extension/datetime/timestamp.rs index 7c0cdaeb1bb..4dbd0c4cfb4 100644 --- a/vortex-array/src/extension/datetime/timestamp.rs +++ b/vortex-array/src/extension/datetime/timestamp.rs @@ -146,8 +146,9 @@ impl ExtVTable for Timestamp { None => bytes.extend_from_slice(0u16.to_le_bytes().as_slice()), Some(tz) => { let tz_bytes = tz.as_bytes(); - let tz_len = u16::try_from(tz_bytes.len()) - .unwrap_or_else(|err| vortex_panic!("tz did not fit in u16: {}", err)); + let tz_len = u16::try_from(tz_bytes.len()).unwrap_or_else( + |err| vortex_panic!(Overflow: "tz did not fit in u16: {}", err), + ); bytes.extend_from_slice(tz_len.to_le_bytes().as_slice()); bytes.extend_from_slice(tz_bytes); } @@ -159,7 +160,7 @@ impl ExtVTable for Timestamp { fn deserialize_metadata(&self, data: &[u8]) -> VortexResult { vortex_ensure!( data.len() >= 3, - "Timestamp metadata must have at least 3 bytes, got {}", + Serde: "Timestamp metadata must have at least 3 bytes, got {}", data.len() ); @@ -180,13 +181,13 @@ impl ExtVTable for Timestamp { // Attempt to load from len-prefixed bytes vortex_ensure!( data.len() >= 3 + tz_len, - "Timestamp metadata is truncated: declared timezone length {} but only {} bytes available", + Serde: "Timestamp metadata is truncated: declared timezone length {} but only {} bytes available", tz_len, data.len() - 3 ); let tz_bytes = &data[3..3 + tz_len]; let tz: Arc = str::from_utf8(tz_bytes) - .map_err(|e| vortex_err!("timezone is not valid utf8 string: {e}"))? + .map_err(|e| vortex_err!(Serde: "timezone is not valid utf8 string: {e}"))? .to_string() .into(); Ok(TimestampOptions { @@ -198,7 +199,7 @@ impl ExtVTable for Timestamp { fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( matches!(ext_dtype.storage_dtype(), DType::Primitive(PType::I64, _)), - "Timestamp storage dtype must be i64" + MismatchedTypes: "Timestamp storage dtype must be i64" ); Ok(()) } @@ -228,17 +229,19 @@ impl ExtVTable for Timestamp { Span::new().seconds(ts_value), TimestampValue::Seconds(ts_value, tz), ), - TimeUnit::Days => vortex_bail!("Timestamp does not support Days time unit"), + TimeUnit::Days => { + vortex_bail!(InvalidArgument: "Timestamp does not support Days time unit") + } }; // Validate the storage value is within the valid range for Timestamp. jiff::Timestamp::UNIX_EPOCH .checked_add(span) - .map_err(|e| vortex_err!("Invalid timestamp scalar: {}", e))?; + .map_err(|e| vortex_err!(InvalidArgument: "Invalid timestamp scalar: {}", e))?; if let Some(tz) = tz { resolve_time_zone(Some(tz)) - .map_err(|e| vortex_err!("Invalid timezone for timestamp scalar: {}", e))?; + .map_err(|e| e.with_context("Invalid timezone for timestamp scalar"))?; } Ok(value) diff --git a/vortex-array/src/extension/datetime/unit.rs b/vortex-array/src/extension/datetime/unit.rs index 7bc7c03121a..f91025f9f61 100644 --- a/vortex-array/src/extension/datetime/unit.rs +++ b/vortex-array/src/extension/datetime/unit.rs @@ -37,7 +37,7 @@ impl TryFrom for TimeUnit { 2 => Ok(TimeUnit::Milliseconds), 3 => Ok(TimeUnit::Seconds), 4 => Ok(TimeUnit::Days), - _ => vortex_bail!("invalid time unit: {value}u8"), + _ => vortex_bail!(InvalidArgument: "invalid time unit: {value}u8"), } } } diff --git a/vortex-array/src/extension/tests/divisible_int.rs b/vortex-array/src/extension/tests/divisible_int.rs index bb035393a91..8a0d276cfcb 100644 --- a/vortex-array/src/extension/tests/divisible_int.rs +++ b/vortex-array/src/extension/tests/divisible_int.rs @@ -45,19 +45,19 @@ impl ExtVTable for DivisibleInt { } fn deserialize_metadata(&self, data: &[u8]) -> VortexResult { - vortex_ensure_eq!(data.len(), 8, "divisible int metadata has the wrong length"); - let bytes: [u8; 8] = data - .try_into() - .map_err(|_| vortex_error::vortex_err!("divisible int metadata must be 8 bytes"))?; + vortex_ensure_eq!(data.len(), 8, Serde: "divisible int metadata has the wrong length"); + let bytes: [u8; 8] = data.try_into().map_err( + |_| vortex_error::vortex_err!(Serde: "divisible int metadata must be 8 bytes"), + )?; let n = u64::from_le_bytes(bytes); - vortex_ensure!(n > 0, "divisor must be greater than 0"); + vortex_ensure!(n > 0, InvalidArgument: "divisor must be greater than 0"); Ok(Divisor(n)) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( matches!(ext_dtype.storage_dtype(), DType::Primitive(PType::U64, _)), - "divisible int storage dtype must be u64" + MismatchedTypes: "divisible int storage dtype must be u64" ); Ok(()) } @@ -69,7 +69,7 @@ impl ExtVTable for DivisibleInt { let value = storage_value.as_primitive().cast::()?; let metadata = ext_dtype.metadata(); if value % metadata.0 != 0 { - vortex_bail!("{} is not divisible by {}", value, metadata.0); + vortex_bail!(InvalidArgument: "{} is not divisible by {}", value, metadata.0); } Ok(value) } diff --git a/vortex-array/src/mask.rs b/vortex-array/src/mask.rs index 561bb3ecdc1..f6a0b70afd4 100644 --- a/vortex-array/src/mask.rs +++ b/vortex-array/src/mask.rs @@ -24,7 +24,7 @@ impl Executable for Mask { fn execute(array: ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { if !matches!(array.dtype(), DType::Bool(Nullability::NonNullable)) { vortex_bail!( - "Mask array must have boolean(NonNullable) dtype, not {}", + MismatchedTypes: "Mask array must have boolean(NonNullable) dtype, not {}", array.dtype() ); } diff --git a/vortex-array/src/mask_future.rs b/vortex-array/src/mask_future.rs index 802a4bf459d..2e0ebdb7d6b 100644 --- a/vortex-array/src/mask_future.rs +++ b/vortex-array/src/mask_future.rs @@ -33,7 +33,7 @@ impl MaskFuture { .inspect(move |r| { if let Ok(mask) = r && mask.len() != len { - vortex_panic!("MaskFuture created with future that returned mask of incorrect length (expected {}, got {})", len, mask.len()); + vortex_panic!(AssertionFailed: "MaskFuture created with future that returned mask of incorrect length (expected {}, got {})", len, mask.len()); } }) .map_err(Arc::new) diff --git a/vortex-array/src/metadata.rs b/vortex-array/src/metadata.rs index 49baf97a19c..456b07f81d8 100644 --- a/vortex-array/src/metadata.rs +++ b/vortex-array/src/metadata.rs @@ -40,7 +40,7 @@ impl DeserializeMetadata for EmptyMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { if !metadata.is_empty() { - vortex_bail!("EmptyMetadata should not have metadata bytes") + vortex_bail!(AssertionFailed: "EmptyMetadata should not have metadata bytes") } Ok(EmptyMetadata) } diff --git a/vortex-array/src/optimizer/mod.rs b/vortex-array/src/optimizer/mod.rs index 1d9c2c87da0..2aa88c7ad8c 100644 --- a/vortex-array/src/optimizer/mod.rs +++ b/vortex-array/src/optimizer/mod.rs @@ -129,7 +129,7 @@ fn optimize_owned( return Ok((current_array, any_optimizations)); } - vortex_bail!("Exceeded maximum optimization iterations (possible infinite loop)"); + vortex_bail!(AssertionFailed: "Exceeded maximum optimization iterations (possible infinite loop)"); } fn try_session_parent_reduce( diff --git a/vortex-array/src/optimizer/rules.rs b/vortex-array/src/optimizer/rules.rs index 90c5e4a7381..9698fa72807 100644 --- a/vortex-array/src/optimizer/rules.rs +++ b/vortex-array/src/optimizer/rules.rs @@ -194,7 +194,7 @@ impl ParentRuleSet { vortex_error::vortex_ensure_eq!( reduced.len(), parent.len(), - "Reduced array length mismatch from {:?}\nFrom:\n{}\nTo:\n{}", + AssertionFailed: "Reduced array length mismatch from {:?}\nFrom:\n{}\nTo:\n{}", rule, parent.encoding_id(), reduced.encoding_id() @@ -202,7 +202,7 @@ impl ParentRuleSet { vortex_error::vortex_ensure_eq!( reduced.dtype(), parent.dtype(), - "Reduced array dtype mismatch from {:?}\nFrom:\n{}\nTo:\n{}", + AssertionFailed: "Reduced array dtype mismatch from {:?}\nFrom:\n{}\nTo:\n{}", rule, parent.encoding_id(), reduced.encoding_id() diff --git a/vortex-array/src/patches.rs b/vortex-array/src/patches.rs index 3dab7b37c3d..7773f5ef17e 100644 --- a/vortex-array/src/patches.rs +++ b/vortex-array/src/patches.rs @@ -87,7 +87,7 @@ impl PatchesMetadata { #[inline] pub fn len(&self) -> VortexResult { - usize::try_from(self.len).map_err(|_| vortex_err!("len does not fit in usize")) + usize::try_from(self.len).map_err(|_| vortex_err!(Overflow: "len does not fit in usize")) } #[inline] @@ -97,7 +97,8 @@ impl PatchesMetadata { #[inline] pub fn offset(&self) -> VortexResult { - usize::try_from(self.offset).map_err(|_| vortex_err!("offset does not fit in usize")) + usize::try_from(self.offset) + .map_err(|_| vortex_err!(Overflow: "offset does not fit in usize")) } #[inline] @@ -105,7 +106,9 @@ impl PatchesMetadata { self.chunk_offsets_ptype .map(|t| { PType::try_from(t) - .map_err(|e| vortex_err!("invalid i32 value {t} for PType: {}", e)) + .map_err( + |e| vortex_err!(InvalidArgument: "invalid i32 value {t} for PType: {}", e), + ) .map(|ptype| DType::Primitive(ptype, NonNullable)) }) .transpose() @@ -113,12 +116,12 @@ impl PatchesMetadata { #[inline] pub fn indices_dtype(&self) -> VortexResult { - let ptype = PType::try_from(self.indices_ptype).map_err(|e| { - vortex_err!("invalid i32 value {} for PType: {}", self.indices_ptype, e) + let ptype = PType::try_from(self.indices_ptype).map_err(|e| { + vortex_err!(InvalidArgument: "invalid i32 value {} for PType: {}", self.indices_ptype, e) })?; vortex_ensure!( ptype.is_unsigned_int(), - "Patch indices must be unsigned integers" + MismatchedTypes: "Patch indices must be unsigned integers" ); Ok(DType::Primitive(ptype, NonNullable)) } @@ -246,27 +249,27 @@ impl Patches { chunk_offsets: Option, ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_ensure_eq!(indices.len(), values.len()); + vortex_ensure_eq!(indices.len(), values.len(), InvalidArgument); vortex_ensure!( indices.dtype().is_unsigned_int() && !indices.dtype().is_nullable(), - "Patch indices must be non-nullable unsigned integers, got {:?}", + MismatchedTypes: "Patch indices must be non-nullable unsigned integers, got {:?}", indices.dtype() ); vortex_ensure!( indices.len() <= array_len, - "Patch indices must be shorter than the array length" + InvalidArgument: "Patch indices must be shorter than the array length" ); - vortex_ensure!(!indices.is_empty(), "Patch indices must not be empty"); + vortex_ensure!(!indices.is_empty(), InvalidArgument: "Patch indices must not be empty"); // Perform validation of components when they are host-resident. // This is not possible to do eagerly when the data is on GPU memory. if indices.is_host() && values.is_host() { let max = usize::try_from(&indices.execute_scalar(indices.len() - 1, ctx)?) - .map_err(|_| vortex_err!("indices must be a number"))?; + .map_err(|_| vortex_err!(InvalidArgument: "indices must be a number"))?; vortex_ensure!( max - offset < array_len, - "Patch indices {max:?}, offset {offset} are longer than the array length {array_len}" + OutOfBounds: "Patch indices {max:?}, offset {offset} are longer than the array length {array_len}" ); #[cfg(debug_assertions)] @@ -376,14 +379,14 @@ impl Patches { #[inline] pub fn chunk_offset_at(&self, idx: usize, ctx: &mut ExecutionCtx) -> VortexResult { let Some(chunk_offsets) = &self.chunk_offsets else { - vortex_bail!("chunk_offsets must be set to retrieve offset at index") + vortex_bail!(InvalidArgument: "chunk_offsets must be set to retrieve offset at index") }; chunk_offsets .execute_scalar(idx, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("chunk offset does not fit in usize")) + .ok_or_else(|| vortex_err!(Overflow: "chunk offset does not fit in usize")) } /// Returns the number of patches sliced off from the current first chunk. @@ -402,20 +405,20 @@ impl Patches { #[inline] pub fn indices_ptype(&self) -> VortexResult { PType::try_from(self.indices.dtype()) - .map_err(|_| vortex_err!("indices dtype is not primitive")) + .map_err(|_| vortex_err!(MismatchedTypes: "indices dtype is not primitive")) } pub fn to_metadata(&self, len: usize, dtype: &DType) -> VortexResult { if self.indices.len() > len { vortex_bail!( - "Patch indices {} are longer than the array length {}", + InvalidArgument: "Patch indices {} are longer than the array length {}", self.indices.len(), len ); } if self.values.dtype() != dtype { vortex_bail!( - "Patch values dtype {} does not match array dtype {}", + MismatchedTypes: "Patch values dtype {} does not match array dtype {}", self.values.dtype(), dtype ); @@ -485,11 +488,11 @@ impl Patches { ctx: &mut ExecutionCtx, ) -> VortexResult { let Some(chunk_offsets) = &self.chunk_offsets else { - vortex_bail!("chunk_offsets is required to be set") + vortex_bail!(InvalidArgument: "chunk_offsets is required to be set") }; let Some(offset_within_chunk) = self.offset_within_chunk else { - vortex_bail!("offset_within_chunk is required to be set") + vortex_bail!(InvalidArgument: "offset_within_chunk is required to be set") }; if index >= self.array_len() { @@ -506,7 +509,7 @@ impl Patches { .execute_scalar(idx, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("chunk offset does not fit in usize")) + .ok_or_else(|| vortex_err!(Overflow: "chunk offset does not fit in usize")) }; // Patch index offsets are absolute and need to be offset by the first chunk of the current slice. @@ -556,7 +559,7 @@ impl Patches { usize: TryFrom, { let Some(offset_within_chunk) = self.offset_within_chunk else { - vortex_bail!("offset_within_chunk is required to be set") + vortex_bail!(InvalidArgument: "offset_within_chunk is required to be set") }; let chunk_idx = { @@ -574,7 +577,7 @@ impl Patches { // Patch index offsets are absolute and need to be offset by the first chunk of the current slice. let chunk_offset = usize::try_from(chunk_offsets[chunk_idx] - chunk_offsets[0]) - .map_err(|_| vortex_err!("chunk_offset failed to convert to usize"))?; + .map_err(|_| vortex_err!(Overflow: "chunk_offset failed to convert to usize"))?; let patches_start_idx = chunk_offset // Chunk offsets are only sliced off in case the slice is fully @@ -587,7 +590,7 @@ impl Patches { let patches_end_idx = if chunk_idx < chunk_offsets.len() - 1 { usize::try_from(chunk_offsets[chunk_idx + 1] - chunk_offsets[0]) - .map_err(|_| vortex_err!("patches_end_idx failed to convert to usize"))? + .map_err(|_| vortex_err!(Overflow: "patches_end_idx failed to convert to usize"))? .saturating_sub(offset_within_chunk) .min(indices.len()) } else { @@ -615,7 +618,7 @@ impl Patches { .execute_scalar(0, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("index does not fit in usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "index does not fit in usize"))?; Ok(first - self.offset) } @@ -626,7 +629,7 @@ impl Patches { .execute_scalar(self.indices.len() - 1, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("index does not fit in usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "index does not fit in usize"))?; Ok(last - self.offset) } @@ -634,7 +637,7 @@ impl Patches { pub fn filter(&self, mask: &Mask, ctx: &mut ExecutionCtx) -> VortexResult> { if mask.len() != self.array_len { vortex_bail!( - "Filter mask length {} does not match array length {}", + MismatchedTypes: "Filter mask length {} does not match array length {}", mask.len(), self.array_len ); @@ -669,7 +672,7 @@ impl Patches { pub fn mask(&self, mask: &Mask, ctx: &mut ExecutionCtx) -> VortexResult> { if mask.len() != self.array_len { vortex_bail!( - "Filter mask length {} does not match array length {}", + MismatchedTypes: "Filter mask length {} does not match array length {}", mask.len(), self.array_len ); @@ -758,7 +761,7 @@ impl Patches { .execute_scalar(0, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!("chunk offset does not fit in usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "chunk offset does not fit in usize"))?; let parent_chunk_base = self.chunk_offset_at(0, ctx)?; let parent_within = self.offset_within_chunk.unwrap_or(0); Ok(parent_chunk_base + parent_within + slice_start_idx - new_chunk_base) @@ -976,7 +979,7 @@ impl Patches { let values = f(self.values)?; if self.indices.len() != values.len() { vortex_bail!( - "map_values must preserve length: expected {} received {}", + InvalidArgument: "map_values must preserve length: expected {} received {}", self.indices.len(), values.len() ) @@ -1065,7 +1068,7 @@ where for (idx_in_take, &take_idx) in take_indices.iter().enumerate() { let ti = usize::try_from(take_idx) - .map_err(|_| vortex_err!("Failed to convert index to usize"))?; + .map_err(|_| vortex_err!(Overflow: "Failed to convert index to usize"))?; // If we have to take nulls the take index doesn't matter, make it 0 for consistency let is_null = match take_validity.bit_buffer() { @@ -1080,7 +1083,7 @@ where } } else if ti >= min_index && ti <= max_index { let ti_as_i = I::try_from(ti) - .map_err(|_| vortex_err!("take index does not fit in index type"))?; + .map_err(|_| vortex_err!(Overflow: "take index does not fit in index type"))?; if let Some(&value_index) = sparse_index_to_value_index.get(&ti_as_i) { new_sparse_indices.push(idx_in_take as u64); value_indices.push(value_index as u64); @@ -1309,7 +1312,7 @@ fn rank_patches_in_mask_bitmap( fn patch_index_to_usize(patch_index: T, offset: usize) -> VortexResult { Ok(patch_index .to_usize() - .ok_or_else(|| vortex_err!("patch index does not fit in usize"))? + .ok_or_else(|| vortex_err!(Overflow: "patch index does not fit in usize"))? - offset) } diff --git a/vortex-array/src/scalar/cast.rs b/vortex-array/src/scalar/cast.rs index 1a2fd1b1021..c52c22fa5c2 100644 --- a/vortex-array/src/scalar/cast.rs +++ b/vortex-array/src/scalar/cast.rs @@ -37,7 +37,7 @@ impl Scalar { && !source.keys_sorted() { return Err(vortex_err!( - "Cannot cast {} to {target_dtype}: source does not assert sorted map keys", + MismatchedTypes: "Cannot cast {} to {target_dtype}: source does not assert sorted map keys", self.dtype() )); } @@ -47,7 +47,7 @@ impl Scalar { if self.value().is_none() || matches!(self.dtype(), DType::Null) { vortex_ensure!( target_dtype.is_nullable(), - "Cannot cast null to {target_dtype}: target type is non-nullable" + InvalidArgument: "Cannot cast null to {target_dtype}: target type is non-nullable" ); return Scalar::try_new(target_dtype.clone(), self.value().cloned()); @@ -63,24 +63,26 @@ impl Scalar { match &self.dtype() { DType::Null => unreachable!("Handled by the if case above"), DType::Bool(_) => vortex_bail!( - "Cannot cast bool to {target_dtype}: boolean scalars can only be cast to boolean types with different nullability" + MismatchedTypes: "Cannot cast bool to {target_dtype}: boolean scalars can only be cast to boolean types with different nullability" ), DType::Primitive(..) => self.as_primitive().cast(target_dtype), DType::Decimal(..) => self.as_decimal().cast(target_dtype), DType::Utf8(_) => vortex_bail!( - "Cannot cast utf8 to {target_dtype}: UTF-8 scalars can only be cast to UTF-8 types with different nullability" + MismatchedTypes: "Cannot cast utf8 to {target_dtype}: UTF-8 scalars can only be cast to UTF-8 types with different nullability" ), DType::Binary(_) => vortex_bail!( - "Cannot cast binary to {target_dtype}: binary scalars can only be cast to binary types with different nullability" + MismatchedTypes: "Cannot cast binary to {target_dtype}: binary scalars can only be cast to binary types with different nullability" ), DType::List(..) | DType::FixedSizeList(..) => self.as_list().cast(target_dtype), DType::Map(..) => self.as_map().cast(target_dtype), DType::Struct(..) => self.as_struct().cast(target_dtype), DType::Union(..) => vortex_bail!( - "union scalar cast from {} to {target_dtype} is not supported (yet)", + InvalidArgument: "union scalar cast from {} to {target_dtype} is not supported (yet)", self.dtype() ), - DType::Variant(_) => vortex_bail!("Variant scalars can't be cast to {target_dtype}"), + DType::Variant(_) => { + vortex_bail!(NotImplemented: "Variant scalars can't be cast to {target_dtype}") + } DType::Extension(..) => self.as_extension().cast(target_dtype), } } diff --git a/vortex-array/src/scalar/constructor.rs b/vortex-array/src/scalar/constructor.rs index 81f72054696..ab5d8bff117 100644 --- a/vortex-array/src/scalar/constructor.rs +++ b/vortex-array/src/scalar/constructor.rs @@ -170,9 +170,9 @@ impl Scalar { dtype: DType, entries: impl IntoIterator, ) -> VortexResult { - let map = dtype - .as_map_opt() - .ok_or_else(|| vortex_error::vortex_err!("Expected map dtype, found {dtype}"))?; + let map = dtype.as_map_opt().ok_or_else( + || vortex_error::vortex_err!(InvalidArgument: "Expected map dtype, found {dtype}"), + )?; let key_dtype = map.key_dtype(); let value_dtype = map.value_dtype(); @@ -182,13 +182,13 @@ impl Scalar { .map(|(index, (key, value))| { if key.dtype() != &key_dtype { vortex_bail!( - "map entry {index} expected key dtype {key_dtype}, got {}", + MismatchedTypes: "map entry {index} expected key dtype {key_dtype}, got {}", key.dtype() ); } if value.dtype() != &value_dtype { vortex_bail!( - "map entry {index} expected value dtype {value_dtype}, got {}", + MismatchedTypes: "map entry {index} expected value dtype {value_dtype}, got {}", value.dtype() ); } @@ -217,7 +217,7 @@ impl Scalar { .map(|child| { if child.dtype() != &*element_dtype { vortex_panic!( - "tried to create list of {} with values of type {}", + MismatchedTypes: "tried to create list of {} with values of type {}", element_dtype, child.dtype() ); @@ -278,7 +278,7 @@ impl Scalar { ) -> VortexResult { let child_index = variants.tag_to_child_index(type_id).ok_or_else(|| { vortex_err!( - "union type ID {type_id} is not present in {:?}", + NotFound: "union type ID {type_id} is not present in {:?}", variants.type_ids() ) })?; @@ -290,7 +290,7 @@ impl Scalar { vortex_ensure_eq!( child.dtype(), &expected_dtype, - "union type ID {type_id} selects a different child dtype" + MismatchedTypes: "union type ID {type_id} selects a different child dtype" ); Self::try_new( diff --git a/vortex-array/src/scalar/convert/decimal.rs b/vortex-array/src/scalar/convert/decimal.rs index 71134b4be88..4286b167cfd 100644 --- a/vortex-array/src/scalar/convert/decimal.rs +++ b/vortex-array/src/scalar/convert/decimal.rs @@ -36,7 +36,7 @@ macro_rules! decimal_scalar_unpack { None => None, Some(DecimalValue::$arm(v)) => Some(v), v => vortex_error::vortex_bail!( - "Cannot extract decimal {:?} as {}", + MismatchedTypes: "Cannot extract decimal {:?} as {}", v, stringify!($T) ), @@ -49,10 +49,10 @@ macro_rules! decimal_scalar_unpack { fn try_from(value: DecimalScalar) -> Result { match value.decimal_value() { - None => vortex_error::vortex_bail!("Cannot extract value from null decimal"), + None => vortex_error::vortex_bail!(InvalidArgument: "Cannot extract value from null decimal"), Some(DecimalValue::$arm(v)) => Ok(v), v => vortex_error::vortex_bail!( - "Cannot extract decimal {:?} as {}", + MismatchedTypes: "Cannot extract decimal {:?} as {}", v, stringify!($T) ), @@ -96,15 +96,13 @@ impl TryFrom<&Scalar> for DecimalValue { type Error = VortexError; fn try_from(scalar: &Scalar) -> Result { - let decimal_scalar = scalar - .as_decimal_opt() - .ok_or_else(|| vortex_err!("Expected decimal scalar, found {}", scalar.dtype()))?; + let decimal_scalar = scalar.as_decimal_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected decimal scalar, found {}", scalar.dtype()), + )?; - decimal_scalar - .decimal_value() - .as_ref() - .cloned() - .ok_or_else(|| vortex_err!("Cannot extract DecimalValue from null decimal")) + decimal_scalar.decimal_value().as_ref().cloned().ok_or_else( + || vortex_err!(InvalidArgument: "Cannot extract DecimalValue from null decimal"), + ) } } @@ -122,7 +120,7 @@ impl TryFrom<&Scalar> for Option { fn try_from(scalar: &Scalar) -> Result { Ok(scalar .as_decimal_opt() - .ok_or_else(|| vortex_err!("Expected decimal scalar, found {}", scalar.dtype()))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected decimal scalar, found {}", scalar.dtype()))? .decimal_value()) } } diff --git a/vortex-array/src/scalar/convert/from_scalar.rs b/vortex-array/src/scalar/convert/from_scalar.rs index 77b35ad3f28..fc3f010ea9c 100644 --- a/vortex-array/src/scalar/convert/from_scalar.rs +++ b/vortex-array/src/scalar/convert/from_scalar.rs @@ -30,9 +30,9 @@ impl<'a> TryFrom<&'a Scalar> for BoolScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_bool_opt() - .ok_or_else(|| vortex_err!("Expected bool scalar, found {}", value.dtype())) + value.as_bool_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected bool scalar, found {}", value.dtype()), + ) } } @@ -40,9 +40,9 @@ impl<'a> TryFrom<&'a Scalar> for PrimitiveScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_primitive_opt() - .ok_or_else(|| vortex_err!("Expected primitive scalar, found {}", value.dtype())) + value.as_primitive_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected primitive scalar, found {}", value.dtype()), + ) } } @@ -50,9 +50,9 @@ impl<'a> TryFrom<&'a Scalar> for DecimalScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_decimal_opt() - .ok_or_else(|| vortex_err!("Expected decimal scalar, found {}", value.dtype())) + value.as_decimal_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected decimal scalar, found {}", value.dtype()), + ) } } @@ -60,9 +60,9 @@ impl<'a> TryFrom<&'a Scalar> for Utf8Scalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_utf8_opt() - .ok_or_else(|| vortex_err!("Expected utf8 scalar, found {}", value.dtype())) + value.as_utf8_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected utf8 scalar, found {}", value.dtype()), + ) } } @@ -70,9 +70,9 @@ impl<'a> TryFrom<&'a Scalar> for BinaryScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_binary_opt() - .ok_or_else(|| vortex_err!("Expected binary scalar, found {}", value.dtype())) + value.as_binary_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected binary scalar, found {}", value.dtype()), + ) } } @@ -80,9 +80,9 @@ impl<'a> TryFrom<&'a Scalar> for StructScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_struct_opt() - .ok_or_else(|| vortex_err!("Expected struct scalar, found {}", value.dtype())) + value.as_struct_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected struct scalar, found {}", value.dtype()), + ) } } @@ -90,9 +90,9 @@ impl<'a> TryFrom<&'a Scalar> for ListScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_list_opt() - .ok_or_else(|| vortex_err!("Expected list scalar, found {}", value.dtype())) + value.as_list_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected list scalar, found {}", value.dtype()), + ) } } @@ -100,9 +100,9 @@ impl<'a> TryFrom<&'a Scalar> for MapScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_map_opt() - .ok_or_else(|| vortex_err!("Expected map scalar, found {}", value.dtype())) + value.as_map_opt().ok_or_else( + || vortex_err!(InvalidArgument: "Expected map scalar, found {}", value.dtype()), + ) } } @@ -110,9 +110,9 @@ impl<'a> TryFrom<&'a Scalar> for ExtScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value - .as_extension_opt() - .ok_or_else(|| vortex_err!("Expected extension scalar, found {}", value.dtype())) + value.as_extension_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected extension scalar, found {}", value.dtype()), + ) } } @@ -126,9 +126,13 @@ impl TryFrom<&Scalar> for bool { fn try_from(value: &Scalar) -> VortexResult { value .as_bool_opt() - .ok_or_else(|| vortex_err!("Expected bool scalar, found {}", value.dtype()))? + .ok_or_else( + || vortex_err!(MismatchedTypes: "Expected bool scalar, found {}", value.dtype()), + )? .value() - .ok_or_else(|| vortex_err!("Can't extract present value from null scalar")) + .ok_or_else( + || vortex_err!(InvalidArgument: "Can't extract present value from null scalar"), + ) } } @@ -138,7 +142,9 @@ impl TryFrom<&Scalar> for Option { fn try_from(value: &Scalar) -> VortexResult { Ok(value .as_bool_opt() - .ok_or_else(|| vortex_err!("Expected bool scalar, found {}", value.dtype()))? + .ok_or_else( + || vortex_err!(MismatchedTypes: "Expected bool scalar, found {}", value.dtype()), + )? .value()) } } @@ -167,14 +173,13 @@ impl<'a> TryFrom<&'a Scalar> for ByteBuffer { type Error = VortexError; fn try_from(scalar: &'a Scalar) -> VortexResult { - let binary = scalar - .as_binary_opt() - .ok_or_else(|| vortex_err!("Cannot extract buffer from non-buffer scalar"))?; + let binary = scalar.as_binary_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Cannot extract buffer from non-buffer scalar"), + )?; - binary - .value() - .cloned() - .ok_or_else(|| vortex_err!("Cannot extract present value from null scalar")) + binary.value().cloned().ok_or_else( + || vortex_err!(InvalidArgument: "Cannot extract present value from null scalar"), + ) } } @@ -184,7 +189,9 @@ impl<'a> TryFrom<&'a Scalar> for Option { fn try_from(scalar: &'a Scalar) -> VortexResult { Ok(scalar .as_binary_opt() - .ok_or_else(|| vortex_err!("Cannot extract buffer from non-buffer scalar"))? + .ok_or_else( + || vortex_err!(MismatchedTypes: "Cannot extract buffer from non-buffer scalar"), + )? .value() .cloned()) } @@ -230,8 +237,9 @@ impl<'a> TryFrom<&'a Scalar> for BufferString { type Error = VortexError; fn try_from(scalar: &'a Scalar) -> VortexResult { - >::try_from(scalar)? - .ok_or_else(|| vortex_err!("Can't extract present value from null scalar")) + >::try_from(scalar)?.ok_or_else( + || vortex_err!(InvalidArgument: "Can't extract present value from null scalar"), + ) } } @@ -249,7 +257,9 @@ impl<'a> TryFrom<&'a Scalar> for Option { fn try_from(scalar: &'a Scalar) -> Result { Ok(scalar .as_utf8_opt() - .ok_or_else(|| vortex_err!("Expected utf8 scalar, found {}", scalar.dtype()))? + .ok_or_else( + || vortex_err!(MismatchedTypes: "Expected utf8 scalar, found {}", scalar.dtype()), + )? .value() .cloned()) } @@ -287,9 +297,11 @@ where fn try_from(value: &'a Scalar) -> Result { value .as_list_opt() - .ok_or_else(|| vortex_err!("Expected list scalar, found {}", value.dtype()))? + .ok_or_else( + || vortex_err!(MismatchedTypes: "Expected list scalar, found {}", value.dtype()), + )? .elements() - .ok_or_else(|| vortex_err!("Expected non-null list"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null list"))? .into_iter() .map(|e| T::try_from(&e)) .collect::>>() diff --git a/vortex-array/src/scalar/convert/primitive.rs b/vortex-array/src/scalar/convert/primitive.rs index 0bf3ec87714..4f62e5372e8 100644 --- a/vortex-array/src/scalar/convert/primitive.rs +++ b/vortex-array/src/scalar/convert/primitive.rs @@ -65,10 +65,10 @@ macro_rules! primitive_scalar { match value.value() { Some(ScalarValue::Primitive(pv)) => pv.cast::<$T>(), Some(_) => Err(vortex_err!( - "Expected primitive scalar, found {}", + MismatchedTypes: "Expected primitive scalar, found {}", value.dtype() )), - None => Err(vortex_err!("Can't extract present value from null scalar")), + None => Err(vortex_err!(InvalidArgument: "Can't extract present value from null scalar")), } } } @@ -166,13 +166,13 @@ impl TryFrom<&Scalar> for usize { type Error = VortexError; fn try_from(value: &Scalar) -> Result { - let prim_scalar = value - .as_primitive_opt() - .ok_or_else(|| vortex_err!("Expected primitive scalar, found {}", value.dtype()))?; + let prim_scalar = value.as_primitive_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected primitive scalar, found {}", value.dtype()), + )?; let prim = prim_scalar .as_::() - .ok_or_else(|| vortex_err!("cannot convert Null to usize"))?; + .ok_or_else(|| vortex_err!(Overflow: "cannot convert Null to usize"))?; Ok(usize::try_from(prim)?) } @@ -182,9 +182,9 @@ impl TryFrom<&Scalar> for Option { type Error = VortexError; fn try_from(value: &Scalar) -> Result { - let prim_scalar = value - .as_primitive_opt() - .ok_or_else(|| vortex_err!("Expected primitive scalar, found {}", value.dtype()))?; + let prim_scalar = value.as_primitive_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Expected primitive scalar, found {}", value.dtype()), + )?; Ok(prim_scalar.as_::().map(usize::try_from).transpose()?) } diff --git a/vortex-array/src/scalar/downcast.rs b/vortex-array/src/scalar/downcast.rs index 91d17e14109..4a5d1d48e5d 100644 --- a/vortex-array/src/scalar/downcast.rs +++ b/vortex-array/src/scalar/downcast.rs @@ -221,7 +221,7 @@ impl ScalarValue { pub fn as_bool(&self) -> bool { match self { ScalarValue::Bool(b) => *b, - _ => vortex_panic!("ScalarValue is not a Bool"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Bool"), } } @@ -230,7 +230,7 @@ impl ScalarValue { pub fn as_primitive(&self) -> &PValue { match self { ScalarValue::Primitive(p) => p, - _ => vortex_panic!("ScalarValue is not a Primitive"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Primitive"), } } @@ -239,7 +239,7 @@ impl ScalarValue { pub fn as_decimal(&self) -> &DecimalValue { match self { ScalarValue::Decimal(d) => d, - _ => vortex_panic!("ScalarValue is not a Decimal"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Decimal"), } } @@ -247,7 +247,7 @@ impl ScalarValue { pub fn as_utf8(&self) -> &BufferString { match self { ScalarValue::Utf8(s) => s, - _ => vortex_panic!("ScalarValue is not a Utf8"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Utf8"), } } @@ -255,7 +255,7 @@ impl ScalarValue { pub fn as_binary(&self) -> &ByteBuffer { match self { ScalarValue::Binary(b) => b, - _ => vortex_panic!("ScalarValue is not a Binary"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Binary"), } } @@ -263,7 +263,7 @@ impl ScalarValue { pub fn as_list(&self) -> &[Option] { match self { ScalarValue::Tuple(elements) => elements, - _ => vortex_panic!("ScalarValue is not a Tuple"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Tuple"), } } @@ -271,7 +271,7 @@ impl ScalarValue { pub fn into_bool(self) -> bool { match self { ScalarValue::Bool(b) => b, - _ => vortex_panic!("ScalarValue is not a Bool"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Bool"), } } @@ -280,7 +280,7 @@ impl ScalarValue { pub fn into_primitive(self) -> PValue { match self { ScalarValue::Primitive(p) => p, - _ => vortex_panic!("ScalarValue is not a Primitive"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Primitive"), } } @@ -289,7 +289,7 @@ impl ScalarValue { pub fn into_decimal(self) -> DecimalValue { match self { ScalarValue::Decimal(d) => d, - _ => vortex_panic!("ScalarValue is not a Decimal"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Decimal"), } } @@ -297,7 +297,7 @@ impl ScalarValue { pub fn into_utf8(self) -> BufferString { match self { ScalarValue::Utf8(s) => s, - _ => vortex_panic!("ScalarValue is not a Utf8"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Utf8"), } } @@ -305,7 +305,7 @@ impl ScalarValue { pub fn into_binary(self) -> ByteBuffer { match self { ScalarValue::Binary(b) => b, - _ => vortex_panic!("ScalarValue is not a Binary"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Binary"), } } @@ -313,7 +313,7 @@ impl ScalarValue { pub fn into_list(self) -> Vec> { match self { ScalarValue::Tuple(elements) => elements, - _ => vortex_panic!("ScalarValue is not a Tuple"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Tuple"), } } @@ -321,7 +321,7 @@ impl ScalarValue { pub fn as_union(&self) -> &UnionValue { match self { ScalarValue::Union(value) => value, - _ => vortex_panic!("ScalarValue is not a Union"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Union"), } } @@ -329,7 +329,7 @@ impl ScalarValue { pub fn into_union(self) -> UnionValue { match self { ScalarValue::Union(value) => value, - _ => vortex_panic!("ScalarValue is not a Union"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Union"), } } @@ -338,7 +338,7 @@ impl ScalarValue { pub fn as_variant(&self) -> &Scalar { match self { ScalarValue::Variant(value) => value, - _ => vortex_panic!("ScalarValue is not a Variant"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Variant"), } } @@ -347,7 +347,7 @@ impl ScalarValue { pub fn into_variant(self) -> Scalar { match self { ScalarValue::Variant(value) => *value, - _ => vortex_panic!("ScalarValue is not a Variant"), + _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Variant"), } } } diff --git a/vortex-array/src/scalar/proto.rs b/vortex-array/src/scalar/proto.rs index fa9e60812fe..8bbb0e841a3 100644 --- a/vortex-array/src/scalar/proto.rs +++ b/vortex-array/src/scalar/proto.rs @@ -516,9 +516,9 @@ fn union_from_proto( let child_value = ScalarValue::from_proto(child_proto, &child_dtype, session)?; Scalar::validate(&child_dtype, child_value.as_ref()).map_err(|error| { - vortex_err!( - Serde: "union type ID {type_id} has invalid child for dtype {child_dtype}: {error}" - ) + error.with_context(format!( + "union type ID {type_id} has invalid child for dtype {child_dtype}" + )) })?; Ok(ScalarValue::Union(UnionValue::new(type_id, child_value))) @@ -531,7 +531,7 @@ mod tests { use std::sync::Arc; use vortex_buffer::BufferString; - use vortex_error::VortexError; + use vortex_error::VortexErrorKind; use vortex_error::vortex_panic; use vortex_session::VortexSession; @@ -865,10 +865,12 @@ mod tests { }))), }; - assert!(matches!( - ScalarValue::from_proto(&missing_child, &dtype, &session()), - Err(VortexError::Serde(..)) - )); + assert_eq!( + ScalarValue::from_proto(&missing_child, &dtype, &session()) + .unwrap_err() + .kind(), + VortexErrorKind::Serde + ); let wrong_child_value = pb::ScalarValue { kind: Some(Kind::UnionValue(Box::new(PbUnionValue { @@ -879,10 +881,12 @@ mod tests { }))), }; - assert!(matches!( - ScalarValue::from_proto(&wrong_child_value, &dtype, &session()), - Err(VortexError::Serde(..)) - )); + assert_eq!( + ScalarValue::from_proto(&wrong_child_value, &dtype, &session()) + .unwrap_err() + .kind(), + VortexErrorKind::Serde + ); Ok(()) } @@ -984,7 +988,7 @@ mod tests { } _ => { vortex_panic!( - "Expected f16 primitive values, got {scalar_value:?} and {read_back:?}" + AssertionFailed: "Expected f16 primitive values, got {scalar_value:?} and {read_back:?}" ) } } @@ -1087,14 +1091,18 @@ mod tests { PValue::U16(v) => *v as u64, PValue::U32(v) => *v as u64, PValue::U64(v) => *v, - _ => vortex_panic!("Unexpected primitive type for {name}: {pv:?}"), + _ => { + vortex_panic!(AssertionFailed: "Unexpected primitive type for {name}: {pv:?}") + } }; assert_eq!( v, expected, "ScalarValue {name} value not preserved: expected {expected}, got {v}" ); } - _ => vortex_panic!("Unexpected type after roundtrip for {name}: {read_back:?}"), + _ => { + vortex_panic!(AssertionFailed: "Unexpected type after roundtrip for {name}: {read_back:?}") + } } } @@ -1132,14 +1140,18 @@ mod tests { PValue::I16(v) => *v as i64, PValue::I32(v) => *v as i64, PValue::I64(v) => *v, - _ => vortex_panic!("Unexpected primitive type for {name}: {pv:?}"), + _ => { + vortex_panic!(AssertionFailed: "Unexpected primitive type for {name}: {pv:?}") + } }; assert_eq!( v, expected, "ScalarValue {name} value not preserved: expected {expected}, got {v}" ); } - _ => vortex_panic!("Unexpected type after roundtrip for {name}: {read_back:?}"), + _ => { + vortex_panic!(AssertionFailed: "Unexpected type after roundtrip for {name}: {read_back:?}") + } } } } diff --git a/vortex-array/src/scalar/scalar_impl.rs b/vortex-array/src/scalar/scalar_impl.rs index 4b9b63a2713..3722f7368b6 100644 --- a/vortex-array/src/scalar/scalar_impl.rs +++ b/vortex-array/src/scalar/scalar_impl.rs @@ -126,7 +126,7 @@ impl Scalar { /// Panics if `dtype` has no default value. pub fn default_value(dtype: &DType) -> Self { Self::try_default_value(dtype) - .unwrap_or_else(|| vortex_panic!("{dtype} has no default value")) + .unwrap_or_else(|| vortex_panic!(AssertionFailed: "{dtype} has no default value")) } /// Returns a valid default scalar, or [`None`] if `dtype` has no default. @@ -219,7 +219,9 @@ impl Scalar { let value = self.value()?; let is_zero = match self.dtype() { - DType::Null => vortex_panic!("non-null value somehow had `DType::Null`"), + DType::Null => { + vortex_panic!(AssertionFailed: "non-null value somehow had `DType::Null`") + } DType::Bool(_) => !value.as_bool(), DType::Primitive(..) => value.as_primitive().is_zero(), DType::Decimal(..) => value.as_decimal().is_zero(), @@ -271,7 +273,7 @@ impl Scalar { vortex_ensure_eq!( primitive.ptype().byte_width(), ptype.byte_width(), - "can't reinterpret cast between integers of two different widths" + InvalidArgument: "can't reinterpret cast between integers of two different widths" ); Scalar::try_new( diff --git a/vortex-array/src/scalar/scalar_value.rs b/vortex-array/src/scalar/scalar_value.rs index eb74c1a0a0e..981beaf2969 100644 --- a/vortex-array/src/scalar/scalar_value.rs +++ b/vortex-array/src/scalar/scalar_value.rs @@ -48,7 +48,7 @@ impl ScalarValue { /// Returns the zero / identity value for the given [`DType`]. pub(super) fn zero_value(dtype: &DType) -> Self { Self::try_zero_value(dtype) - .unwrap_or_else(|| vortex_panic!("{dtype} has no non-null zero value")) + .unwrap_or_else(|| vortex_panic!(AssertionFailed: "{dtype} has no non-null zero value")) } /// Returns the non-null zero value for `dtype`, or [`None`] if no such value exists. diff --git a/vortex-array/src/scalar/tests/casting.rs b/vortex-array/src/scalar/tests/casting.rs index 4b27b1ead6d..f867eb00dea 100644 --- a/vortex-array/src/scalar/tests/casting.rs +++ b/vortex-array/src/scalar/tests/casting.rs @@ -281,11 +281,11 @@ mod tests { } fn serialize_metadata(&self, _metadata: &Self::Metadata) -> VortexResult> { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { @@ -339,11 +339,11 @@ mod tests { } fn serialize_metadata(&self, _metadata: &Self::Metadata) -> VortexResult> { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { diff --git a/vortex-array/src/scalar/truncation.rs b/vortex-array/src/scalar/truncation.rs index 66dd8cee969..b9592b41631 100644 --- a/vortex-array/src/scalar/truncation.rs +++ b/vortex-array/src/scalar/truncation.rs @@ -43,7 +43,7 @@ impl ScalarTruncation for ByteBuffer { fn from_scalar(value: Scalar) -> VortexResult> { vortex_ensure!( value.dtype().is_binary(), - "Expected binary scalar, got {}", + MismatchedTypes: "Expected binary scalar, got {}", value.dtype() ); Ok(value.into_value().map(|b| b.into_binary())) @@ -79,7 +79,7 @@ impl ScalarTruncation for BufferString { fn from_scalar(value: Scalar) -> VortexResult> { vortex_ensure!( value.dtype().is_utf8(), - "Expected utf8 scalar, got {}", + MismatchedTypes: "Expected utf8 scalar, got {}", value.dtype() ); Ok(value.into_value().map(|b| b.into_utf8())) diff --git a/vortex-array/src/scalar/typed_view/binary.rs b/vortex-array/src/scalar/typed_view/binary.rs index 3adfcba9aa0..bcaca5fa63a 100644 --- a/vortex-array/src/scalar/typed_view/binary.rs +++ b/vortex-array/src/scalar/typed_view/binary.rs @@ -67,7 +67,7 @@ impl<'a> BinaryScalar<'a> { /// Returns an error if the data type is not a binary type. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Binary(..)) { - vortex_bail!("Can only construct binary scalar from binary dtype, found {dtype}") + vortex_bail!(MismatchedTypes: "Can only construct binary scalar from binary dtype, found {dtype}") } Ok(Self { diff --git a/vortex-array/src/scalar/typed_view/bool.rs b/vortex-array/src/scalar/typed_view/bool.rs index cace40ce5fe..27bc72d0471 100644 --- a/vortex-array/src/scalar/typed_view/bool.rs +++ b/vortex-array/src/scalar/typed_view/bool.rs @@ -61,7 +61,7 @@ impl<'a> BoolScalar<'a> { /// Returns an error if the data type is not a [`DType::Bool`]. pub fn try_new(dtype: &'a DType, value: Option<&ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Bool(_)) { - vortex_bail!("Expected bool scalar, found {}", dtype) + vortex_bail!(MismatchedTypes: "Expected bool scalar, found {}", dtype) } Ok(Self { dtype, diff --git a/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs b/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs index 2a47c9cf977..0f491fcbfb5 100644 --- a/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs +++ b/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs @@ -69,7 +69,7 @@ pub(crate) fn decimal_numeric_result_dtype( .filter(|scale| *scale <= MAX_SCALE) else { vortex_bail!( - "output scale {result_scale} of {input} {op} {input} is outside the \ + Overflow: "output scale {result_scale} of {input} {op} {input} is outside the \ representable scale range of {} to {MAX_SCALE}", i8::MIN ); diff --git a/vortex-array/src/scalar/typed_view/decimal/dvalue.rs b/vortex-array/src/scalar/typed_view/decimal/dvalue.rs index 5fe5a353e7c..cced9573d18 100644 --- a/vortex-array/src/scalar/typed_view/decimal/dvalue.rs +++ b/vortex-array/src/scalar/typed_view/decimal/dvalue.rs @@ -133,7 +133,7 @@ impl DecimalValue { let factor = decimal_scale_factor(scale_delta as u32)?; value.checked_mul(&factor).ok_or_else(|| { vortex_err!( - "Rescaling decimal from scale {} to {} overflows", + Overflow: "Rescaling decimal from scale {} to {} overflows", from_scale, to_scale ) @@ -143,7 +143,7 @@ impl DecimalValue { let remainder = value % factor; if remainder != i256::ZERO { vortex_bail!( - "Rescaling decimal value {} from scale {} to {} would lose precision", + InvalidArgument: "Rescaling decimal value {} from scale {} to {} would lose precision", value, from_scale, to_scale @@ -174,7 +174,7 @@ impl DecimalValue { let decimal_value = Self::I256(value); decimal_value.normalize(decimal_dtype).ok_or_else(|| { vortex_err!( - "decimal value {} does not fit in precision of {}", + Overflow: "decimal value {} does not fit in precision of {}", decimal_value, decimal_dtype ) @@ -240,7 +240,7 @@ impl DecimalValue { fn decimal_scale_factor(exp: u32) -> VortexResult { i256::from_i128(10).checked_pow(exp).ok_or_else(|| { vortex_err!( - "decimal scale factor 10^{} cannot be represented in i256", + InvalidArgument: "decimal scale factor 10^{} cannot be represented in i256", exp ) }) diff --git a/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs b/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs index c9ea14a58ce..6e4f436eab7 100644 --- a/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs +++ b/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs @@ -54,7 +54,7 @@ impl DecimalToIntegerCast { pub(crate) fn error(&self, value: i256) -> VortexError { vortex_err!( - "Decimal value {} at scale {} out of range for {}", + OutOfBounds: "Decimal value {} at scale {} out of range for {}", value, self.scale, T::PTYPE diff --git a/vortex-array/src/scalar/typed_view/decimal/scalar.rs b/vortex-array/src/scalar/typed_view/decimal/scalar.rs index 2c1c88319e0..8dee6959bcb 100644 --- a/vortex-array/src/scalar/typed_view/decimal/scalar.rs +++ b/vortex-array/src/scalar/typed_view/decimal/scalar.rs @@ -123,7 +123,7 @@ impl<'a> DecimalScalar<'a> { } } _ => vortex_bail!( - "Cannot cast decimal to {dtype}: decimal scalars can only be cast to decimal or primitive numeric types" + MismatchedTypes: "Cannot cast decimal to {dtype}: decimal scalars can only be cast to decimal or primitive numeric types" ), } } @@ -163,7 +163,7 @@ impl<'a> DecimalScalar<'a> { // We could have ops between different types but need to add rules for type inference. if self.decimal_type != other.decimal_type { vortex_bail!( - "decimal types must match: {} vs {}", + MismatchedTypes: "decimal types must match: {} vs {}", self.decimal_type, other.decimal_type ); diff --git a/vortex-array/src/scalar/typed_view/decimal/tests.rs b/vortex-array/src/scalar/typed_view/decimal/tests.rs index 2600256688e..9720f5b459e 100644 --- a/vortex-array/src/scalar/typed_view/decimal/tests.rs +++ b/vortex-array/src/scalar/typed_view/decimal/tests.rs @@ -967,7 +967,7 @@ fn test_decimal_scalar_mul_widens_beyond_operand_storage() -> VortexResult<()> { let operand = DecimalValue::I64(100_000_000_000_000_000); let (value, result_dtype) = checked_op(operand, operand, dtype, NumericOperator::Mul)? - .ok_or_else(|| vortex_err!("expected an in-precision product"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected an in-precision product"))?; assert_eq!(result_dtype, DecimalDType::new(37, 0)); assert_eq!( value, @@ -988,7 +988,7 @@ fn test_decimal_scalar_add_reserves_carry_digit() -> VortexResult<()> { dtype, NumericOperator::Add, )? - .ok_or_else(|| vortex_err!("expected the carry digit to absorb the result"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "expected the carry digit to absorb the result"))?; assert_eq!(result_dtype, DecimalDType::new(4, 0)); assert_eq!(value, DecimalValue::I16(1_001)); assert_eq!(value.decimal_type(), DecimalType::I16); @@ -1022,7 +1022,7 @@ fn test_decimal_scalar_div_reports_unrepresentable_intermediate() -> VortexResul let pow10 = |exp: u32| { i256::from_i128(10) .checked_pow(exp) - .ok_or_else(|| vortex_err!("10^{exp} is representable as i256")) + .ok_or_else(|| vortex_err!(AssertionFailed: "10^{exp} is representable as i256")) }; let lhs = DecimalValue::I256(pow10(75)?); let rhs = DecimalValue::I256(pow10(70)?); @@ -1044,7 +1044,9 @@ fn test_decimal_scalar_null_handling() -> VortexResult<()> { let result = null .as_decimal() .checked_binary_numeric(&value.as_decimal(), NumericOperator::Add)? - .ok_or_else(|| vortex_err!("a null operand yields a null result, not an overflow"))?; + .ok_or_else( + || vortex_err!(Overflow: "a null operand yields a null result, not an overflow"), + )?; assert!(result.is_null()); assert_eq!( result.dtype(), diff --git a/vortex-array/src/scalar/typed_view/extension/mod.rs b/vortex-array/src/scalar/typed_view/extension/mod.rs index 27b1567869f..230b9ea32c9 100644 --- a/vortex-array/src/scalar/typed_view/extension/mod.rs +++ b/vortex-array/src/scalar/typed_view/extension/mod.rs @@ -52,7 +52,7 @@ impl<'a> ExtScalar<'a> { /// been verified to be valid for the extension type. pub(crate) fn new_unchecked(dtype: &'a DType, value: Option<&'a ScalarValue>) -> Self { let DType::Extension(ext_dtype) = dtype else { - vortex_panic!("Expected extension scalar, found {}", dtype) + vortex_panic!(MismatchedTypes: "Expected extension scalar, found {}", dtype) }; Self { @@ -96,7 +96,7 @@ impl<'a> ExtScalar<'a> { } vortex_bail!( - "cannot cast extension dtype with id {} and storage type {} to {}", + MismatchedTypes: "cannot cast extension dtype with id {} and storage type {} to {}", self.ext_dtype.id(), self.ext_dtype.storage_dtype(), target_dtype diff --git a/vortex-array/src/scalar/typed_view/extension/tests.rs b/vortex-array/src/scalar/typed_view/extension/tests.rs index d26acd20127..2d1205486d2 100644 --- a/vortex-array/src/scalar/typed_view/extension/tests.rs +++ b/vortex-array/src/scalar/typed_view/extension/tests.rs @@ -316,11 +316,11 @@ fn test_ext_scalar_with_metadata() { } fn serialize_metadata(&self, _metadata: &Self::Metadata) -> VortexResult> { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { diff --git a/vortex-array/src/scalar/typed_view/list.rs b/vortex-array/src/scalar/typed_view/list.rs index 01e91800432..5ac0a19d862 100644 --- a/vortex-array/src/scalar/typed_view/list.rs +++ b/vortex-array/src/scalar/typed_view/list.rs @@ -104,7 +104,7 @@ impl<'a> ListScalar<'a> { pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { let element_dtype = dtype .as_any_size_list_element_opt() - .ok_or_else(|| vortex_err!("Expected list scalar, found {}", dtype))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected list scalar, found {}", dtype))?; Ok(Self { dtype, @@ -146,7 +146,9 @@ impl<'a> ListScalar<'a> { pub fn element_dtype(&self) -> &DType { self.dtype .as_any_size_list_element_opt() - .unwrap_or_else(|| vortex_panic!("`ListScalar` somehow had dtype {}", self.dtype)) + .unwrap_or_else( + || vortex_panic!(AssertionFailed: "`ListScalar` somehow had dtype {}", self.dtype), + ) .as_ref() } @@ -197,7 +199,7 @@ impl<'a> ListScalar<'a> { .as_any_size_list_element_opt() .ok_or_else(|| { vortex_err!( - "Cannot cast {} to {}: list can only be cast to a list or fixed-size list", + MismatchedTypes: "Cannot cast {} to {}: list can only be cast to a list or fixed-size list", self.dtype(), dtype ) @@ -208,7 +210,7 @@ impl<'a> ListScalar<'a> { && *size as usize != self.len() { vortex_bail!( - "tried to cast to a `FixedSizeList[{size}]` but had {} elements", + InvalidArgument: "tried to cast to a `FixedSizeList[{size}]` but had {} elements", self.len() ) } @@ -217,7 +219,7 @@ impl<'a> ListScalar<'a> { dtype.clone(), Some(ScalarValue::Tuple( self.elements - .ok_or_else(|| vortex_err!("nullness should be handled in Scalar::cast"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "nullness should be handled in Scalar::cast"))? .iter() .map(|element| { // Recursively cast the elements of the list. diff --git a/vortex-array/src/scalar/typed_view/map.rs b/vortex-array/src/scalar/typed_view/map.rs index fd49f999325..c6501e974f8 100644 --- a/vortex-array/src/scalar/typed_view/map.rs +++ b/vortex-array/src/scalar/typed_view/map.rs @@ -67,7 +67,7 @@ impl<'a> MapScalar<'a> { /// Returns an error when `dtype` is not [`DType::Map`]. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !dtype.is_map() { - vortex_bail!("Expected map scalar, found {dtype}") + vortex_bail!(InvalidArgument: "Expected map scalar, found {dtype}") } Ok(Self { @@ -145,20 +145,20 @@ impl<'a> MapScalar<'a> { /// returns an error for direct null-map casts; callers should use [`Scalar::cast`] so null /// handling and sortedness checks stay centralized. pub(crate) fn cast(&self, dtype: &DType) -> VortexResult { - let target = dtype - .as_map_opt() - .ok_or_else(|| vortex_err!("Cannot cast map to {dtype}: target must be a map"))?; + let target = dtype.as_map_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Cannot cast map to {dtype}: target must be a map"), + )?; if target.keys_sorted() && !self.map_dtype().keys_sorted() { vortex_bail!( - "Cannot cast {} to {dtype}: source does not assert sorted map keys", + MismatchedTypes: "Cannot cast {} to {dtype}: source does not assert sorted map keys", self.dtype ); } let Some(entries) = self.entries else { vortex_bail!( - "Cannot cast null map {} to {dtype}: Scalar::cast should handle nulls first", + MismatchedTypes: "Cannot cast null map {} to {dtype}: Scalar::cast should handle nulls first", self.dtype ); }; diff --git a/vortex-array/src/scalar/typed_view/primitive/pvalue.rs b/vortex-array/src/scalar/typed_view/primitive/pvalue.rs index bea7193e2d3..e5cc3a25090 100644 --- a/vortex-array/src/scalar/typed_view/primitive/pvalue.rs +++ b/vortex-array/src/scalar/typed_view/primitive/pvalue.rs @@ -299,7 +299,7 @@ impl PValue { PValue::F64(f) => T::from_f64(f), }; let to = T::PTYPE; - res.ok_or_else(|| vortex_err!("Cannot cast {self} to {to}")) + res.ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot cast {self} to {to}")) } /// Returns true if the value of float type and is NaN. @@ -413,7 +413,7 @@ macro_rules! int_pvalue { ) { PValue::cast(&value) } else { - vortex_bail!("Cannot read primitive value {:?} as {}", value, PType::$PT) + vortex_bail!(MismatchedTypes: "Cannot read primitive value {:?} as {}", value, PType::$PT) } } } @@ -437,10 +437,9 @@ impl TryFrom for usize { type Error = VortexError; fn try_from(value: PValue) -> Result { - value - .cast::()? - .to_usize() - .ok_or_else(|| vortex_err!("Cannot read primitive value {:?} as usize", value)) + value.cast::()?.to_usize().ok_or_else( + || vortex_err!(Overflow: "Cannot read primitive value {:?} as usize", value), + ) } } @@ -557,26 +556,24 @@ impl CoercePValue for f16 { PValue::U32(u) => { vortex_ensure!( u <= u16::MAX as u32, - "Cannot coerce U32 value to f16: value out of range" + Overflow: "Cannot coerce U32 value to f16: value out of range" ); Ok(Self::from_bits(u as u16)) } PValue::U64(u) => { vortex_ensure!( u <= u16::MAX as u64, - "Cannot coerce U64 value to f16: value out of range" + Overflow: "Cannot coerce U64 value to f16: value out of range" ); Ok(Self::from_bits(u as u16)) } PValue::F16(u) => Ok(u), - PValue::F32(f) => { - ::from(f).ok_or_else(|| vortex_err!("Cannot convert f32 to f16")) - } - PValue::F64(f) => { - ::from(f).ok_or_else(|| vortex_err!("Cannot convert f64 to f16")) - } + PValue::F32(f) => ::from(f) + .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f32 to f16")), + PValue::F64(f) => ::from(f) + .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f64 to f16")), PValue::I8(_) | PValue::I16(_) | PValue::I32(_) | PValue::I64(_) => { - vortex_bail!("Cannot coerce {value:?} to f16: type not supported for coercion") + vortex_bail!(InvalidArgument: "Cannot coerce {value:?} to f16: type not supported for coercion") } } } @@ -596,19 +593,17 @@ impl CoercePValue for f32 { PValue::U64(u) => { vortex_ensure!( u <= u32::MAX as u64, - "Cannot coerce U64 value to f32: value out of range" + Overflow: "Cannot coerce U64 value to f32: value out of range" ); Ok(Self::from_bits(u as u32)) } - PValue::F16(f) => { - ::from(f).ok_or_else(|| vortex_err!("Cannot convert f16 to f32")) - } + PValue::F16(f) => ::from(f) + .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f16 to f32")), PValue::F32(f) => Ok(f), - PValue::F64(f) => { - ::from(f).ok_or_else(|| vortex_err!("Cannot convert f64 to f32")) - } + PValue::F64(f) => ::from(f) + .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f64 to f32")), PValue::I8(_) | PValue::I16(_) | PValue::I32(_) | PValue::I64(_) => { - vortex_bail!("Unsupported PValue {value:?} type for f32") + vortex_bail!(InvalidArgument: "Unsupported PValue {value:?} type for f32") } } } @@ -622,15 +617,13 @@ impl CoercePValue for f64 { PValue::U16(u) => Ok(Self::from_bits(u as u64)), PValue::U32(u) => Ok(Self::from_bits(u as u64)), PValue::U64(u) => Ok(Self::from_bits(u)), - PValue::F16(f) => { - ::from(f).ok_or_else(|| vortex_err!("Cannot convert f16 to f64")) - } - PValue::F32(f) => { - ::from(f).ok_or_else(|| vortex_err!("Cannot convert f32 to f64")) - } + PValue::F16(f) => ::from(f) + .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f16 to f64")), + PValue::F32(f) => ::from(f) + .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f32 to f64")), PValue::F64(f) => Ok(f), PValue::I8(_) | PValue::I16(_) | PValue::I32(_) | PValue::I64(_) => { - vortex_bail!("Unsupported PValue {value:?} type for f64") + vortex_bail!(InvalidArgument: "Unsupported PValue {value:?} type for f64") } } } diff --git a/vortex-array/src/scalar/typed_view/primitive/scalar.rs b/vortex-array/src/scalar/typed_view/primitive/scalar.rs index a1e27d679ab..b35c88dc4f4 100644 --- a/vortex-array/src/scalar/typed_view/primitive/scalar.rs +++ b/vortex-array/src/scalar/typed_view/primitive/scalar.rs @@ -155,7 +155,7 @@ impl<'a> PrimitiveScalar<'a> { vortex_ensure_eq!( self.ptype, T::PTYPE, - "Attempting to read a primitive scalar as the wrong type" + MismatchedTypes: "Attempting to read a primitive scalar as the wrong type" ); if let Some(pv) = self.pvalue { @@ -180,7 +180,7 @@ impl<'a> PrimitiveScalar<'a> { *decimal_dtype, *nullability, )), - _ => vortex_bail!("Cannot cast primitive scalar to {dtype}"), + _ => vortex_bail!(MismatchedTypes: "Cannot cast primitive scalar to {dtype}"), } } @@ -222,7 +222,7 @@ impl<'a> PrimitiveScalar<'a> { pub fn as_(&self) -> Option { self.as_opt::().unwrap_or_else(|| { vortex_panic!( - "cast {} to {}: value out of range", + Overflow: "cast {} to {}: value out of range", self.ptype, type_name::() ) @@ -289,7 +289,7 @@ fn pvalue_to_decimal(pvalue: PValue, decimal_dtype: DecimalDType) -> VortexResul PValue::I32(v) => i256::from_i128(i128::from(v)), PValue::I64(v) => i256::from_i128(i128::from(v)), PValue::F16(_) | PValue::F32(_) | PValue::F64(_) => { - vortex_bail!("Cannot cast floating primitive {pvalue} to decimal {decimal_dtype}") + vortex_bail!(MismatchedTypes: "Cannot cast floating primitive {pvalue} to decimal {decimal_dtype}") } }; @@ -345,7 +345,7 @@ impl<'a> PrimitiveScalar<'a> { op: NumericOperator, ) -> Option> { if !self.dtype().eq_ignore_nullability(other.dtype()) { - vortex_panic!("types must match: {} {}", self.dtype(), other.dtype()); + vortex_panic!(MismatchedTypes: "types must match: {} {}", self.dtype(), other.dtype()); } let result_dtype = if self.dtype().is_nullable() { self.dtype() diff --git a/vortex-array/src/scalar/typed_view/struct_.rs b/vortex-array/src/scalar/typed_view/struct_.rs index c1903b9f1a4..e5fb960117f 100644 --- a/vortex-array/src/scalar/typed_view/struct_.rs +++ b/vortex-array/src/scalar/typed_view/struct_.rs @@ -116,7 +116,7 @@ impl<'a> StructScalar<'a> { /// Creates a new [`StructScalar`] from a [`DType`] and optional [`ScalarValue`]. pub(crate) fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Struct(..)) { - vortex_bail!("Expected struct scalar, found {}", dtype) + vortex_bail!(MismatchedTypes: "Expected struct scalar, found {}", dtype) } Ok(Self { @@ -204,7 +204,7 @@ impl<'a> StructScalar<'a> { pub fn cast(&self, dtype: &DType) -> VortexResult { let DType::Struct(st, _) = dtype else { vortex_bail!( - "Cannot cast struct to {}: struct can only be cast to struct", + MismatchedTypes: "Cannot cast struct to {}: struct can only be cast to struct", dtype ) }; @@ -212,7 +212,7 @@ impl<'a> StructScalar<'a> { if st.fields().len() != own_st.fields().len() { vortex_bail!( - "Cannot cast between structs with different number of fields: {} and {}", + MismatchedTypes: "Cannot cast between structs with different number of fields: {} and {}", own_st.fields().len(), st.fields().len() ); @@ -251,7 +251,7 @@ impl<'a> StructScalar<'a> { let struct_dtype = self .dtype .as_struct_fields_opt() - .ok_or_else(|| vortex_err!("Not a struct dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Not a struct dtype"))?; let projected_dtype = DType::Struct( struct_dtype.project(projection)?, self.dtype().nullability(), @@ -281,14 +281,14 @@ impl Scalar { /// Creates a new struct scalar with the given fields, checking dtypes at runtime. pub fn struct_(dtype: DType, children: impl IntoIterator) -> Self { let DType::Struct(struct_fields, _) = &dtype else { - vortex_panic!("Expected struct dtype, found {}", dtype); + vortex_panic!(MismatchedTypes: "Expected struct dtype, found {}", dtype); }; let children: Vec = children.into_iter().collect(); let field_dtypes = struct_fields.field_dtypes(); if children.len() != field_dtypes.len() { vortex_panic!( - "Struct has {} fields but {} children were provided", + InvalidArgument: "Struct has {} fields but {} children were provided", field_dtypes.len(), children.len() ); @@ -297,7 +297,7 @@ impl Scalar { for (idx, (child, expected_dtype)) in children.iter().zip(field_dtypes).enumerate() { if child.dtype() != expected_dtype { vortex_panic!( - "Field {} expected dtype {} but got {}", + MismatchedTypes: "Field {} expected dtype {} but got {}", idx, expected_dtype, child.dtype() diff --git a/vortex-array/src/scalar/typed_view/union.rs b/vortex-array/src/scalar/typed_view/union.rs index 60ff96dbb78..aaa7e1d117a 100644 --- a/vortex-array/src/scalar/typed_view/union.rs +++ b/vortex-array/src/scalar/typed_view/union.rs @@ -107,7 +107,7 @@ impl<'a> UnionScalar<'a> { /// non-union dtype, a null value for a non-nullable union, an unknown type ID, or a value that /// is invalid for the selected variant dtype. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { - vortex_ensure!(dtype.is_union(), "Expected union scalar, found {dtype}"); + vortex_ensure!(dtype.is_union(), MismatchedTypes: "Expected union scalar, found {dtype}"); Scalar::validate(dtype, value)?; @@ -125,7 +125,7 @@ impl<'a> UnionScalar<'a> { /// Panics if `dtype` is not a union dtype or a non-null `value` is not a union value. pub(crate) fn new_unchecked(dtype: &'a DType, value: Option<&'a ScalarValue>) -> Self { if !dtype.is_union() { - vortex_panic!("Expected union scalar, found {dtype}") + vortex_panic!(MismatchedTypes: "Expected union scalar, found {dtype}") } Self { diff --git a/vortex-array/src/scalar/typed_view/utf8.rs b/vortex-array/src/scalar/typed_view/utf8.rs index 771ea0d5d0f..268c8832af9 100644 --- a/vortex-array/src/scalar/typed_view/utf8.rs +++ b/vortex-array/src/scalar/typed_view/utf8.rs @@ -63,7 +63,7 @@ impl<'a> Utf8Scalar<'a> { /// Returns an error if the data type is not a UTF-8 type. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Utf8(..)) { - vortex_bail!("Can only construct utf8 scalar from utf8 dtype, found {dtype}") + vortex_bail!(MismatchedTypes: "Can only construct utf8 scalar from utf8 dtype, found {dtype}") } Ok(Self { diff --git a/vortex-array/src/scalar/typed_view/variant.rs b/vortex-array/src/scalar/typed_view/variant.rs index ced2461e0cf..eedeae0c3e1 100644 --- a/vortex-array/src/scalar/typed_view/variant.rs +++ b/vortex-array/src/scalar/typed_view/variant.rs @@ -34,7 +34,7 @@ impl<'a> VariantScalar<'a> { #[inline] pub(crate) fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Variant(_)) { - vortex_bail!("Expected variant scalar, found {}", dtype) + vortex_bail!(InvalidArgument: "Expected variant scalar, found {}", dtype) } Ok(Self { diff --git a/vortex-array/src/scalar/validate.rs b/vortex-array/src/scalar/validate.rs index 1c9cf50e558..227bbfe5110 100644 --- a/vortex-array/src/scalar/validate.rs +++ b/vortex-array/src/scalar/validate.rs @@ -112,7 +112,7 @@ impl Scalar { match Self::validate_detailed(dtype, value) { Err(err) => err, Ok(()) => vortex_err!( - "scalar validation fast path rejected value {value:?} for dtype {dtype}, but the \ + AssertionFailed: "scalar validation fast path rejected value {value:?} for dtype {dtype}, but the \ detailed check accepted it" ), } @@ -123,7 +123,7 @@ impl Scalar { let Some(value) = value else { vortex_ensure!( dtype.is_nullable(), - "non-nullable dtype {dtype} cannot hold a null value", + InvalidArgument: "non-nullable dtype {dtype} cannot hold a null value", ); return Ok(()); }; @@ -131,17 +131,17 @@ impl Scalar { // From here onwards, we know that the value is not null. match dtype { DType::Null => { - vortex_bail!("null dtype cannot hold a non-null value {value}"); + vortex_bail!(InvalidArgument: "null dtype cannot hold a non-null value {value}"); } DType::Bool(_) => { vortex_ensure!( matches!(value, ScalarValue::Bool(_)), - "bool dtype expected Bool value, got {value}", + MismatchedTypes: "bool dtype expected Bool value, got {value}", ); } DType::Primitive(ptype, _) => { let ScalarValue::Primitive(pvalue) = value else { - vortex_bail!("primitive dtype {ptype} expected Primitive value, got {value}",); + vortex_bail!(MismatchedTypes: "primitive dtype {ptype} expected Primitive value, got {value}",); }; // Note that this is a backwards compatibility check for poor design in the @@ -153,92 +153,91 @@ impl Scalar { vortex_ensure!( f16_backcompat_still_works || pvalue.ptype() == *ptype, - "primitive dtype {ptype} is not compatible with value {pvalue}", + MismatchedTypes: "primitive dtype {ptype} is not compatible with value {pvalue}", ); } DType::Decimal(dec_dtype, _) => { let ScalarValue::Decimal(dvalue) = value else { - vortex_bail!("decimal dtype expected Decimal value, got {value}"); + vortex_bail!(MismatchedTypes: "decimal dtype expected Decimal value, got {value}"); }; vortex_ensure!( dvalue.fits_in_precision(*dec_dtype), - "decimal value {dvalue} does not fit in precision of {dec_dtype}", + Overflow: "decimal value {dvalue} does not fit in precision of {dec_dtype}", ); } DType::Utf8(_) => { vortex_ensure!( matches!(value, ScalarValue::Utf8(_)), - "utf8 dtype expected Utf8 value, got {value}", + MismatchedTypes: "utf8 dtype expected Utf8 value, got {value}", ); } DType::Binary(_) => { vortex_ensure!( matches!(value, ScalarValue::Binary(_)), - "binary dtype expected Binary value, got {value}", + MismatchedTypes: "binary dtype expected Binary value, got {value}", ); } DType::List(elem_dtype, _) => { let ScalarValue::Tuple(elements) = value else { - vortex_bail!("list dtype expected Tuple value, got {value}"); + vortex_bail!(MismatchedTypes: "list dtype expected Tuple value, got {value}"); }; for (i, element) in elements.iter().enumerate() { Self::validate_detailed(elem_dtype.as_ref(), element.as_ref()) - .map_err(|e| vortex_error::vortex_err!("list element at index {i}: {e}"))?; + .map_err(|e| e.with_context(format!("list element at index {i}")))?; } } DType::FixedSizeList(elem_dtype, size, _) => { let ScalarValue::Tuple(elements) = value else { - vortex_bail!("fixed-size list dtype expected Tuple value, got {value}",); + vortex_bail!(MismatchedTypes: "fixed-size list dtype expected Tuple value, got {value}",); }; let len = elements.len(); vortex_ensure_eq!( len, *size as usize, - "fixed-size list scalar has the wrong number of elements", + InvalidArgument: "fixed-size list scalar has the wrong number of elements", ); for (i, element) in elements.iter().enumerate() { Self::validate_detailed(elem_dtype.as_ref(), element.as_ref()).map_err( - |e| vortex_error::vortex_err!("fixed-size list element at index {i}: {e}",), + |e| e.with_context(format!("fixed-size list element at index {i}")), )?; } } DType::Map(map, _) => { let ScalarValue::Tuple(entries) = value else { - vortex_bail!("map dtype expected Tuple value, got {value}"); + vortex_bail!(MismatchedTypes: "map dtype expected Tuple value, got {value}"); }; let key_dtype = map.key_dtype(); let value_dtype = map.value_dtype(); for (index, entry) in entries.iter().enumerate() { let entry = entry.as_ref().ok_or_else(|| { - vortex_error::vortex_err!("map entry at index {index} cannot be null") + vortex_error::vortex_err!(InvalidArgument: "map entry at index {index} cannot be null") })?; let ScalarValue::Tuple(values) = entry else { vortex_bail!( - "map entry at index {index} expected Tuple value, got {entry}" + MismatchedTypes: "map entry at index {index} expected Tuple value, got {entry}" ); }; vortex_ensure_eq!( values.len(), 2, - "map entry at index {index} has the wrong number of values", + InvalidArgument: "map entry at index {index} has the wrong number of values", ); - Self::validate_detailed(&key_dtype, values[0].as_ref()).map_err(|error| { - vortex_error::vortex_err!("map key at entry {index}: {error}") - })?; + Self::validate_detailed(&key_dtype, values[0].as_ref()) + .map_err(|error| error.with_context(format!("map key at entry {index}")))?; Self::validate_detailed(&value_dtype, values[1].as_ref()).map_err(|error| { - vortex_error::vortex_err!("map value at entry {index}: {error}") + error.with_context(format!("map value at entry {index}")) })?; } } DType::Struct(fields, _) => { let ScalarValue::Tuple(values) = value else { - vortex_bail!("struct dtype expected Tuple value, got {value}"); + vortex_bail!(MismatchedTypes: "struct dtype expected Tuple value, got {value}"); }; let nfields = fields.nfields(); @@ -246,7 +245,7 @@ impl Scalar { vortex_ensure_eq!( nvalues, nfields, - "struct scalar has the wrong number of fields", + InvalidArgument: "struct scalar has the wrong number of fields", ); for (field, field_value) in fields.field_dtypes().zip(values.iter()) { @@ -255,13 +254,13 @@ impl Scalar { } DType::Union(variants, _) => { let ScalarValue::Union(union_value) = value else { - vortex_bail!("union dtype expected Union value, got {value}"); + vortex_bail!(MismatchedTypes: "union dtype expected Union value, got {value}"); }; let type_id = union_value.type_id(); let Some(child_index) = variants.tag_to_child_index(type_id) else { vortex_bail!( - "union value has unknown type ID {type_id}; expected one of {:?}", + NotFound: "union value has unknown type ID {type_id}; expected one of {:?}", variants.type_ids() ); }; @@ -272,22 +271,21 @@ impl Scalar { Self::validate_detailed(&child_dtype, union_value.child_value()).map_err( |error| { - vortex_error::vortex_err!( - "union value for type ID {type_id} is invalid for dtype {child_dtype}: \ - {error}" - ) + error.with_context(format!( + "union value for type ID {type_id} is invalid for dtype {child_dtype}" + )) }, )?; } DType::Variant(_) => { let ScalarValue::Variant(inner) = value else { - vortex_bail!("variant dtype expected Variant value, got {value}"); + vortex_bail!(MismatchedTypes: "variant dtype expected Variant value, got {value}"); }; Self::validate_detailed(inner.dtype(), inner.value())?; vortex_ensure!( !inner.is_null() || matches!(inner.dtype(), DType::Null), - "variant nulls must use a nested null scalar, got {}", + InvalidArgument: "variant nulls must use a nested null scalar, got {}", inner.dtype(), ); } diff --git a/vortex-array/src/scalar_fn/erased.rs b/vortex-array/src/scalar_fn/erased.rs index ae951376778..fa64feb68a0 100644 --- a/vortex-array/src/scalar_fn/erased.rs +++ b/vortex-array/src/scalar_fn/erased.rs @@ -94,7 +94,7 @@ impl ScalarFnRef { self.try_downcast::() .map_err(|this| { vortex_err!( - "Failed to downcast ScalarFnRef {} to {}", + MismatchedTypes: "Failed to downcast ScalarFnRef {} to {}", this.0.id(), type_name::(), ) diff --git a/vortex-array/src/scalar_fn/fns/between/mod.rs b/vortex-array/src/scalar_fn/fns/between/mod.rs index 9ba0173975d..fd884a54884 100644 --- a/vortex-array/src/scalar_fn/fns/between/mod.rs +++ b/vortex-array/src/scalar_fn/fns/between/mod.rs @@ -286,14 +286,14 @@ impl ScalarFnVTable for Between { if !arr_dt.eq_ignore_nullability(lower_dt) { vortex_bail!( - "Array dtype {} does not match lower dtype {}", + MismatchedTypes: "Array dtype {} does not match lower dtype {}", arr_dt, lower_dt ); } if !arr_dt.eq_ignore_nullability(upper_dt) { vortex_bail!( - "Array dtype {} does not match upper dtype {}", + MismatchedTypes: "Array dtype {} does not match upper dtype {}", arr_dt, upper_dt ); @@ -389,7 +389,7 @@ mod tests { let lazy = data.apply(&between(col("x"), col("lo"), col("hi"), NON_STRICT))?; let Validity::Array(validity) = lazy.validity()? else { - vortex_bail!("non-lazy validity"); + vortex_bail!(AssertionFailed: "non-lazy validity"); }; assert_eq!( validity.encoding_id().to_string(), diff --git a/vortex-array/src/scalar_fn/fns/binary/boolean.rs b/vortex-array/src/scalar_fn/fns/binary/boolean.rs index df23e5a87cb..47bae8d5280 100644 --- a/vortex-array/src/scalar_fn/fns/binary/boolean.rs +++ b/vortex-array/src/scalar_fn/fns/binary/boolean.rs @@ -138,7 +138,7 @@ pub(crate) fn execute_boolean( let rhs = rhs.execute::(ctx)?; let Some(result) = ::boolean(rhs.as_view(), &lhs.into_array(), op, ctx)? else { - vortex_bail!("No boolean kernel for two BoolArrays"); + vortex_bail!(AssertionFailed: "No boolean kernel for two BoolArrays"); }; Ok(result) } @@ -187,7 +187,7 @@ fn constant_array_boolean( ))), (Operator::Or, Some(false)) => Ok(Some(cast_bool_nullability(array, nullability)?)), (Operator::And | Operator::Or, None) => Ok(None), - (other, _) => vortex_bail!("Not a boolean operator: {other}"), + (other, _) => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), } } @@ -207,14 +207,14 @@ fn boolean_scalar_scalar( (None, _) | (_, None) => None, (Some(l), Some(r)) => Some(l | r), }, - other => vortex_bail!("Not a boolean operator: {other}"), + other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), }) } fn bool_scalar_value(scalar: &Scalar) -> VortexResult> { Ok(scalar .as_bool_opt() - .ok_or_else(|| vortex_err!("expected boolean scalar"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))? .value()) } @@ -235,7 +235,7 @@ pub fn kleene_boolean_buffers( let values = match operator { Operator::And => lhs_values & &rhs_values, Operator::Or => lhs_values | &rhs_values, - other => vortex_bail!("Not a boolean operator: {other}"), + other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), }; return Ok(BoolArray::try_new(values, Validity::from(nullability))?.into_array()); } @@ -298,7 +298,7 @@ pub fn kleene_boolean_buffer_scalar( Validity::from_mask(valid, nullability), )? } - (other, _) => vortex_bail!("Not a boolean operator: {other}"), + (other, _) => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), }; Ok(result.into_array()) @@ -482,7 +482,7 @@ fn fused_boolean_word_sources( nullability, allocator, ), - other => vortex_bail!("Not a boolean operator: {other}"), + other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), } } @@ -642,7 +642,7 @@ where nullability, allocator, ), - other => vortex_bail!("Not a boolean operator: {other}"), + other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), } } diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs b/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs index b569e791f32..6de49ed07b2 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs @@ -29,9 +29,11 @@ impl BoolOperand { let value = constant .scalar() .as_bool_opt() - .ok_or_else(|| vortex_err!("expected boolean scalar"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))? .value() - .ok_or_else(|| vortex_err!("null constant handled by execute_compare"))?; + .ok_or_else( + || vortex_err!(AssertionFailed: "null constant handled by execute_compare"), + )?; return Ok(Self::Constant { value, validity: if constant.scalar().dtype().is_nullable() { diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs b/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs index ef833adf6c4..3f5d8cae63f 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs @@ -76,9 +76,11 @@ fn constant_bytes(scalar: &Scalar) -> VortexResult> { .value() .map(|s| s.as_str().as_bytes().to_vec()), DType::Binary(_) => scalar.as_binary().value().map(|b| b.to_vec()), - _ => vortex_bail!("expected utf8 or binary scalar, got {}", scalar.dtype()), + _ => { + vortex_bail!(MismatchedTypes: "expected utf8 or binary scalar, got {}", scalar.dtype()) + } }; - value.ok_or_else(|| vortex_err!("null constant handled by execute_compare")) + value.ok_or_else(|| vortex_err!(AssertionFailed: "null constant handled by execute_compare")) } /// Compare `lhs_view` from `lhs` against `rhs_view` from `rhs` for equality. diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs b/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs index e88e12f11d0..47c0dd92299 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs @@ -46,11 +46,9 @@ enum DecimalOperand { impl DecimalOperand { fn try_new(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { if let Some(constant) = array.as_opt::() { - let value = constant - .scalar() - .as_decimal() - .decimal_value() - .ok_or_else(|| vortex_err!("null constant handled by execute_compare"))?; + let value = constant.scalar().as_decimal().decimal_value().ok_or_else( + || vortex_err!(AssertionFailed: "null constant handled by execute_compare"), + )?; return Ok(Self::Constant { value, validity: if constant.scalar().dtype().is_nullable() { diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs b/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs index 6593af28c6e..b1cb8589190 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs @@ -137,7 +137,7 @@ pub(crate) fn execute_compare( if lhs.len() != rhs.len() { vortex_bail!( - "compare operator requires equal lengths, got {} and {}", + InvalidArgument: "compare operator requires equal lengths, got {} and {}", lhs.len(), rhs.len() ); @@ -183,7 +183,7 @@ fn compare_arrays( && !lhs.dtype().eq_ignore_nullability(rhs.dtype()) { vortex_bail!( - "Cannot compare extension dtypes {} and {}", + MismatchedTypes: "Cannot compare extension dtypes {} and {}", lhs.dtype(), rhs.dtype() ); @@ -195,7 +195,7 @@ fn compare_arrays( if !lhs.dtype().eq_ignore_nullability(rhs.dtype()) { vortex_bail!( - "Cannot compare different DTypes {} and {}", + MismatchedTypes: "Cannot compare different DTypes {} and {}", lhs.dtype(), rhs.dtype() ); @@ -216,7 +216,7 @@ fn compare_arrays( nested::compare_nested(lhs, rhs, op, nullability, ctx) } DType::Union(..) | DType::Variant(_) | DType::Extension(_) => { - vortex_bail!("compare is not supported for dtype {}", lhs.dtype()) + vortex_bail!(InvalidArgument: "compare is not supported for dtype {}", lhs.dtype()) } } } @@ -248,7 +248,7 @@ pub fn scalar_cmp(lhs: &Scalar, rhs: &Scalar, operator: CompareOperator) -> Vort // We use `partial_cmp` to ensure we do not lose a type mismatch error. let ordering = lhs.partial_cmp(rhs).ok_or_else(|| { vortex_err!( - "Cannot compare scalars with incompatible types: {} and {}", + MismatchedTypes: "Cannot compare scalars with incompatible types: {} and {}", lhs.dtype(), rhs.dtype() ) diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs b/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs index ccccc3ca955..6514a1a0336 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs @@ -147,7 +147,7 @@ fn build_values_comparator( ) -> VortexResult { if !lhs.dtype().eq_ignore_nullability(rhs.dtype()) { vortex_bail!( - "Cannot compare different DTypes {} and {}", + MismatchedTypes: "Cannot compare different DTypes {} and {}", lhs.dtype(), rhs.dtype() ); @@ -237,7 +237,7 @@ fn build_values_comparator( build_values_comparator(lhs.entries(), rhs.entries(), ctx)? } DType::Union(..) | DType::Variant(_) => { - vortex_bail!("compare is not supported for dtype {}", lhs.dtype()) + vortex_bail!(InvalidArgument: "compare is not supported for dtype {}", lhs.dtype()) } }) } diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs b/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs index a1da5a84097..b38b21f67e4 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs @@ -57,7 +57,7 @@ fn compare_primitive_typed( let rhs = PrimitiveOperand::::try_new(rhs, ctx)?; if lhs.len() != rhs.len() { vortex_bail!( - "compare operator requires equal lengths, got {} and {}", + InvalidArgument: "compare operator requires equal lengths, got {} and {}", lhs.len(), rhs.len() ); diff --git a/vortex-array/src/scalar_fn/fns/binary/mod.rs b/vortex-array/src/scalar_fn/fns/binary/mod.rs index 42cebc8401c..2e2bdb53dcb 100644 --- a/vortex-array/src/scalar_fn/fns/binary/mod.rs +++ b/vortex-array/src/scalar_fn/fns/binary/mod.rs @@ -153,7 +153,7 @@ impl ScalarFnVTable for Binary { )); } vortex_bail!( - "incompatible types for arithmetic operation: {} {}", + MismatchedTypes: "incompatible types for arithmetic operation: {} {}", lhs, rhs ); @@ -164,13 +164,13 @@ impl ScalarFnVTable for Binary { && !lhs.is_extension() && !rhs.is_extension() { - vortex_bail!("Cannot compare different DTypes {} and {}", lhs, rhs); + vortex_bail!(MismatchedTypes: "Cannot compare different DTypes {} and {}", lhs, rhs); } if matches!(operator, Operator::And | Operator::Or) && !(lhs.is_boolean() && rhs.is_boolean()) { - vortex_bail!("'{operator}' requires bool operands, got {lhs} and {rhs}",); + vortex_bail!(MismatchedTypes: "'{operator}' requires bool operands, got {lhs} and {rhs}",); } Ok(DType::Bool((lhs.is_nullable() || rhs.is_nullable()).into())) diff --git a/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs b/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs index c96aa433ba4..017882482db 100644 --- a/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs +++ b/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs @@ -38,7 +38,7 @@ pub(crate) fn execute_numeric( ) -> VortexResult { vortex_ensure!( lhs.dtype().eq_ignore_nullability(rhs.dtype()), - "numeric operator requires matching types, got {} and {}", + MismatchedTypes: "numeric operator requires matching types, got {} and {}", lhs.dtype(), rhs.dtype() ); @@ -46,14 +46,14 @@ pub(crate) fn execute_numeric( let dtype = lhs.dtype(); vortex_ensure!( matches!(dtype, DType::Primitive(..) | DType::Decimal(..)), - "numeric operator is not supported for dtype {}", + MismatchedTypes: "numeric operator is not supported for dtype {}", dtype ); vortex_ensure_eq!( lhs.len(), rhs.len(), - "numeric operator requires equal lengths" + InvalidArgument: "numeric operator requires equal lengths" ); if lhs.is_empty() { diff --git a/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs b/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs index ff7fbe7ab81..23fbb172d6e 100644 --- a/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs +++ b/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs @@ -69,10 +69,9 @@ impl RowFn for NumericBinary { args: &[DType], visitor: V, ) -> VortexResult { - let ptype = PType::try_from( - args.first() - .ok_or_else(|| vortex_err!("a numeric operator takes two operands, got none"))?, - )?; + let ptype = PType::try_from(args.first().ok_or_else( + || vortex_err!(InvalidArgument: "a numeric operator takes two operands, got none"), + )?)?; match_each_native_ptype!(ptype, |T| { match op { diff --git a/vortex-array/src/scalar_fn/fns/byte_length.rs b/vortex-array/src/scalar_fn/fns/byte_length.rs index afdf77d118d..73c09a983cc 100644 --- a/vortex-array/src/scalar_fn/fns/byte_length.rs +++ b/vortex-array/src/scalar_fn/fns/byte_length.rs @@ -98,7 +98,9 @@ impl ScalarFnVTable for ByteLength { DType::Utf8(nullable) | DType::Binary(nullable) => { Ok(DType::Primitive(PType::U64, *nullable)) } - other => vortex_bail!("byte_length() requires Utf8 or Binary, got {other}"), + other => { + vortex_bail!(InvalidArgument: "byte_length() requires Utf8 or Binary, got {other}") + } } } @@ -118,7 +120,9 @@ impl ScalarFnVTable for ByteLength { match input.dtype() { DType::Utf8(_) | DType::Binary(_) => byte_length(&input, nullability, ctx), - other => vortex_bail!("byte_length() requires Utf8 or Binary, got {other}"), + other => { + vortex_bail!(InvalidArgument: "byte_length() requires Utf8 or Binary, got {other}") + } } } @@ -147,7 +151,9 @@ fn scalar_byte_length(scalar: &Scalar, nullability: Nullability) -> VortexResult .value() .vortex_expect("null binary scalar") .len(), - other => vortex_bail!("byte_length() requires Utf8 or Binary, got {other}"), + other => { + vortex_bail!(InvalidArgument: "byte_length() requires Utf8 or Binary, got {other}") + } }; let len: u64 = len.as_(); Ok(Scalar::primitive(len, nullability)) diff --git a/vortex-array/src/scalar_fn/fns/case_when.rs b/vortex-array/src/scalar_fn/fns/case_when.rs index 1a2e7f6abb5..5e26eb5e9f0 100644 --- a/vortex-array/src/scalar_fn/fns/case_when.rs +++ b/vortex-array/src/scalar_fn/fns/case_when.rs @@ -98,14 +98,14 @@ impl ScalarFnVTable for CaseWhen { fn serialize(&self, options: &Self::Options) -> VortexResult>> { vortex_ensure!( options.num_when_then_pairs > 0, - "CaseWhen must have at least one WHEN/THEN pair" + InvalidArgument: "CaseWhen must have at least one WHEN/THEN pair" ); let Some(num_children) = options .num_when_then_pairs .checked_mul(2) .and_then(|count| count.checked_add(u32::from(options.has_else))) else { - vortex_bail!("CaseWhen has too many children to serialize"); + vortex_bail!(Overflow: "CaseWhen has too many children to serialize"); }; Ok(Some(pb::CaseWhenOpts { num_children }.encode_to_vec())) } @@ -118,7 +118,7 @@ impl ScalarFnVTable for CaseWhen { let opts = pb::CaseWhenOpts::decode(metadata)?; if opts.num_children < 2 { vortex_bail!( - "CaseWhen expects at least 2 children, got {}", + InvalidArgument: "CaseWhen expects at least 2 children, got {}", opts.num_children ); } @@ -172,13 +172,13 @@ impl ScalarFnVTable for CaseWhen { fn return_dtype(&self, options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { if options.num_when_then_pairs == 0 { - vortex_bail!("CaseWhen must have at least one WHEN/THEN pair"); + vortex_bail!(InvalidArgument: "CaseWhen must have at least one WHEN/THEN pair"); } let expected_len = options.num_children(); if arg_dtypes.len() != expected_len { vortex_bail!( - "CaseWhen expects {expected_len} argument dtypes, got {}", + InvalidArgument: "CaseWhen expects {expected_len} argument dtypes, got {}", arg_dtypes.len() ); } @@ -193,7 +193,7 @@ impl ScalarFnVTable for CaseWhen { let then_i = &arg_dtypes[i * 2 + 1]; let Some(union) = zip_nullability_union(&result_dtype, then_i) else { vortex_bail!( - "CaseWhen THEN dtypes must match (ignoring nullability), got {} and {}", + MismatchedTypes: "CaseWhen THEN dtypes must match (ignoring nullability), got {} and {}", first_then, then_i ); @@ -205,7 +205,7 @@ impl ScalarFnVTable for CaseWhen { let else_dtype = &arg_dtypes[options.num_when_then_pairs as usize * 2]; let Some(union) = zip_nullability_union(&result_dtype, else_dtype) else { vortex_bail!( - "CaseWhen THEN and ELSE dtypes must match (ignoring nullability), got {} and {}", + MismatchedTypes: "CaseWhen THEN and ELSE dtypes must match (ignoring nullability), got {} and {}", first_then, else_dtype ); diff --git a/vortex-array/src/scalar_fn/fns/cast/mod.rs b/vortex-array/src/scalar_fn/fns/cast/mod.rs index f3d90cf05fc..0f4da74ade8 100644 --- a/vortex-array/src/scalar_fn/fns/cast/mod.rs +++ b/vortex-array/src/scalar_fn/fns/cast/mod.rs @@ -91,7 +91,7 @@ impl ScalarFnVTable for Cast { DType::from_proto( proto .as_ref() - .ok_or_else(|| vortex_err!("Missing target dtype in Cast expression"))?, + .ok_or_else(|| vortex_err!(Serde: "Missing target dtype in Cast expression"))?, session, ) } @@ -140,7 +140,7 @@ impl ScalarFnVTable for Cast { match cast_canonical(canonical, target_dtype, ctx)? { Some(result) => Ok(result), None => vortex_bail!( - "No CastKernel to cast canonical array {} from {} to {}", + NotImplemented: "No CastKernel to cast canonical array {} from {} to {}", canonical.to_array_ref().encoding_id(), canonical.to_array_ref().dtype(), target_dtype, @@ -223,13 +223,13 @@ fn cast_canonical( CanonicalView::Struct(a) => struct_cast(a, dtype, ctx), CanonicalView::Union(_) => { vortex_bail!( - "TODO(connor)[Union]: implement Union casting with conformance coverage for \ + NotImplemented: "TODO(connor)[Union]: implement Union casting with conformance coverage for \ outer nullability changes, including validation of nullable-to-nonnullable casts" ) } CanonicalView::Extension(a) => ::cast(a, dtype), CanonicalView::Variant(_) => { - vortex_bail!("Variant arrays don't support casting") + vortex_bail!(NotImplemented: "Variant arrays don't support casting") } } } @@ -323,9 +323,9 @@ mod tests { ); let optimized = expr.bind(&test_harness::struct_dtype())?.optimize()?; - let scalar = optimized - .as_opt::() - .ok_or_else(|| vortex_err!("expected a bare literal, got {optimized}"))?; + let scalar = optimized.as_opt::().ok_or_else( + || vortex_err!(MismatchedTypes: "expected a bare literal, got {optimized}"), + )?; assert_eq!(scalar, &Scalar::primitive(3.0f64, Nullability::NonNullable)); Ok(()) } @@ -343,9 +343,9 @@ mod tests { ); let optimized = expr.bind(&test_harness::struct_dtype())?.optimize()?; - let scalar = optimized - .as_opt::() - .ok_or_else(|| vortex_err!("expected a bare literal, got {optimized}"))?; + let scalar = optimized.as_opt::().ok_or_else( + || vortex_err!(MismatchedTypes: "expected a bare literal, got {optimized}"), + )?; assert_eq!( scalar, &Scalar::primitive(3.19f64, Nullability::NonNullable) diff --git a/vortex-array/src/scalar_fn/fns/dynamic.rs b/vortex-array/src/scalar_fn/fns/dynamic.rs index 7ce5a17dd3b..4c6e835997c 100644 --- a/vortex-array/src/scalar_fn/fns/dynamic.rs +++ b/vortex-array/src/scalar_fn/fns/dynamic.rs @@ -85,7 +85,7 @@ impl ScalarFnVTable for DynamicComparison { let lhs = &arg_dtypes[0]; if !dynamic.rhs.dtype.eq_ignore_nullability(lhs) { vortex_bail!( - "Incompatible dtypes for dynamic comparison: expected {} (ignore nullability) but got {}", + MismatchedTypes: "Incompatible dtypes for dynamic comparison: expected {} (ignore nullability) but got {}", &dynamic.rhs.dtype, lhs ); diff --git a/vortex-array/src/scalar_fn/fns/ext_storage.rs b/vortex-array/src/scalar_fn/fns/ext_storage.rs index 1e708cf2414..75f054ae278 100644 --- a/vortex-array/src/scalar_fn/fns/ext_storage.rs +++ b/vortex-array/src/scalar_fn/fns/ext_storage.rs @@ -57,7 +57,7 @@ impl ScalarFnVTable for ExtStorage { fn return_dtype(&self, _options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { let DType::Extension(ext_dtype) = &arg_dtypes[0] else { - vortex_bail!("ext_storage() requires Extension, got {}", arg_dtypes[0]); + vortex_bail!(InvalidArgument: "ext_storage() requires Extension, got {}", arg_dtypes[0]); }; Ok(ext_dtype.storage_dtype().clone()) @@ -72,7 +72,7 @@ impl ScalarFnVTable for ExtStorage { let input = args.get(0)?; if !matches!(input.dtype(), DType::Extension(_)) { - vortex_bail!("ext_storage() requires Extension, got {}", input.dtype()); + vortex_bail!(InvalidArgument: "ext_storage() requires Extension, got {}", input.dtype()); } if let Some(scalar) = input.as_constant() { diff --git a/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs b/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs index 1fdcf1c2d76..853f5449b0d 100644 --- a/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs +++ b/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs @@ -70,7 +70,7 @@ pub(super) fn short_circuit( ) -> VortexResult> { vortex_ensure!( !fill_value.is_null(), - "fill_null requires a non-null fill value" + InvalidArgument: "fill_null requires a non-null fill value" ); // If the array has no nulls, fill_null is a no-op (just cast for nullability). diff --git a/vortex-array/src/scalar_fn/fns/fill_null/mod.rs b/vortex-array/src/scalar_fn/fns/fill_null/mod.rs index 5d17aaa68b8..9450a945ac6 100644 --- a/vortex-array/src/scalar_fn/fns/fill_null/mod.rs +++ b/vortex-array/src/scalar_fn/fns/fill_null/mod.rs @@ -105,7 +105,7 @@ impl ScalarFnVTable for FillNull { fn return_dtype(&self, _options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { vortex_ensure!( arg_dtypes[0].eq_ignore_nullability(&arg_dtypes[1]), - "fill_null requires input and fill value to have the same base type, got {} and {}", + MismatchedTypes: "fill_null requires input and fill value to have the same base type, got {} and {}", arg_dtypes[0], arg_dtypes[1] ); @@ -137,7 +137,7 @@ impl ScalarFnVTable for FillNull { // than a constant. An empty input has no nulls to fill, so there is nothing to do. vortex_ensure!( input.is_empty(), - "fill_null fill_value must be a constant/scalar" + InvalidArgument: "fill_null fill_value must be a constant/scalar" ); let dtype = input .dtype() @@ -147,7 +147,7 @@ impl ScalarFnVTable for FillNull { vortex_ensure!( !fill_scalar.is_null(), - "fill_null requires a non-null fill value" + InvalidArgument: "fill_null requires a non-null fill value" ); let Some(columnar) = input.as_opt::() else { @@ -216,19 +216,25 @@ fn fill_null_canonical( } match canonical { CanonicalView::Bool(a) => ::fill_null(a, fill_value, ctx)? - .ok_or_else(|| vortex_err!("FillNullKernel for BoolArray returned None")), + .ok_or_else( + || vortex_err!(AssertionFailed: "FillNullKernel for BoolArray returned None"), + ), CanonicalView::Primitive(a) => { - ::fill_null(a, fill_value, ctx)? - .ok_or_else(|| vortex_err!("FillNullKernel for PrimitiveArray returned None")) + ::fill_null(a, fill_value, ctx)?.ok_or_else( + || vortex_err!(AssertionFailed: "FillNullKernel for PrimitiveArray returned None"), + ) } CanonicalView::Decimal(a) => ::fill_null(a, fill_value, ctx)? - .ok_or_else(|| vortex_err!("FillNullKernel for DecimalArray returned None")), + .ok_or_else( + || vortex_err!(AssertionFailed: "FillNullKernel for DecimalArray returned None"), + ), CanonicalView::VarBinView(a) => { - ::fill_null(a, fill_value, ctx)? - .ok_or_else(|| vortex_err!("FillNullKernel for VarBinViewArray returned None")) + ::fill_null(a, fill_value, ctx)?.ok_or_else( + || vortex_err!(AssertionFailed: "FillNullKernel for VarBinViewArray returned None"), + ) } other => vortex_bail!( - "No FillNullKernel for canonical array {}", + NotImplemented: "No FillNullKernel for canonical array {}", other.to_array_ref().encoding_id() ), } diff --git a/vortex-array/src/scalar_fn/fns/get_item.rs b/vortex-array/src/scalar_fn/fns/get_item.rs index 663e3eebdbf..b49c1020a4b 100644 --- a/vortex-array/src/scalar_fn/fns/get_item.rs +++ b/vortex-array/src/scalar_fn/fns/get_item.rs @@ -157,7 +157,7 @@ impl ScalarFnVTable for GetItem { .as_struct_fields_opt() .and_then(|st| st.field(field_name)) .ok_or_else(|| { - vortex_err!("Couldn't find the {} field in the input scope", field_name) + vortex_err!(NotFound: "Couldn't find the {} field in the input scope", field_name) })?; // Match here to avoid cloning the dtype if nullability doesn't need to change @@ -189,7 +189,7 @@ impl ScalarFnVTable for GetItem { .field(field_name) .ok_or_else(|| { vortex_err!( - "Field '{}' missing from constant struct array {}", + NotFound: "Field '{}' missing from constant struct array {}", field_name, input.dtype() ) diff --git a/vortex-array/src/scalar_fn/fns/is_nan.rs b/vortex-array/src/scalar_fn/fns/is_nan.rs index c8059a4e6ab..f6aebc48630 100755 --- a/vortex-array/src/scalar_fn/fns/is_nan.rs +++ b/vortex-array/src/scalar_fn/fns/is_nan.rs @@ -38,7 +38,7 @@ impl RowFn for IsNan { ) -> VortexResult { let ptype = match args { [DType::Primitive(ptype, _)] if ptype.is_float() => *ptype, - _ => vortex_bail!("is_nan expects a single float input, got {args:?}"), + _ => vortex_bail!(InvalidArgument: "is_nan expects a single float input, got {args:?}"), }; match_each_float_ptype!(ptype, |T| { visitor.visit_bool::<(T,), false>(|(value,)| value.is_nan()) diff --git a/vortex-array/src/scalar_fn/fns/like/mod.rs b/vortex-array/src/scalar_fn/fns/like/mod.rs index da0d094c201..17402584eea 100644 --- a/vortex-array/src/scalar_fn/fns/like/mod.rs +++ b/vortex-array/src/scalar_fn/fns/like/mod.rs @@ -145,11 +145,11 @@ impl ScalarFnVTable for Like { let pattern = &arg_dtypes[1]; if !input.is_utf8() { - vortex_bail!("LIKE expression requires UTF8 input dtype, got {}", input); + vortex_bail!(InvalidArgument: "LIKE expression requires UTF8 input dtype, got {}", input); } if !pattern.is_utf8() { vortex_bail!( - "LIKE expression requires UTF8 pattern dtype, got {}", + InvalidArgument: "LIKE expression requires UTF8 pattern dtype, got {}", pattern ); } @@ -244,8 +244,9 @@ pub(crate) fn execute_like( let compiled = match &cached { Some((bytes, compiled)) if *bytes == pattern_bytes => compiled, _ => { - let pattern_str = std::str::from_utf8(pattern_bytes) - .map_err(|e| vortex_err!("LIKE pattern is not valid UTF-8: {e}"))?; + let pattern_str = std::str::from_utf8(pattern_bytes).map_err( + |e| vortex_err!(InvalidArgument: "LIKE pattern is not valid UTF-8: {e}"), + )?; let compiled = LikePattern::compile( pattern_str, options.case_insensitive, diff --git a/vortex-array/src/scalar_fn/fns/like/pattern.rs b/vortex-array/src/scalar_fn/fns/like/pattern.rs index ced63d033d8..e6a89fb84ea 100644 --- a/vortex-array/src/scalar_fn/fns/like/pattern.rs +++ b/vortex-array/src/scalar_fn/fns/like/pattern.rs @@ -189,7 +189,7 @@ fn regex_like(pattern: &str, case_insensitive: bool) -> VortexResult { .case_insensitive(case_insensitive) .dot_matches_new_line(true) .build() - .map_err(|e| vortex_err!("Unable to build regex from LIKE pattern: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "Unable to build regex from LIKE pattern: {e}")) } #[cfg(test)] diff --git a/vortex-array/src/scalar_fn/fns/list_contains/mod.rs b/vortex-array/src/scalar_fn/fns/list_contains/mod.rs index 5d92baac6f6..941767c08e8 100644 --- a/vortex-array/src/scalar_fn/fns/list_contains/mod.rs +++ b/vortex-array/src/scalar_fn/fns/list_contains/mod.rs @@ -181,13 +181,13 @@ impl ScalarFnVTable for ListContains { let DType::List(element_dtype, _) = list_dtype else { vortex_bail!( - "First argument to ListContains must be a List, got {:?}", + MismatchedTypes: "First argument to ListContains must be a List, got {:?}", list_dtype ); }; if !element_dtype.eq_ignore_nullability(needle_dtype) { vortex_bail!( - "Element type {} of list does not match search value {}", + MismatchedTypes: "Element type {} of list does not match search value {}", element_dtype, needle_dtype, ); @@ -297,7 +297,7 @@ fn compute_contains_scalar( ) -> VortexResult { if !matches!(list.dtype(), DType::List(..)) { vortex_bail!( - "First argument to ListContains must be a List, got {}", + MismatchedTypes: "First argument to ListContains must be a List, got {}", list.dtype() ); } @@ -310,7 +310,7 @@ fn compute_contains_scalar( let list_scalar = list.as_list(); let elements = list_scalar .elements() - .ok_or_else(|| vortex_err!("Expected non-null list"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null list"))?; if needle.is_null() { return Ok(if elements.is_empty() && !options.sql_null_semantics { @@ -334,11 +334,11 @@ fn compute_list_contains( ctx: &mut ExecutionCtx, ) -> VortexResult { let DType::List(elem_dtype, _) = array.dtype() else { - vortex_bail!("Array must be of List type"); + vortex_bail!(InvalidArgument: "Array must be of List type"); }; if !elem_dtype.as_ref().eq_ignore_nullability(value.dtype()) { vortex_bail!( - "Element type {} of list does not match search value {}", + MismatchedTypes: "Element type {} of list does not match search value {}", elem_dtype, value.dtype(), ); diff --git a/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs b/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs index aaaf047c1d9..20f0e73ffdc 100644 --- a/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs +++ b/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs @@ -94,15 +94,15 @@ impl PreparedSetData { pub(crate) fn try_from_literal(literal: ScalarFnRef) -> VortexResult { let (has_null_element, is_empty) = { let Some(list) = literal.as_opt::() else { - vortex_bail!("A prepared set needs a literal list"); + vortex_bail!(InvalidArgument: "A prepared set needs a literal list"); }; vortex_ensure!( matches!(list.dtype(), DType::List(..)), - "A prepared set needs a list, got {}", + MismatchedTypes: "A prepared set needs a list, got {}", list.dtype() ); let Some(elements) = list.as_list().element_values() else { - vortex_bail!("A prepared set needs a non-null list"); + vortex_bail!(InvalidArgument: "A prepared set needs a non-null list"); }; (elements.iter().any(Option::is_none), elements.is_empty()) }; @@ -157,7 +157,7 @@ impl PreparedSetData { /// The dtype of the list's elements. fn element_dtype(&self) -> &DType { let DType::List(element_dtype, _) = self.list_dtype() else { - vortex_panic!("A prepared set always holds a list"); + vortex_panic!(AssertionFailed: "A prepared set always holds a list"); }; element_dtype } @@ -234,7 +234,7 @@ impl PreparedSetData { if let Some(len) = needle_validity.maybe_len() { vortex_ensure!( len == bits.len(), - "Needle validity has {len} rows, but there are {} membership bits", + InvalidArgument: "Needle validity has {len} rows, but there are {} membership bits", bits.len() ); } @@ -258,7 +258,7 @@ impl PreparedSetData { let element_dtype = self.element_dtype(); if !element_dtype.eq_ignore_nullability(needle_dtype) { vortex_bail!( - "Element type {} of list does not match search value {}", + MismatchedTypes: "Element type {} of list does not match search value {}", element_dtype, needle_dtype, ); diff --git a/vortex-array/src/scalar_fn/fns/list_length.rs b/vortex-array/src/scalar_fn/fns/list_length.rs index f88e2baf80d..67f9c3049fb 100644 --- a/vortex-array/src/scalar_fn/fns/list_length.rs +++ b/vortex-array/src/scalar_fn/fns/list_length.rs @@ -78,7 +78,9 @@ impl ScalarFnVTable for ListLength { DType::List(_, nullable) | DType::FixedSizeList(_, _, nullable) => { Ok(DType::Primitive(PType::U64, *nullable)) } - other => vortex_bail!("list_length() requires List or FixedSizeList, got {other}"), + other => { + vortex_bail!(InvalidArgument: "list_length() requires List or FixedSizeList, got {other}") + } } } @@ -141,7 +143,7 @@ pub(crate) fn list_length( (lengths, l.list_validity()) } else { let dtype = any_list.dtype(); - vortex_bail!("list_length() requires List, ListView, or FixedSizeList but got {dtype}") + vortex_bail!(InvalidArgument: "list_length() requires List, ListView, or FixedSizeList but got {dtype}") }; // Cast to `U64` diff --git a/vortex-array/src/scalar_fn/fns/list_sum.rs b/vortex-array/src/scalar_fn/fns/list_sum.rs index 0e83a22ed3b..2baf541d058 100644 --- a/vortex-array/src/scalar_fn/fns/list_sum.rs +++ b/vortex-array/src/scalar_fn/fns/list_sum.rs @@ -72,11 +72,13 @@ impl ScalarFnVTable for ListSum { fn return_dtype(&self, options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { let elem_dtype = match &arg_dtypes[0] { DType::List(elem, _) | DType::FixedSizeList(elem, ..) => elem.as_ref(), - other => vortex_bail!("list_sum() requires List or FixedSizeList, got {other}"), + other => { + vortex_bail!(InvalidArgument: "list_sum() requires List or FixedSizeList, got {other}") + } }; - SumV2 - .return_dtype(options, elem_dtype) - .ok_or_else(|| vortex_err!("list_sum() cannot sum elements of type {elem_dtype}")) + SumV2.return_dtype(options, elem_dtype).ok_or_else( + || vortex_err!(MismatchedTypes: "list_sum() cannot sum elements of type {elem_dtype}"), + ) } fn execute( @@ -89,7 +91,9 @@ impl ScalarFnVTable for ListSum { let elem_dtype = match input.dtype() { DType::List(elem, _) | DType::FixedSizeList(elem, ..) => elem.as_ref().clone(), - other => vortex_bail!("list_sum() requires List or FixedSizeList, got {other}"), + other => { + vortex_bail!(InvalidArgument: "list_sum() requires List or FixedSizeList, got {other}") + } }; let columnar = input.execute::(ctx)?; diff --git a/vortex-array/src/scalar_fn/fns/literal.rs b/vortex-array/src/scalar_fn/fns/literal.rs index cb6c3284523..1d7aaa09a6a 100644 --- a/vortex-array/src/scalar_fn/fns/literal.rs +++ b/vortex-array/src/scalar_fn/fns/literal.rs @@ -55,7 +55,7 @@ impl ScalarFnVTable for Literal { Scalar::from_proto( ops.value .as_ref() - .ok_or_else(|| vortex_err!("Literal metadata missing value"))?, + .ok_or_else(|| vortex_err!(NotFound: "Literal metadata missing value"))?, session, ) } diff --git a/vortex-array/src/scalar_fn/fns/mask/kernel.rs b/vortex-array/src/scalar_fn/fns/mask/kernel.rs index b03c2dd5509..3732f1bcf0d 100644 --- a/vortex-array/src/scalar_fn/fns/mask/kernel.rs +++ b/vortex-array/src/scalar_fn/fns/mask/kernel.rs @@ -82,7 +82,7 @@ where let parent_ref: ArrayRef = (*parent).clone(); let mask_child = parent_ref .nth_child(1) - .ok_or_else(|| vortex_err!("Mask expression must have 2 children"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Mask expression must have 2 children"))?; if mask_child.as_opt::().is_none() && mask_child.as_opt::().is_none() { let can_attach_mask = @@ -120,7 +120,7 @@ where } let mask_child = parent .nth_child(1) - .ok_or_else(|| vortex_err!("Mask expression must have 2 children"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Mask expression must have 2 children"))?; ::mask(array, mask_child, ctx) } } diff --git a/vortex-array/src/scalar_fn/fns/mask/mod.rs b/vortex-array/src/scalar_fn/fns/mask/mod.rs index 994c409adc3..82244fdafd8 100644 --- a/vortex-array/src/scalar_fn/fns/mask/mod.rs +++ b/vortex-array/src/scalar_fn/fns/mask/mod.rs @@ -94,7 +94,7 @@ impl ScalarFnVTable for Mask { vortex_ensure_eq!( arg_dtypes[1], DType::Bool(Nullability::NonNullable), - "The mask argument to 'mask' must be a non-nullable boolean array" + MismatchedTypes: "The mask argument to 'mask' must be a non-nullable boolean array" ); Ok(arg_dtypes[0].as_nullable()) } diff --git a/vortex-array/src/scalar_fn/fns/merge.rs b/vortex-array/src/scalar_fn/fns/merge.rs index 4913b120000..0470453d488 100644 --- a/vortex-array/src/scalar_fn/fns/merge.rs +++ b/vortex-array/src/scalar_fn/fns/merge.rs @@ -68,7 +68,7 @@ impl ScalarFnVTable for Merge { [0x00] => DuplicateHandling::RightMost, [0x01] => DuplicateHandling::Error, _ => { - vortex_bail!("invalid metadata for Merge expression"); + vortex_bail!(InvalidArgument: "invalid metadata for Merge expression"); } }; Ok(instance) @@ -90,10 +90,10 @@ impl ScalarFnVTable for Merge { for dtype in arg_dtypes { let Some(fields) = dtype.as_struct_fields_opt() else { - vortex_bail!("merge expects struct input"); + vortex_bail!(InvalidArgument: "merge expects struct input"); }; if dtype.is_nullable() { - vortex_bail!("merge expects non-nullable input"); + vortex_bail!(InvalidArgument: "merge expects non-nullable input"); } merge_nullability |= dtype.nullability(); @@ -111,7 +111,7 @@ impl ScalarFnVTable for Merge { if options == &DuplicateHandling::Error && !duplicate_names.is_empty() { vortex_bail!( - "merge: duplicate fields in children: {}", + InvalidArgument: "merge: duplicate fields in children: {}", duplicate_names.into_iter().format(", ") ) } @@ -136,7 +136,7 @@ impl ScalarFnVTable for Merge { for i in 0..args.num_inputs() { let array = args.get(i)?.execute::(ctx)?; if array.dtype().is_nullable() { - vortex_bail!("merge expects non-nullable input"); + vortex_bail!(InvalidArgument: "merge expects non-nullable input"); } for (field_name, field_array) in array @@ -157,7 +157,7 @@ impl ScalarFnVTable for Merge { if options == &DuplicateHandling::Error && !duplicate_names.is_empty() { vortex_bail!( - "merge: duplicate fields in children: {}", + InvalidArgument: "merge: duplicate fields in children: {}", duplicate_names.into_iter().format(", ") ) } @@ -180,7 +180,7 @@ impl ScalarFnVTable for Merge { let child_dtype = child.node_dtype()?; if !child_dtype.is_struct() || child_dtype.is_nullable() { vortex_bail!( - "Merge child must return a non-nullable struct dtype, got {}", + MismatchedTypes: "Merge child must return a non-nullable struct dtype, got {}", child_dtype ) } @@ -207,7 +207,7 @@ impl ScalarFnVTable for Merge { if options == &DuplicateHandling::Error && !duplicate_names.is_empty() { vortex_bail!( - "merge: duplicate fields in children: {}", + InvalidArgument: "merge: duplicate fields in children: {}", duplicate_names.into_iter().format(", ") ) } @@ -289,7 +289,7 @@ mod tests { let mut field_path = field_path.iter(); let Some(field) = field_path.next() else { - vortex_bail!("empty field path"); + vortex_bail!(InvalidArgument: "empty field path"); }; let mut array = array diff --git a/vortex-array/src/scalar_fn/fns/not/mod.rs b/vortex-array/src/scalar_fn/fns/not/mod.rs index b4c0c1b3bb5..dd9ef935be9 100644 --- a/vortex-array/src/scalar_fn/fns/not/mod.rs +++ b/vortex-array/src/scalar_fn/fns/not/mod.rs @@ -78,7 +78,7 @@ impl ScalarFnVTable for Not { let child_dtype = &arg_dtypes[0]; if !matches!(child_dtype, DType::Bool(_)) { vortex_bail!( - "Not expression expects a boolean child, got: {}", + InvalidArgument: "Not expression expects a boolean child, got: {}", child_dtype ); } diff --git a/vortex-array/src/scalar_fn/fns/pack.rs b/vortex-array/src/scalar_fn/fns/pack.rs index c9e5a60ec3a..9eac75a8e89 100644 --- a/vortex-array/src/scalar_fn/fns/pack.rs +++ b/vortex-array/src/scalar_fn/fns/pack.rs @@ -201,7 +201,7 @@ mod tests { let mut field_path = field_path.iter(); let Some(field) = field_path.next() else { - vortex_bail!("empty field path"); + vortex_bail!(InvalidArgument: "empty field path"); }; let mut array = array diff --git a/vortex-array/src/scalar_fn/fns/replace_time_zone.rs b/vortex-array/src/scalar_fn/fns/replace_time_zone.rs index a07029cfe70..7c9d5f65f17 100644 --- a/vortex-array/src/scalar_fn/fns/replace_time_zone.rs +++ b/vortex-array/src/scalar_fn/fns/replace_time_zone.rs @@ -131,11 +131,11 @@ impl ScalarFnVTable for ReplaceTimeZone { fn return_dtype(&self, options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { let input = timestamp_options(&arg_dtypes[0])?; if input.unit == TimeUnit::Days { - vortex_bail!("Timestamp cannot use day units"); + vortex_bail!(InvalidArgument: "Timestamp cannot use day units"); } if !matches!(arg_dtypes[1], DType::Utf8(_) | DType::Null) { vortex_bail!( - "replace_time_zone() requires a UTF-8 ambiguity policy, got {}", + MismatchedTypes: "replace_time_zone() requires a UTF-8 ambiguity policy, got {}", arg_dtypes[1] ); } @@ -238,7 +238,7 @@ fn replace_scalar( let policy = policy .as_utf8() .value() - .ok_or_else(|| vortex_err!("Missing ambiguity policy"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "Missing ambiguity policy"))?; replace( i64::try_from(&storage)?, metadata.unit, @@ -261,7 +261,7 @@ fn timestamp_options(dtype: &DType) -> VortexResult<&TimestampOptions> { { return Ok(options); } - vortex_bail!("replace_time_zone() requires Timestamp, got {dtype}") + vortex_bail!(MismatchedTypes: "replace_time_zone() requires Timestamp, got {dtype}") } fn replace( @@ -274,7 +274,7 @@ fn replace( ) -> VortexResult> { if !matches!(policy, "raise" | "earliest" | "latest" | "null") { vortex_bail!( - "Invalid ambiguity policy {policy:?}: expected raise, earliest, latest, or null" + InvalidArgument: "Invalid ambiguity policy {policy:?}: expected raise, earliest, latest, or null" ); } // Keeping the same timezone does not introduce a new ambiguity to reject. @@ -286,7 +286,7 @@ fn replace( TimeUnit::Milliseconds => JiffTimestamp::from_millisecond(value)?, TimeUnit::Microseconds => JiffTimestamp::from_microsecond(value)?, TimeUnit::Nanoseconds => JiffTimestamp::from_nanosecond(i128::from(value))?, - TimeUnit::Days => vortex_bail!("Timestamp cannot use day units"), + TimeUnit::Days => vortex_bail!(InvalidArgument: "Timestamp cannot use day units"), }; let wall_time = source.to_datetime(timestamp); let ambiguous = target.to_ambiguous_timestamp(wall_time); @@ -306,7 +306,7 @@ fn replace( TimeUnit::Milliseconds => timestamp.as_millisecond(), TimeUnit::Microseconds => timestamp.as_microsecond(), TimeUnit::Nanoseconds => i64::try_from(timestamp.as_nanosecond()) - .map_err(|e| vortex_err!("Timestamp overflow: {e}"))?, + .map_err(|e| vortex_err!(Overflow: "Timestamp overflow: {e}"))?, TimeUnit::Days => unreachable!(), })) } @@ -476,9 +476,9 @@ mod tests { let optimized = expr.bind(&scope)?.optimize()?; // Stats pruning only matches bare literal operands, so the replacement must fold. - let scalar = optimized - .as_opt::() - .ok_or_else(|| vortex_err!("expected a bare literal, got {optimized}"))?; + let scalar = optimized.as_opt::().ok_or_else( + || vortex_err!(MismatchedTypes: "expected a bare literal, got {optimized}"), + )?; assert_eq!( scalar, &Scalar::extension_ref( diff --git a/vortex-array/src/scalar_fn/fns/select.rs b/vortex-array/src/scalar_fn/fns/select.rs index e410105d1b4..29527ce591b 100644 --- a/vortex-array/src/scalar_fn/fns/select.rs +++ b/vortex-array/src/scalar_fn/fns/select.rs @@ -80,7 +80,7 @@ impl ScalarFnVTable for Select { let select_opts = prost_metadata .opts - .ok_or_else(|| vortex_err!("SelectOpts missing opts field"))?; + .ok_or_else(|| vortex_err!(Serde: "SelectOpts missing opts field"))?; let field_selection = match select_opts { Opts::Include(field_names) => FieldSelection::Include(FieldNames::from_iter( @@ -130,7 +130,7 @@ impl ScalarFnVTable for Select { let child_dtype = &arg_dtypes[0]; let child_struct_dtype = child_dtype .as_struct_fields_opt() - .ok_or_else(|| vortex_err!("Select child not a struct dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Select child not a struct dtype"))?; let projected = match selection { FieldSelection::Include(fields) => child_struct_dtype.project(fields.as_ref())?, @@ -157,7 +157,7 @@ impl ScalarFnVTable for Select { let child_struct_dtype = child .dtype() .as_struct_fields_opt() - .ok_or_else(|| vortex_err!("Select child not a struct dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Select child not a struct dtype"))?; let included = selection.normalize_to_included_fields(child_struct_dtype.names())?; let scalar = constant.scalar().as_struct().project(included.as_ref())?; @@ -193,7 +193,7 @@ impl ScalarFnVTable for Select { let struct_fields = struct_dtype.as_struct_fields_opt().ok_or_else(|| { vortex_err!( - "Select child must return a struct dtype, however it was a {}", + MismatchedTypes: "Select child must return a struct dtype, however it was a {}", struct_dtype ) })?; @@ -248,7 +248,7 @@ impl ScalarFnVTable for Select { .map(|name| { let idx = child_pack.names.find(name).ok_or_else(|| { vortex_err!( - "Cannot find field {} in pack fields {:?}", + NotFound: "Cannot find field {} in pack fields {:?}", name, child_pack.names ) @@ -315,7 +315,7 @@ impl FieldSelection { // Check that all of the field names exist in the available fields. if self.field_names().iter().any(|f| !available.contains(f)) { vortex_bail!( - "Select fields {:?} must be a subset of child fields {:?}", + InvalidArgument: "Select fields {:?} must be a subset of child fields {:?}", self, available_fields ); diff --git a/vortex-array/src/scalar_fn/fns/stat.rs b/vortex-array/src/scalar_fn/fns/stat.rs index c961ac10d53..8609c68c7c3 100644 --- a/vortex-array/src/scalar_fn/fns/stat.rs +++ b/vortex-array/src/scalar_fn/fns/stat.rs @@ -132,7 +132,7 @@ impl ScalarFnVTable for StatFn { fn stat_dtype(aggregate_fn: &AggregateFnRef, input_dtype: &DType) -> VortexResult { let Some(dtype) = aggregate_fn.state_dtype(input_dtype) else { vortex_bail!( - "Aggregate function {} does not support input dtype {}", + InvalidArgument: "Aggregate function {} does not support input dtype {}", aggregate_fn, input_dtype ); diff --git a/vortex-array/src/scalar_fn/fns/variant_get/mod.rs b/vortex-array/src/scalar_fn/fns/variant_get/mod.rs index ef493d0146e..0be78f8d6a9 100644 --- a/vortex-array/src/scalar_fn/fns/variant_get/mod.rs +++ b/vortex-array/src/scalar_fn/fns/variant_get/mod.rs @@ -122,7 +122,7 @@ impl ScalarFnVTable for VariantGet { let input_dtype = &arg_dtypes[0]; vortex_ensure!( matches!(input_dtype, DType::Variant(_)), - "VariantGet input must be Variant, found {input_dtype}" + MismatchedTypes: "VariantGet input must be Variant, found {input_dtype}" ); // Missing paths, traversal mismatches, and cast failures all produce nulls. @@ -367,7 +367,7 @@ impl VariantPathElement { pub fn from_proto(value: pb::VariantPathElement) -> VortexResult { match value .element - .ok_or_else(|| vortex_err!("Variant path element missing value"))? + .ok_or_else(|| vortex_err!(NotFound: "Variant path element missing value"))? { variant_path_element::Element::Field(field) => Ok(Self::field(field)), variant_path_element::Element::Index(index) => Ok(Self::index(index)), @@ -487,7 +487,7 @@ mod tests { .get(pos) .is_some_and(|byte| !matches!(byte, b'.' | b'[')) { - vortex_bail!("Invalid Variant path {path:?}: expected '.' or '[' after '$'"); + vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.' or '[' after '$'"); } while pos < path.len() { @@ -509,7 +509,7 @@ mod tests { pos = next_pos; } _ => { - vortex_bail!("Invalid Variant path {path:?}: expected '.', '[', or end of path") + vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.', '[', or end of path") } } } @@ -528,7 +528,7 @@ mod tests { } vortex_ensure!( pos > start, - "Invalid Variant path {path:?}: expected field name" + InvalidArgument: "Invalid Variant path {path:?}: expected field name" ); Ok((&path[start..pos], pos)) } @@ -544,15 +544,15 @@ mod tests { } vortex_ensure!( pos > start, - "Invalid Variant path {path:?}: expected list index" + InvalidArgument: "Invalid Variant path {path:?}: expected list index" ); vortex_ensure!( path.as_bytes().get(pos) == Some(&b']'), - "Invalid Variant path {path:?}: expected closing ']'" + InvalidArgument: "Invalid Variant path {path:?}: expected closing ']'" ); - let index = path[start..pos] - .parse() - .map_err(|_| vortex_err!("Invalid Variant path {path:?}: list index is too large"))?; + let index = path[start..pos].parse().map_err( + |_| vortex_err!(Overflow: "Invalid Variant path {path:?}: list index is too large"), + )?; Ok((index, pos + 1)) } @@ -826,7 +826,7 @@ mod tests { .execute::(&mut SESSION.create_execution_ctx())?; let canonical = result.execute::(&mut SESSION.create_execution_ctx())?; let Canonical::Variant(canonical_variant) = canonical else { - vortex_bail!("expected Variant canonical array"); + vortex_bail!(InvalidArgument: "expected Variant canonical array"); }; assert_eq!(variant.len(), 2); diff --git a/vortex-array/src/scalar_fn/fns/zip/mod.rs b/vortex-array/src/scalar_fn/fns/zip/mod.rs index fa46512a4f0..57de10db991 100644 --- a/vortex-array/src/scalar_fn/fns/zip/mod.rs +++ b/vortex-array/src/scalar_fn/fns/zip/mod.rs @@ -117,7 +117,7 @@ impl ScalarFnVTable for Zip { fn return_dtype(&self, _options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { vortex_ensure!( matches!(arg_dtypes[2], DType::Bool(_)), - "zip requires mask to be a boolean type, got {}", + MismatchedTypes: "zip requires mask to be a boolean type, got {}", arg_dtypes[2] ); zip_return_dtype(&arg_dtypes[0], &arg_dtypes[1]) @@ -227,7 +227,7 @@ fn zip_impl( fn zip_return_dtype(if_true: &DType, if_false: &DType) -> VortexResult { zip_nullability_union(if_true, if_false).ok_or_else(|| { vortex_err!( - "zip requires if_true and if_false to have the same base type, got {} and {}", + InvalidArgument: "zip requires if_true and if_false to have the same base type, got {} and {}", if_true, if_false ) diff --git a/vortex-array/src/scalar_fn/foreign.rs b/vortex-array/src/scalar_fn/foreign.rs index 667b4756c1c..e880e5370b3 100644 --- a/vortex-array/src/scalar_fn/foreign.rs +++ b/vortex-array/src/scalar_fn/foreign.rs @@ -116,7 +116,7 @@ impl ScalarFnVTable for ForeignScalarFnVTable { _args: &dyn ExecutionArgs, _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!("Cannot execute unknown scalar function '{}'", self.id); + vortex_bail!(NotFound: "Cannot execute unknown scalar function '{}'", self.id); } fn is_strict(&self, _options: &Self::Options) -> bool { diff --git a/vortex-array/src/scalar_fn/internal/row_count.rs b/vortex-array/src/scalar_fn/internal/row_count.rs index bc217db75bf..c7f17598f4b 100644 --- a/vortex-array/src/scalar_fn/internal/row_count.rs +++ b/vortex-array/src/scalar_fn/internal/row_count.rs @@ -80,7 +80,7 @@ impl ScalarFnVTable for RowCount { _args: &dyn ExecutionArgs, _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!("RowCount must be substituted before evaluation") + vortex_bail!(InvalidArgument: "RowCount must be substituted before evaluation") } fn is_strict(&self, _options: &Self::Options) -> bool { @@ -122,12 +122,12 @@ pub fn substitute_row_count(array: ArrayRef, replacement: &ArrayRef) -> VortexRe vortex_ensure_eq!( replacement.len(), array.len(), - "RowCount replacement length does not match scope length", + AssertionFailed: "RowCount replacement length does not match scope length", ); vortex_ensure_eq!( replacement.dtype(), array.dtype(), - "RowCount replacement dtype does not match scope dtype", + AssertionFailed: "RowCount replacement dtype does not match scope dtype", ); return Ok(replacement.clone()); } diff --git a/vortex-array/src/scalar_fn/typed.rs b/vortex-array/src/scalar_fn/typed.rs index ab6db6e098e..ed649691605 100644 --- a/vortex-array/src/scalar_fn/typed.rs +++ b/vortex-array/src/scalar_fn/typed.rs @@ -158,7 +158,7 @@ impl DynScalarFn for TypedScalarFnInstance { vortex_error::vortex_ensure_eq!( result.dtype(), &expected_dtype, - "Expression execution {} returned vector of invalid dtype", + AssertionFailed: "Expression execution {} returned vector of invalid dtype", self.vtable.id(), ); } diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/args.rs b/vortex-array/src/scalar_fn/unstable/row/batch/args.rs index 3f9d7ae7d3d..68debfb61f1 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/args.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/args.rs @@ -65,7 +65,7 @@ impl ExecutionArgs for BorrowedRowFnArgs<'_> { fn get(&self, index: usize) -> VortexResult { self.arrays.get(index).cloned().ok_or_else(|| { vortex_err!( - "row-function input index must be less than {}, got {index}", + InvalidArgument: "row-function input index must be less than {}, got {index}", self.arrays.len(), ) }) diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs b/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs index 6afea5798dd..59adb278ffe 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs @@ -69,7 +69,7 @@ pub(crate) fn finalize_kernel_output( validate_output(id, result_dtype, expected_len, &values)?; vortex_ensure!( values.all_valid(ctx)?, - "the {id} row kernel must produce only valid rows, got at least one null row", + AssertionFailed: "the {id} row kernel must produce only valid rows, got at least one null row", ); cast_output_nullability(result_dtype, values) @@ -85,14 +85,14 @@ fn validate_output( vortex_ensure_eq!( values.len(), expected_len, - "the {id} kernel output has the wrong row count", + AssertionFailed: "the {id} kernel output has the wrong row count", ); let values_with_result_nullability = values.dtype().with_nullability(result_dtype.nullability()); vortex_ensure_eq!( values_with_result_nullability, *result_dtype, - "the {id} output dtype must match the result dtype except for outer nullability", + AssertionFailed: "the {id} output dtype must match the result dtype except for outer nullability", ); Ok(()) diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs b/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs index 1ae3d525437..d3c44e800a1 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs @@ -33,7 +33,7 @@ impl RowFnExecutionArgs { vortex_ensure_eq!( input.len(), row_count, - "the {id} input {index} has the wrong row count", + InvalidArgument: "the {id} input {index} has the wrong row count", ); } diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs b/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs index 532bd30a6f7..d12a8864dc8 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs @@ -184,7 +184,7 @@ unsafe impl InputElement for FilterOnlyI64 { let values = ::decode(array, ctx)?; vortex_ensure!( !values.as_slice().contains(&i64::MIN), - "test input contains an invalid payload", + AssertionFailed: "test input contains an invalid payload", ); Ok(values) @@ -192,7 +192,7 @@ unsafe impl InputElement for FilterOnlyI64 { fn decode_constant(array: ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { let value = ::decode_constant(array, ctx)?; - vortex_ensure!(value != i64::MIN, "test input contains an invalid payload",); + vortex_ensure!(value != i64::MIN, AssertionFailed: "test input contains an invalid payload",); Ok(value) } @@ -384,7 +384,7 @@ impl RowFn for DeferredAdd { |&(), (lhs, rhs)| lhs.overflowing_add(rhs), |overflowed| { if overflowed { - vortex_bail!(InvalidArgument: "deferred addition overflowed"); + vortex_bail!(Overflow: "deferred addition overflowed"); } Ok(()) @@ -459,7 +459,7 @@ impl RowFn for DenseRetryIncrement { |(value,)| value.overflowing_add(1), |overflowed| { if overflowed { - vortex_bail!(InvalidArgument: "deferred increment overflowed"); + vortex_bail!(Overflow: "deferred increment overflowed"); } Ok(()) @@ -728,7 +728,9 @@ fn test_kernel_output_rejects_nulls_at_function_boundary() -> VortexResult<()> { Err(error) => error, Ok(output) => match output.execute::(&mut ctx) { Err(error) => error, - Ok(_) => vortex_bail!("an invalid row kernel output passed boundary validation"), + Ok(_) => { + vortex_bail!(InvalidArgument: "an invalid row kernel output passed boundary validation") + } }, }; let error = error.to_string(); @@ -1030,7 +1032,7 @@ fn test_deferred_bool_output_reports_valid_row_failure() -> VortexResult<()> { let error = match execute_rows(&DeferredGreaterThan::, &EmptyOptions, &args, &mut ctx) { Err(error) => error.to_string(), - Ok(_) => vortex_bail!("a valid-row deferred failure was not reported"), + Ok(_) => vortex_bail!(AssertionFailed: "a valid-row deferred failure was not reported"), }; assert!( diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs b/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs index b73b255223c..153d9bf999b 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs @@ -54,7 +54,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!("a decoded row input does not address exactly {row_count} rows"); + vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); }; Ok(Out::build_from( @@ -136,7 +136,7 @@ where vortex_ensure_eq!( valid.true_count(), filtered_len, - "the filtered batch must contain one row per valid row", + AssertionFailed: "the filtered batch must contain one row per valid row", ); let prepared = prepare(Args::const_values(&columns)); @@ -154,7 +154,7 @@ where if let Some(views) = Args::views_if_no_consts(&columns) { vortex_ensure!( Args::view_lens_match(&views, filtered_len), - "a decoded row input does not address exactly {filtered_len} rows", + AssertionFailed: "a decoded row input does not address exactly {filtered_len} rows", ); valid_rows.for_each_set_index(|index| { @@ -171,7 +171,7 @@ where } else { vortex_ensure!( Args::decoded_lens_match(&columns, filtered_len), - "a decoded row input does not address exactly {filtered_len} rows", + AssertionFailed: "a decoded row input does not address exactly {filtered_len} rows", ); valid_rows.for_each_set_index(|index| { @@ -215,7 +215,7 @@ where vortex_ensure_eq!( valid_rows.len(), row_count, - "the validity mask has the wrong row count", + AssertionFailed: "the validity mask has the wrong row count", ); let prepared = prepare(Args::const_values(&columns)); @@ -231,7 +231,7 @@ where if let Some(views) = Args::views_if_no_consts(&columns) { vortex_ensure!( Args::view_lens_match(&views, row_count), - "a decoded row input does not address exactly {row_count} rows", + AssertionFailed: "a decoded row input does not address exactly {row_count} rows", ); valid_rows.for_each_set_index(|index| { @@ -247,7 +247,7 @@ where } else { vortex_ensure!( Args::decoded_lens_match(&columns, row_count), - "a decoded row input does not address exactly {row_count} rows", + AssertionFailed: "a decoded row input does not address exactly {row_count} rows", ); valid_rows.for_each_set_index(|index| { @@ -290,7 +290,7 @@ where let output = &mut values.slots()[..row_count]; let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!("a decoded row input does not address exactly {row_count} rows"); + vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); }; let failure = source.map_checked_into(output, |elements| apply(&prepared, elements)); diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs b/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs index 5fb3d0cadc1..b7b20082869 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs @@ -41,7 +41,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!("a decoded row input does not address exactly {row_count} rows"); + vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); }; let collect = |index| { @@ -82,7 +82,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!("a decoded row input does not address exactly {row_count} rows"); + vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); }; let mut failure = Fail::default(); @@ -136,7 +136,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!("a decoded row input does not address exactly {row_count} rows"); + vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); }; // NB: The collector must capture one borrow of the whole state. That shape is load-bearing for diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs b/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs index ebf67461e6c..53e83ef6c28 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs @@ -69,7 +69,7 @@ where // Keep this validation beside the views so LLVM sees their common length here. vortex_ensure!( Args::view_lens_match(&views, row_count), - "a decoded row input does not address exactly {row_count} rows", + AssertionFailed: "a decoded row input does not address exactly {row_count} rows", ); // SAFETY: `view_lens_match` checked that these exact retained views address `row_count` @@ -83,7 +83,7 @@ where // LTO. vortex_ensure!( Args::decoded_lens_match(&columns, row_count), - "a decoded row input does not address exactly {row_count} rows", + AssertionFailed: "a decoded row input does not address exactly {row_count} rows", ); let mut accumulated_failure = Fail::default(); diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs b/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs index b964cbb737e..f70471e47c6 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs @@ -56,7 +56,7 @@ where vortex_ensure_eq!( sink_row_count, row_count, - "the output sink has the wrong row count", + AssertionFailed: "the output sink has the wrong row count", ); let views = Args::views_if_no_consts(&columns); @@ -140,7 +140,7 @@ where vortex_ensure_eq!( initialized_row_count, row_count, - "the initialized output sink has the wrong row count", + AssertionFailed: "the initialized output sink has the wrong row count", ); if let Some(views) = views { @@ -204,7 +204,7 @@ where vortex_ensure_eq!( valid.true_count(), filtered_len, - "the filtered batch must contain one row per valid row", + AssertionFailed: "the filtered batch must contain one row per valid row", ); let original_len = valid.len(); @@ -227,7 +227,7 @@ where vortex_ensure_eq!( initialized_row_count, original_len, - "the initialized output sink has the wrong row count", + AssertionFailed: "the initialized output sink has the wrong row count", ); let mut filtered_index = 0; @@ -280,7 +280,7 @@ where #[cold] #[inline(never)] fn decoded_length_error(row_count: usize) -> VortexResult<()> { - vortex_bail!("a decoded row input does not address exactly {row_count} rows") + vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows") } /// State resolved before preparing the skip-invalid row loop. @@ -323,7 +323,7 @@ where vortex_ensure_eq!( valid_rows.len(), row_count, - "the validity mask has the wrong row count", + AssertionFailed: "the validity mask has the wrong row count", ); Ok(Some(ValidRowsSetup { @@ -401,7 +401,7 @@ mod tests { let input = PrimitiveArray::from_iter([10_i64, 20]).into_array(); let args = VecExecutionArgs::new(vec![input], 2); let Mask::Values(valid) = Mask::from_iter([false, true]) else { - vortex_bail!("the test validity must be partially valid"); + vortex_bail!(InvalidArgument: "the test validity must be partially valid"); }; let mut ctx = SESSION.create_execution_ctx(); @@ -418,7 +418,9 @@ mod tests { let error = match result { Err(error) => error, - Ok(_) => vortex_bail!("the sink must reject rows changed by its initializer"), + Ok(_) => { + vortex_bail!(AssertionFailed: "the sink must reject rows changed by its initializer") + } }; assert!( error diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs b/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs index 3fd72339f4d..f3893baa323 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs @@ -104,7 +104,7 @@ fn collect_owned( |_| (), |_, (value,)| apply(value), )? - .ok_or_else(|| vortex_err!("canonical input must support selected rows")), + .ok_or_else(|| vortex_err!(AssertionFailed: "canonical input must support selected rows")), Traversal::Filtered => execute_owned_infallible_filtered::<(i64,), Out, ()>( args, valid, @@ -233,7 +233,7 @@ fn packed_boolean_payload_uses_allocator( DenseAttempt::DeferredError(error) => return Err(error), } } - _ => vortex_bail!("this test traversal requires packed Boolean output"), + _ => vortex_bail!(InvalidArgument: "this test traversal requires packed Boolean output"), }; tracker.assert_owns(output.as_::().to_bit_buffer().inner().as_slice()); assert_eq!(tracker.live_allocations(), 1); @@ -268,7 +268,7 @@ where |_| (), |_, _, row| apply(row), )? - .ok_or_else(|| vortex_err!("canonical input must support selected rows")), + .ok_or_else(|| vortex_err!(AssertionFailed: "canonical input must support selected rows")), Traversal::Filtered => execute_sink_filtered::<(i64,), (), Sink, ApplyResult>( args, valid, @@ -277,7 +277,7 @@ where |_| (), |_, _, row| apply(row), ), - _ => vortex_bail!("this test traversal requires an owned output"), + _ => vortex_bail!(InvalidArgument: "this test traversal requires an owned output"), } } diff --git a/vortex-array/src/scalar_fn/unstable/row/row_fn.rs b/vortex-array/src/scalar_fn/unstable/row/row_fn.rs index edf2f9371d0..0d677e425c6 100644 --- a/vortex-array/src/scalar_fn/unstable/row/row_fn.rs +++ b/vortex-array/src/scalar_fn/unstable/row/row_fn.rs @@ -75,7 +75,7 @@ pub trait RowFn: 'static + Sized + Clone + Send + Sync { _metadata: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!("Expression {} is not deserializable", self.id()) + vortex_bail!(Serde: "Expression {} is not deserializable", self.id()) } /// Choose element types for these input dtypes and visit the framework with them. diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs index 9b517ef89d9..712efa9ff59 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs @@ -38,7 +38,7 @@ unsafe impl InputElement for bool { fn validate(dtype: &DType) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Bool(_)), - "expected a Bool column, got {dtype}", + MismatchedTypes: "expected a Bool column, got {dtype}", ); Ok(()) } @@ -50,13 +50,13 @@ unsafe impl InputElement for bool { fn decode_constant(array: ArrayRef, _ctx: &mut ExecutionCtx) -> VortexResult { let Some(constant) = array.as_opt::() else { vortex_bail!( - "a Boolean batch constant must use the Constant encoding, got {}", + MismatchedTypes: "a Boolean batch constant must use the Constant encoding, got {}", array.encoding_id() ); }; let scalar = constant.scalar(); let Some(ScalarValue::Bool(value)) = scalar.value() else { - vortex_bail!("a Boolean batch constant must contain a non-null value, got {scalar}"); + vortex_bail!(InvalidArgument: "a Boolean batch constant must contain a non-null value, got {scalar}"); }; Ok(*value) diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs index f20ad1410fa..4310af843aa 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs @@ -38,9 +38,9 @@ unsafe impl InputElement for T { fn validate(dtype: &DType) -> VortexResult<()> { let expected = T::PTYPE; let DType::Primitive(ptype, _) = dtype else { - vortex_bail!("expected a {expected} column, got {dtype}"); + vortex_bail!(MismatchedTypes: "expected a {expected} column, got {dtype}"); }; - vortex_ensure_eq!(*ptype, expected, "row input column has the wrong ptype"); + vortex_ensure_eq!(*ptype, expected, MismatchedTypes: "row input column has the wrong ptype"); Ok(()) } @@ -51,14 +51,14 @@ unsafe impl InputElement for T { fn decode_constant(array: ArrayRef, _ctx: &mut ExecutionCtx) -> VortexResult { let Some(constant) = array.as_opt::() else { vortex_bail!( - "a primitive batch constant must use the Constant encoding, got {}", + MismatchedTypes: "a primitive batch constant must use the Constant encoding, got {}", array.encoding_id() ); }; let scalar = constant.scalar(); let Some(ScalarValue::Primitive(value)) = scalar.value() else { vortex_bail!( - "a primitive batch constant must contain a non-null {} value, got {scalar}", + InvalidArgument: "a primitive batch constant must contain a non-null {} value, got {scalar}", T::PTYPE ); }; diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs index 77a0c13574d..76080992ba7 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs @@ -247,7 +247,7 @@ impl ElementTuple for () { const DECODE_INFALLIBLE: bool = true; fn validate(dtypes: &[DType]) -> VortexResult<()> { - vortex_ensure_eq!(dtypes.len(), 0); + vortex_ensure_eq!(dtypes.len(), 0, InvalidArgument); Ok(()) } @@ -306,7 +306,7 @@ macro_rules! element_tuple { const DECODE_INFALLIBLE: bool = $($t::DECODE_INFALLIBLE &&)+ true; fn validate(dtypes: &[DType]) -> VortexResult<()> { - vortex_ensure_eq!(dtypes.len(), $arity); + vortex_ensure_eq!(dtypes.len(), $arity, InvalidArgument); $($t::validate(&dtypes[$idx])?;)+ Ok(()) diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs index 16f639c4254..4b48da75141 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs @@ -155,7 +155,7 @@ fn test_batch_const_unwraps_filtered_masked_constant() -> VortexResult<()> { let filtered = masked.filter(Mask::from_iter([true, true, false]))?; let Some(const_array) = batch_const(&filtered) else { - vortex_bail!("filtered masked constant must remain batch-constant"); + vortex_bail!(AssertionFailed: "filtered masked constant must remain batch-constant"); }; assert!(const_array.is::()); @@ -171,7 +171,7 @@ fn test_batch_const_preserves_filtered_extension() -> VortexResult<()> { let filtered = extension.filter(Mask::from_iter([true, false, true]))?; let Some(const_array) = batch_const(&filtered) else { - vortex_bail!("filtered extension storage must remain batch-constant"); + vortex_bail!(AssertionFailed: "filtered extension storage must remain batch-constant"); }; assert_eq!(const_array.dtype(), extension.dtype()); diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs index 17b034dca94..c506b864396 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs @@ -237,13 +237,13 @@ fn decode_views(array: ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult VortexResult { let Some(constant) = array.as_opt::() else { vortex_bail!( - "a Utf8 batch constant must use the Constant encoding, got {}", + MismatchedTypes: "a Utf8 batch constant must use the Constant encoding, got {}", array.encoding_id() ); }; let scalar = constant.scalar(); let Some(ScalarValue::Utf8(value)) = scalar.value() else { - vortex_bail!("a Utf8 batch constant must contain a non-null value, got {scalar}"); + vortex_bail!(InvalidArgument: "a Utf8 batch constant must contain a non-null value, got {scalar}"); }; Ok(value.clone()) @@ -265,7 +265,7 @@ unsafe impl InputElement for Utf8Column { fn validate(dtype: &DType) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Utf8(_)), - "expected a Utf8 column, got {dtype}" + MismatchedTypes: "expected a Utf8 column, got {dtype}" ); Ok(()) @@ -447,7 +447,7 @@ mod tests { bytes: decoded_bytes, } = &column.0 else { - vortex_bail!("expected offset storage"); + vortex_bail!(AssertionFailed: "expected offset storage"); }; assert_eq!(decoded_bytes.as_ptr(), bytes.as_ptr()); assert_eq!( diff --git a/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs b/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs index f73325f285d..0dac8dee5a0 100644 --- a/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs +++ b/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs @@ -84,7 +84,7 @@ pub(super) fn validate_owned_visit( let dtype = Out::element_dtype(); vortex_ensure!( !dtype.is_nullable(), - "row output elements must declare a non-nullable dtype, got {dtype}", + AssertionFailed: "row output elements must declare a non-nullable dtype, got {dtype}", ); Ok(dtype) @@ -103,7 +103,7 @@ where let dtype = Sink::storage_dtype(params); vortex_ensure!( !dtype.is_nullable(), - "row output sinks must declare a non-nullable dtype, got {dtype}", + AssertionFailed: "row output sinks must declare a non-nullable dtype, got {dtype}", ); Ok(dtype) diff --git a/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs b/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs index 7e911681f7d..63a7f320f6f 100644 --- a/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs +++ b/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs @@ -225,18 +225,18 @@ impl BatchPlan { pub(crate) fn ensure_reproduced_by(&self, actual: &Self) -> VortexResult<()> { vortex_ensure!( actual.policy == self.policy, - "row dispatch must select the planned nullable execution policy: planned {:?}, got {:?}", + AssertionFailed: "row dispatch must select the planned nullable execution policy: planned {:?}, got {:?}", self.policy, actual.policy, ); vortex_ensure_eq!( actual.storage_dtype, self.storage_dtype, - "row dispatch must select the planned storage dtype", + AssertionFailed: "row dispatch must select the planned storage dtype", ); vortex_ensure!( actual.output_label == self.output_label, - "row dispatch must declare the planned output dtype: planned {}, got {}", + AssertionFailed: "row dispatch must declare the planned output dtype: planned {}, got {}", self.output_dtype(), actual.output_dtype(), ); @@ -262,7 +262,7 @@ fn validate_output_label( ) -> VortexResult> { vortex_ensure!( !output_dtype.is_nullable(), - "a declared row output dtype must be non-nullable, got {output_dtype}", + AssertionFailed: "a declared row output dtype must be non-nullable, got {output_dtype}", ); if output_dtype == *storage_dtype { @@ -271,14 +271,14 @@ fn validate_output_label( let DType::Extension(output_label) = output_dtype else { vortex_bail!( - "a declared row output dtype must be an extension dtype over the storage dtype \ + InvalidArgument: "a declared row output dtype must be an extension dtype over the storage dtype \ {storage_dtype}, got {output_dtype}", ); }; vortex_ensure_eq!( *output_label.storage_dtype(), *storage_dtype, - "a declared row extension output dtype has the wrong storage dtype", + AssertionFailed: "a declared row extension output dtype has the wrong storage dtype", ); Ok(Some(output_label)) diff --git a/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs b/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs index 952d0b478ea..86dc478929b 100644 --- a/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs +++ b/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs @@ -183,7 +183,7 @@ pub trait RowVisitor: private::Sealed + Sized { /// #[cold] /// #[inline(never)] /// fn integer_division_error() -> VortexError { - /// vortex_err!(InvalidArgument: "integer division by zero or overflow") + /// vortex_err!(Overflow: "integer division by zero or overflow") /// } /// /// visitor.visit_into::<(i64, i64), UninitElementSink, _>( @@ -281,7 +281,7 @@ pub trait RowVisitor: private::Sealed + Sized { /// #[cold] /// #[inline(never)] /// fn integer_addition_error() -> VortexError { - /// vortex_err!(InvalidArgument: "integer overflow in checked add") + /// vortex_err!(Overflow: "integer overflow in checked add") /// } /// /// visitor.visit_deferred::<(i64, i64), i64, bool>( @@ -350,7 +350,7 @@ pub trait RowVisitor: private::Sealed + Sized { /// #[cold] /// #[inline(never)] /// fn decimal_rescaling_overflow() -> VortexError { - /// vortex_err!(InvalidArgument: "decimal rescaling overflowed") + /// vortex_err!(Overflow: "decimal rescaling overflowed") /// } /// /// visitor.visit_prepared_deferred::< diff --git a/vortex-array/src/scalar_fn/unstable/row/vtable.rs b/vortex-array/src/scalar_fn/unstable/row/vtable.rs index 32212d367e0..4f3bd5225fe 100644 --- a/vortex-array/src/scalar_fn/unstable/row/vtable.rs +++ b/vortex-array/src/scalar_fn/unstable/row/vtable.rs @@ -156,7 +156,7 @@ fn ensure_arity(function: &F, actual: usize) -> VortexResult<()> { vortex_ensure_eq!( actual, expected, - "row function {} has the wrong arity", + InvalidArgument: "row function {} has the wrong arity", RowFn::id(function), ); @@ -393,7 +393,9 @@ mod tests { let error = match execute_rows(&function, &EmptyOptions, &args, &mut ctx) { Err(error) => error, - Ok(_) => vortex_error::vortex_bail!("dispatch must not change after planning"), + Ok(_) => { + vortex_error::vortex_bail!(InvalidArgument: "dispatch must not change after planning") + } }; let message = error.to_string(); @@ -420,7 +422,9 @@ mod tests { let error = match execute_rows(&function, &EmptyOptions, &args, &mut ctx) { Err(error) => error, - Ok(_) => vortex_error::vortex_bail!("dispatch must preserve its planned element types"), + Ok(_) => { + vortex_error::vortex_bail!(AssertionFailed: "dispatch must preserve its planned element types") + } }; assert!( diff --git a/vortex-array/src/scalar_fn/vtable.rs b/vortex-array/src/scalar_fn/vtable.rs index 4cd658d4774..66fbd7ed9a5 100644 --- a/vortex-array/src/scalar_fn/vtable.rs +++ b/vortex-array/src/scalar_fn/vtable.rs @@ -112,7 +112,7 @@ pub trait ScalarFnVTable: 'static + Sized + Clone + Send + Sync { _metadata: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!("Expression {} is not deserializable", self.id()); + vortex_bail!(Serde: "Expression {} is not deserializable", self.id()); } /// Returns the arity of this expression. @@ -576,7 +576,7 @@ impl ExecutionArgs for VecExecutionArgs { fn get(&self, index: usize) -> VortexResult { self.inputs.get(index).cloned().ok_or_else(|| { vortex_err!( - "Input index {} out of bounds (num_inputs={})", + OutOfBounds: "Input index {} out of bounds (num_inputs={})", index, self.inputs.len() ) diff --git a/vortex-array/src/serde.rs b/vortex-array/src/serde.rs index e87d8bc7e77..57f257ecff8 100644 --- a/vortex-array/src/serde.rs +++ b/vortex-array/src/serde.rs @@ -110,8 +110,9 @@ impl ArrayRef { u16::try_from(padding).vortex_expect("padding fits into u16"), buffer.alignment().exponent(), Compression::None, - u32::try_from(buffer.len()) - .map_err(|_| vortex_err!("All buffers must fit into u32 for serialization"))?, + u32::try_from(buffer.len()).map_err( + |_| vortex_err!(Overflow: "All buffers must fit into u32 for serialization"), + )?, )); pos += buffer.len(); @@ -148,7 +149,7 @@ impl ArrayRef { // Finally, we write down the u32 length for the flatbuffer. buffers.push(ByteBuffer::from( u32::try_from(fb_length) - .map_err(|_| vortex_err!("Array metadata flatbuffer must fit into u32 for serialization. Array encoding tree is too large."))? + .map_err(|_| vortex_err!(Overflow: "Array metadata flatbuffer must fit into u32 for serialization. Array encoding tree is too large."))? .to_le_bytes() .to_vec(), )); @@ -170,7 +171,7 @@ impl ArraySerializationTree { fn try_new(session: &VortexSession, source: &ArrayRef) -> VortexResult { let Some(serialization) = session.array_serialize(source)? else { vortex_bail!( - "Array {} does not support serialization", + Serde: "Array {} does not support serialization", source.encoding_id() ); }; @@ -228,7 +229,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { let n_buffers_recursive = array.nbuffers_recursive(); if n_buffers_recursive > u16::MAX as usize { vortex_bail!( - "Array and all descendent arrays can have at most u16::MAX buffers: {}", + Serde: "Array and all descendent arrays can have at most u16::MAX buffers: {}", n_buffers_recursive ); }; @@ -250,7 +251,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { ) -> VortexResult>> { let encoding_idx = self.ctx.intern(&array.serialized_id).ok_or_else(|| { vortex_err!( - "Serialized array ID {} not permitted by ctx", + Serde: "Serialized array ID {} not permitted by ctx", array.serialized_id ) })?; @@ -259,7 +260,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { // Assign buffer indices for all child arrays. let nbuffers = u16::try_from(array.buffers.len()) - .map_err(|_| vortex_err!("Array can have at most u16::MAX buffers"))?; + .map_err(|_| vortex_err!(Serde: "Array can have at most u16::MAX buffers"))?; let mut child_buffer_idx = buffer_idx + nbuffers; let children = array @@ -272,7 +273,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { child_buffer_idx = u16::try_from(child.nbuffers_recursive()) .ok() .and_then(|nbuffers| nbuffers.checked_add(child_buffer_idx)) - .ok_or_else(|| vortex_err!("Too many buffers (u16) for Array"))?; + .ok_or_else(|| vortex_err!(Serde: "Too many buffers (u16) for Array"))?; Ok(msg) }) @@ -364,12 +365,12 @@ impl SerializedArray { let encoding_idx = self.flatbuffer().encoding(); let encoding_id = ctx .resolve(encoding_idx) - .ok_or_else(|| vortex_err!("Unknown encoding index: {}", encoding_idx))?; + .ok_or_else(|| vortex_err!(NotFound: "Unknown encoding index: {}", encoding_idx))?; let Some(plugin) = session.arrays().registry().get(&encoding_id) else { if session.allows_unknown() { return self.decode_foreign(encoding_id, dtype, len, ctx); } - vortex_bail!("Unknown encoding: {}", encoding_id); + vortex_bail!(NotFound: "Unknown encoding: {}", encoding_id); }; let children = SerializedArrayChildren { @@ -437,9 +438,9 @@ impl SerializedArray { .map(|idx| { let child = self.child(idx); let child_encoding_idx = child.flatbuffer().encoding(); - let child_encoding_id = ctx - .resolve(child_encoding_idx) - .ok_or_else(|| vortex_err!("Unknown encoding index: {}", child_encoding_idx))?; + let child_encoding_id = ctx.resolve(child_encoding_idx).ok_or_else( + || vortex_err!(NotFound: "Unknown encoding index: {}", child_encoding_idx), + )?; child .decode_foreign(child_encoding_id, dtype, len, ctx) .map(Some) @@ -484,7 +485,7 @@ impl SerializedArray { .vortex_expect("Expected array to have children"); if idx >= children.len() { vortex_panic!( - "Invalid child index {} for array with {} children", + OutOfBounds: "Invalid child index {} for array with {} children", idx, children.len() ); @@ -504,14 +505,14 @@ impl SerializedArray { let buffer_idx = self .flatbuffer() .buffers() - .ok_or_else(|| vortex_err!("Array has no buffers"))? + .ok_or_else(|| vortex_err!(Serde: "Array has no buffers"))? .get(idx); self.buffers .get(buffer_idx as usize) .cloned() .ok_or_else(|| { vortex_err!( - "Invalid buffer index {} for array with {} buffers", + InvalidArgument: "Invalid buffer index {} for array with {} buffers", buffer_idx, self.nbuffers() ) @@ -539,7 +540,7 @@ impl SerializedArray { self.buffers.get(start..start + count).map_or_else( || { vortex_bail!( - "buffer indices {}..{} out of range for {} buffers", + OutOfBounds: "buffer indices {}..{} out of range for {} buffers", start, start + count, self.buffers.len() @@ -575,7 +576,7 @@ impl SerializedArray { let fb_array = root::(fb_buffer.as_ref())?; let fb_root = fb_array .root() - .ok_or_else(|| vortex_err!("Array must have a root node"))?; + .ok_or_else(|| vortex_err!(Serde: "Array must have a root node"))?; let flatbuffer_loc = fb_root._tab.loc(); Ok((fb_buffer, flatbuffer_loc)) } @@ -678,10 +679,10 @@ impl SerializedArray { let start = offset .checked_add(fb_buf.padding() as usize) .ok_or_else(|| { - vortex_err!("Buffer {idx} offset overflows when adding its padding") + vortex_err!(Overflow: "Buffer {idx} offset overflows when adding its padding") })?; let end = start.checked_add(buffer_len).ok_or_else(|| { - vortex_err!("Buffer {idx} offset overflows when adding its length") + vortex_err!(Overflow: "Buffer {idx} offset overflows when adding its length") })?; // The alignment exponent comes from the flatbuffer and may be corrupt, so validate @@ -695,7 +696,7 @@ impl SerializedArray { // `VortexError` rather than panicking when slicing (see issue #8819). if end > segment.len() { vortex_bail!( - "Buffer {idx} at offset {start} with length {buffer_len} is out of \ + OutOfBounds: "Buffer {idx} at offset {start} with length {buffer_len} is out of \ bounds of the {}-byte segment", segment.len(), ); @@ -740,7 +741,7 @@ impl TryFrom for SerializedArray { fn try_from(value: ByteBuffer) -> Result { // The final 4 bytes contain the length of the flatbuffer. if value.len() < 4 { - vortex_bail!("SerializedArray buffer is too short"); + vortex_bail!(Serde: "SerializedArray buffer is too short"); } // We align each buffer individually, so we remove alignment requirements on the buffer. @@ -748,7 +749,7 @@ impl TryFrom for SerializedArray { let fb_length = u32::try_from_le_bytes(&value.as_slice()[value.len() - 4..])? as usize; if value.len() < 4 + fb_length { - vortex_bail!("SerializedArray buffer is too short for flatbuffer"); + vortex_bail!(Serde: "SerializedArray buffer is too short for flatbuffer"); } let fb_offset = value.len() - 4 - fb_length; @@ -823,7 +824,7 @@ mod tests { vortex_ensure_eq!( array.encoding_id(), self.id(), - "versioned primitive serializer received a different encoding", + Serde: "versioned primitive serializer received a different encoding", ); let serialized_id = if array.len() <= 4 { @@ -847,12 +848,12 @@ mod tests { vortex_ensure!( parts.serialized_id == old_primitive_id() || parts.serialized_id == new_primitive_id(), - "versioned primitive deserializer does not recognize {}", + Serde: "versioned primitive deserializer does not recognize {}", parts.serialized_id, ); vortex_ensure!( parts.serialized_id != old_primitive_id() || parts.len <= 4, - "old primitive wire ID cannot represent length {}", + Serde: "old primitive wire ID cannot represent length {}", parts.len, ); Ok(Array::::try_from_parts(ArrayVTable::deserialize( @@ -1052,7 +1053,7 @@ mod tests { let Some(err) = SerializedArray::from_flatbuffer_and_segment(array_tree, truncated).err() else { - vortex_bail!("out-of-bounds buffer must be rejected"); + vortex_bail!(AssertionFailed: "out-of-bounds buffer must be rejected"); }; assert!( err.to_string().contains("out of bounds"), @@ -1086,7 +1087,7 @@ mod tests { let segment = BufferHandle::new_host(ByteBuffer::from(vec![0u8; 4])); let Some(err) = SerializedArray::from_flatbuffer_and_segment(array_tree, segment).err() else { - vortex_bail!("excessive buffer alignment must be rejected"); + vortex_bail!(InvalidArgument: "excessive buffer alignment must be rejected"); }; assert!( err.to_string().contains("exceeds"), diff --git a/vortex-array/src/session/mod.rs b/vortex-array/src/session/mod.rs index e9d0d36a55f..ef18afd1ca9 100644 --- a/vortex-array/src/session/mod.rs +++ b/vortex-array/src/session/mod.rs @@ -133,7 +133,7 @@ pub trait ArraySessionExt: SessionExt { fn array_serialize(&self, array: &ArrayRef) -> VortexResult> { let Some(plugin) = self.arrays().serializer(&array.encoding_id()) else { vortex_bail!( - "Array {} is not registered for serialization", + Serde: "Array {} is not registered for serialization", array.encoding_id() ); }; @@ -145,7 +145,7 @@ pub trait ArraySessionExt: SessionExt { plugin .serialized_ids() .contains(&serialization.serialized_id), - "array serializer {} produced undeclared serialized ID {}", + Serde: "array serializer {} produced undeclared serialized ID {}", array.encoding_id(), serialization.serialized_id, ); diff --git a/vortex-array/src/stats/flatbuffers.rs b/vortex-array/src/stats/flatbuffers.rs index 2e385885e5a..f0aa6b275d5 100644 --- a/vortex-array/src/stats/flatbuffers.rs +++ b/vortex-array/src/stats/flatbuffers.rs @@ -165,7 +165,9 @@ impl StatsSet { match fb.max_precision() { fba::Precision::Exact => Precision::Exact(value), fba::Precision::Inexact => Precision::Inexact(value), - other => vortex_bail!("Corrupted max_precision field: {other:?}"), + other => { + vortex_bail!(Serde: "Corrupted max_precision field: {other:?}") + } }, ); } @@ -185,7 +187,9 @@ impl StatsSet { match fb.min_precision() { fba::Precision::Exact => Precision::Exact(value), fba::Precision::Inexact => Precision::Inexact(value), - other => vortex_bail!("Corrupted min_precision field: {other:?}"), + other => { + vortex_bail!(Serde: "Corrupted min_precision field: {other:?}") + } }, ); } @@ -273,7 +277,7 @@ mod tests { &DType::Primitive(PType::F64, Nullability::Nullable), ) .as_exact() - .ok_or_else(|| vortex_err!("sum must be exact after a round trip"))? + .ok_or_else(|| vortex_err!(Serde: "sum must be exact after a round trip"))? .to_bits()) } diff --git a/vortex-array/src/stats/stats_set.rs b/vortex-array/src/stats/stats_set.rs index eb898bd387c..937f0d4c636 100644 --- a/vortex-array/src/stats/stats_set.rs +++ b/vortex-array/src/stats/stats_set.rs @@ -136,7 +136,7 @@ impl StatsSet { pub(super) fn get_bool(&self, stat: Stat) -> Precision { self.get_ref(stat).map(|v| match v { ScalarValue::Bool(b) => *b, - _ => vortex_panic!("Failed to get stat {} as bool, found {}", stat, v), + _ => vortex_panic!(MismatchedTypes: "Failed to get stat {} as bool, found {}", stat, v), }) } @@ -372,7 +372,7 @@ impl MutTypedStatsSetRef<'_, '_> { .intersection(&m2) .vortex_expect("can always compare scalar") .ok_or_else(|| { - vortex_err!("{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) + vortex_err!(InvalidArgument: "{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) })?; if meet != m1 { self.set( @@ -410,7 +410,7 @@ impl MutTypedStatsSetRef<'_, '_> { .intersection(&m2) .vortex_expect("can always compare boolean") .ok_or_else(|| { - vortex_err!("{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) + vortex_err!(InvalidArgument: "{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) })?; if intersection != m1 { self.set(S::STAT, intersection.into_value().map(ScalarValue::from)); diff --git a/vortex-array/src/test_harness/trace/mod.rs b/vortex-array/src/test_harness/trace/mod.rs index 1e053cf5a7a..c3443b8826e 100644 --- a/vortex-array/src/test_harness/trace/mod.rs +++ b/vortex-array/src/test_harness/trace/mod.rs @@ -234,7 +234,7 @@ pub fn trace_op_with( ACTIVE_TRACE.with(|active| { let mut active = active.borrow_mut(); if active.is_some() { - return Err(vortex_err!("trace_op captures cannot be nested")); + return Err(vortex_err!(InvalidArgument: "trace_op captures cannot be nested")); } *active = Some(TraceRecorder::new(options)); Ok(()) diff --git a/vortex-array/src/test_harness/trace/tests.rs b/vortex-array/src/test_harness/trace/tests.rs index 353fc669a54..e8ef4b548a7 100644 --- a/vortex-array/src/test_harness/trace/tests.rs +++ b/vortex-array/src/test_harness/trace/tests.rs @@ -158,14 +158,14 @@ impl VTable for StackParent { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(dtype, &test_dtype(), "unexpected stack parent dtype"); - vortex_ensure_eq!(len, 3, "unexpected stack parent length"); - vortex_ensure_eq!(slots.len(), 1, "unexpected stack parent slot count"); + vortex_ensure_eq!(dtype, &test_dtype(), AssertionFailed: "unexpected stack parent dtype"); + vortex_ensure_eq!(len, 3, AssertionFailed: "unexpected stack parent length"); + vortex_ensure_eq!(slots.len(), 1, AssertionFailed: "unexpected stack parent slot count"); let Some(child) = &slots[0] else { - vortex_bail!("stack parent child slot is missing"); + vortex_bail!(InvalidArgument: "stack parent child slot is missing"); }; - vortex_ensure_eq!(child.dtype(), dtype, "stack parent child dtype mismatch"); - vortex_ensure_eq!(child.len(), len, "stack parent child length mismatch"); + vortex_ensure_eq!(child.dtype(), dtype, AssertionFailed: "stack parent child dtype mismatch"); + vortex_ensure_eq!(child.len(), len, AssertionFailed: "stack parent child length mismatch"); Ok(()) } @@ -174,7 +174,7 @@ impl VTable for StackParent { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("StackParent buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "StackParent buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -197,7 +197,7 @@ impl VTable for StackParent { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("StackParent cannot be deserialized") + vortex_bail!(Serde: "StackParent cannot be deserialized") } fn with_buffers( @@ -211,13 +211,13 @@ impl VTable for StackParent { fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { match idx { 0 => "child".to_string(), - _ => vortex_panic!("StackParent slot index {idx} out of bounds"), + _ => vortex_panic!(OutOfBounds: "StackParent slot index {idx} out of bounds"), } } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { let Some(child) = array.slots()[0].as_ref() else { - vortex_bail!("stack parent child slot is missing"); + vortex_bail!(InvalidArgument: "stack parent child slot is missing"); }; if !child.is::() { return Ok(ExecutionResult::execute_slot::(array, 0)); @@ -272,9 +272,9 @@ impl VTable for StackChild { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(dtype, &test_dtype(), "unexpected stack child dtype"); - vortex_ensure_eq!(len, 3, "unexpected stack child length"); - vortex_ensure!(slots.is_empty(), "stack child must not have slots"); + vortex_ensure_eq!(dtype, &test_dtype(), AssertionFailed: "unexpected stack child dtype"); + vortex_ensure_eq!(len, 3, AssertionFailed: "unexpected stack child length"); + vortex_ensure!(slots.is_empty(), AssertionFailed: "stack child must not have slots"); Ok(()) } @@ -283,7 +283,7 @@ impl VTable for StackChild { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("StackChild buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "StackChild buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -306,7 +306,7 @@ impl VTable for StackChild { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!("StackChild cannot be deserialized") + vortex_bail!(Serde: "StackChild cannot be deserialized") } fn with_buffers( @@ -318,7 +318,7 @@ impl VTable for StackChild { } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { - vortex_panic!("StackChild slot index {idx} out of bounds") + vortex_panic!(OutOfBounds: "StackChild slot index {idx} out of bounds") } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/validity.rs b/vortex-array/src/validity.rs index 449f66b07d9..5e96e53d16d 100644 --- a/vortex-array/src/validity.rs +++ b/vortex-array/src/validity.rs @@ -167,11 +167,9 @@ impl Validity { Ok(match self { Self::NonNullable | Self::AllValid => true, Self::AllInvalid => false, - Self::Array(a) => a - .execute_scalar(index, ctx)? - .as_bool() - .value() - .ok_or_else(|| vortex_err!("validity value at index {index} is null"))?, + Self::Array(a) => a.execute_scalar(index, ctx)?.as_bool().value().ok_or_else( + || vortex_err!(AssertionFailed: "validity value at index {index} is null"), + )?, }) } @@ -328,10 +326,10 @@ impl Validity { match (&self, patches) { (Validity::NonNullable, Validity::NonNullable) => return Ok(Validity::NonNullable), (Validity::NonNullable, _) => { - vortex_bail!("Can't patch a non-nullable validity with nullable validity") + vortex_bail!(InvalidArgument: "Can't patch a non-nullable validity with nullable validity") } (_, Validity::NonNullable) => { - vortex_bail!("Can't patch a nullable validity with non-nullable validity") + vortex_bail!(InvalidArgument: "Can't patch a nullable validity with non-nullable validity") } (Validity::AllValid, Validity::AllValid) => return Ok(Validity::AllValid), (Validity::AllInvalid, Validity::AllInvalid) => return Ok(Validity::AllInvalid), diff --git a/vortex-arrow/src/convert.rs b/vortex-arrow/src/convert.rs index a2760a82883..00d3c935d39 100644 --- a/vortex-arrow/src/convert.rs +++ b/vortex-arrow/src/convert.rs @@ -252,9 +252,9 @@ where DataType::Date32 => TemporalArray::new_date(arr, TimeUnit::Days).into(), DataType::Date64 => TemporalArray::new_date(arr, TimeUnit::Milliseconds).into(), DataType::Duration(_) | DataType::Interval(_) => { - vortex_bail!("Arrow {} arrays are not supported", value.data_type()) + vortex_bail!(InvalidArgument: "Arrow {} arrays are not supported", value.data_type()) } - _ => vortex_panic!("Invalid temporal type: {}", value.data_type()), + _ => vortex_panic!(MismatchedTypes: "Invalid temporal type: {}", value.data_type()), }) } @@ -286,7 +286,7 @@ where let dtype = match T::DATA_TYPE { DataType::Binary | DataType::LargeBinary => DType::Binary(nullable.into()), DataType::Utf8 | DataType::LargeUtf8 => DType::Utf8(nullable.into()), - dt => vortex_panic!("Invalid data type for ByteArray: {dt}"), + dt => vortex_panic!(MismatchedTypes: "Invalid data type for ByteArray: {dt}"), }; let (offsets, referenced) = trim_offsets(value.offsets()); let bytes = value @@ -312,7 +312,7 @@ pub fn from_arrow_byte_view( let dtype = match T::DATA_TYPE { DataType::BinaryView => DType::Binary(nullable.into()), DataType::Utf8View => DType::Utf8(nullable.into()), - dt => vortex_panic!("Invalid data type for ByteViewArray: {dt}"), + dt => vortex_panic!(MismatchedTypes: "Invalid data type for ByteViewArray: {dt}"), }; let views_buffer = Buffer::from_byte_buffer( @@ -379,7 +379,7 @@ pub(crate) fn remove_nulls(data: arrow_data::ArrayData) -> VortexResult VortexResult( let elements_are_nullable = match value.data_type() { DataType::List(field) => field.is_nullable(), DataType::LargeList(field) => field.is_nullable(), - dt => vortex_panic!("Invalid data type for ListArray: {dt}"), + dt => vortex_panic!(MismatchedTypes: "Invalid data type for ListArray: {dt}"), }; let (offsets, referenced) = trim_offsets(value.offsets()); @@ -457,7 +457,7 @@ pub fn from_arrow_list_view( let elements_are_nullable = match array.data_type() { DataType::ListView(field) => field.is_nullable(), DataType::LargeListView(field) => field.is_nullable(), - dt => vortex_panic!("Invalid data type for ListViewArray: {dt}"), + dt => vortex_panic!(MismatchedTypes: "Invalid data type for ListViewArray: {dt}"), }; let elements = from_arrow_dyn(array.values().as_ref(), elements_are_nullable)?; @@ -478,7 +478,7 @@ pub fn from_arrow_fixed_size_list( nullable: bool, ) -> VortexResult { let DataType::FixedSizeList(field, list_size) = array.data_type() else { - vortex_panic!("Invalid data type for ListArray: {}", array.data_type()); + vortex_panic!(MismatchedTypes: "Invalid data type for ListArray: {}", array.data_type()); }; Ok(FixedSizeListArray::try_new( @@ -499,26 +499,26 @@ pub(crate) fn map_from_arrow_parts( ) -> VortexResult { let DType::Struct(struct_dtype, Nullability::NonNullable) = entries.dtype() else { vortex_bail!( - "Arrow map entries must import as non-nullable struct, got {}", + MismatchedTypes: "Arrow map entries must import as non-nullable struct, got {}", entries.dtype() ); }; vortex_ensure_eq!( struct_dtype.nfields(), 2, - "Arrow map entries struct must contain exactly two fields" + InvalidArgument: "Arrow map entries struct must contain exactly two fields" ); let key_dtype = struct_dtype .field_by_index(0) - .ok_or_else(|| vortex_err!("Arrow map entries struct missing key field"))?; + .ok_or_else(|| vortex_err!(NotFound: "Arrow map entries struct missing key field"))?; vortex_ensure!( !key_dtype.is_nullable(), - "Arrow map key field must be non-nullable" + InvalidArgument: "Arrow map key field must be non-nullable" ); let value_dtype = struct_dtype .field_by_index(1) - .ok_or_else(|| vortex_err!("Arrow map entries struct missing value field"))?; + .ok_or_else(|| vortex_err!(NotFound: "Arrow map entries struct missing value field"))?; let map_dtype = MapDType::try_new(key_dtype, value_dtype, keys_sorted)?; let entries_struct = entries.as_::(); let entries = StructArray::try_new( @@ -551,7 +551,7 @@ pub(crate) fn map_from_arrow_parts( /// Conversion of an Arrow map array into a Vortex `Map` array. pub fn from_arrow_map(array: &ArrowMapArray, nullable: bool) -> VortexResult { let DataType::Map(_, keys_sorted) = array.data_type() else { - vortex_panic!("Invalid data type for MapArray: {}", array.data_type()); + vortex_panic!(MismatchedTypes: "Invalid data type for MapArray: {}", array.data_type()); }; let entries = from_arrow_struct(array.entries(), false)?; map_from_arrow_parts( @@ -567,7 +567,7 @@ pub fn from_arrow_map(array: &ArrowMapArray, nullable: bool) -> VortexResult VortexResult { vortex_ensure!( nullable, - "Cannot convert an Arrow NullArray into a non-nullable Vortex array" + InvalidArgument: "Cannot convert an Arrow NullArray into a non-nullable Vortex array" ); Ok(NullArray::new(value.len()).into_array()) } @@ -606,7 +606,7 @@ pub fn nulls(nulls: Option<&NullBuffer>, nullable: bool) -> VortexResult VortexResult vortex_bail!("Unsupported dictionary key type: {key_dt}"), + key_dt => vortex_bail!(InvalidArgument: "Unsupported dictionary key type: {key_dt}"), }, - dt => vortex_bail!("Array encoding not implemented for Arrow data type {dt}"), + dt => { + vortex_bail!(NotImplemented: "Array encoding not implemented for Arrow data type {dt}") + } } } diff --git a/vortex-arrow/src/datum.rs b/vortex-arrow/src/datum.rs index d501ff1d920..2587ffdcfff 100644 --- a/vortex-arrow/src/datum.rs +++ b/vortex-arrow/src/datum.rs @@ -120,7 +120,7 @@ pub fn from_arrow_columnar( if array.len() != 1 { vortex_panic!( - "Array length mismatch, expected {} got {} for encoding {}", + AssertionFailed: "Array length mismatch, expected {} got {} for encoding {}", len, array.len(), array.encoding_id() diff --git a/vortex-arrow/src/dtype.rs b/vortex-arrow/src/dtype.rs index 9fb33b8ebba..f1b87bfcd26 100644 --- a/vortex-arrow/src/dtype.rs +++ b/vortex-arrow/src/dtype.rs @@ -62,7 +62,7 @@ pub(crate) fn to_arrow_time_unit(value: TimeUnit) -> VortexResult TimeUnit::Milliseconds => ArrowTimeUnit::Millisecond, TimeUnit::Microseconds => ArrowTimeUnit::Microsecond, TimeUnit::Nanoseconds => ArrowTimeUnit::Nanosecond, - _ => vortex_bail!("Cannot convert {value} to Arrow TimeUnit"), + _ => vortex_bail!(MismatchedTypes: "Cannot convert {value} to Arrow TimeUnit"), }) } @@ -81,7 +81,7 @@ pub(crate) fn ptype_from_arrow(value: &DataType) -> VortexResult { DataType::Float32 => Ok(PType::F32), DataType::Float64 => Ok(PType::F64), _ => Err(vortex_err!( - "Arrow datatype {:?} cannot be converted to ptype", + InvalidArgument: "Arrow datatype {:?} cannot be converted to ptype", value )), } @@ -138,11 +138,11 @@ pub(crate) fn from_arrow_data_type( DataType::Map(entries, keys_sorted) => { vortex_ensure!( !entries.is_nullable(), - "Arrow map entries field must be non-nullable" + InvalidArgument: "Arrow map entries field must be non-nullable" ); let DataType::Struct(fields) = entries.data_type() else { vortex_bail!( - "Arrow map entries field must have Struct type, got {:?}", + MismatchedTypes: "Arrow map entries field must have Struct type, got {:?}", entries.data_type() ); }; @@ -155,7 +155,7 @@ pub(crate) fn from_arrow_data_type( let value = &fields[1]; vortex_ensure!( !key.is_nullable(), - "Arrow map key field must be non-nullable" + InvalidArgument: "Arrow map key field must be non-nullable" ); DType::map( from_arrow_field_naive(key.as_ref())?, @@ -170,7 +170,7 @@ pub(crate) fn from_arrow_data_type( DataType::RunEndEncoded(_, value_type) => { from_arrow_data_type(value_type.data_type(), nullability)? } - _ => vortex_bail!("Arrow data type not supported: {data_type:?}"), + _ => vortex_bail!(InvalidArgument: "Arrow data type not supported: {data_type:?}"), }) } @@ -274,9 +274,9 @@ pub(crate) fn to_data_type_naive(dtype: &DType) -> VortexResult { DataType::Struct(Fields::from(fields)) } - DType::Union(..) => vortex_bail!("TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_bail!(NotImplemented: "TODO(connor)[Union]: unimplemented"), DType::Variant(_) => vortex_bail!( - "DType::Variant requires Arrow Field metadata; use to_arrow_schema or a Field helper" + InvalidArgument: "DType::Variant requires Arrow Field metadata; use to_arrow_schema or a Field helper" ), DType::Extension(ext_dtype) => { // NOTE: Temporal are the only builtin and default-loaded extension types, and they map @@ -307,7 +307,7 @@ pub(crate) fn to_data_type_naive(dtype: &DType) -> VortexResult { }); }; - vortex_bail!("Unsupported extension type \"{}\"", ext_dtype.id()) + vortex_bail!(InvalidArgument: "Unsupported extension type \"{}\"", ext_dtype.id()) } }) } diff --git a/vortex-arrow/src/executor/bool.rs b/vortex-arrow/src/executor/bool.rs index f6815884b33..a0587fb37ee 100644 --- a/vortex-arrow/src/executor/bool.rs +++ b/vortex-arrow/src/executor/bool.rs @@ -37,7 +37,7 @@ pub(super) fn to_arrow_bool( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::Bool(_)), - "Cannot convert Vortex array with dtype {} to an Arrow Boolean array", + MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow Boolean array", array.dtype() ); let bool_array = array.execute::(ctx)?; diff --git a/vortex-arrow/src/executor/byte.rs b/vortex-arrow/src/executor/byte.rs index c593bd24074..8e1cda30d09 100644 --- a/vortex-arrow/src/executor/byte.rs +++ b/vortex-arrow/src/executor/byte.rs @@ -60,7 +60,7 @@ where { if !matches!(array.dtype(), DType::Utf8(_) | DType::Binary(_)) { vortex_bail!( - "Cannot convert Vortex array with dtype {} to Arrow byte array type {}", + MismatchedTypes: "Cannot convert Vortex array with dtype {} to Arrow byte array type {}", array.dtype(), T::DATA_TYPE ); @@ -142,7 +142,7 @@ fn validate_live_values_utf8( let value_at = |index: usize, start: usize, end: usize| -> VortexResult<&[u8]> { values .get(start..end) - .ok_or_else(|| vortex_err!("Offsets {start}..{end} at index {index} are out of bounds")) + .ok_or_else(|| vortex_err!(OutOfBounds: "Offsets {start}..{end} at index {index} are out of bounds")) }; let Some(nulls) = nulls.filter(|nulls| nulls.null_count() > 0) else { @@ -155,7 +155,7 @@ fn validate_live_values_utf8( let start = first.as_usize(); let bytes = value_at(0, start, last.as_usize())?; let validated = utf8_from_bytes(bytes) - .map_err(|err| vortex_err!("Encountered non UTF-8 data: {err}"))?; + .map_err(|err| vortex_err!(InvalidArgument: "Encountered non UTF-8 data: {err}"))?; for (index, offset) in offsets.iter().enumerate() { let boundary = offset .as_usize() @@ -163,7 +163,7 @@ fn validate_live_values_utf8( .filter(|boundary| validated.is_char_boundary(*boundary)); vortex_ensure!( boundary.is_some(), - "Offset {} at index {index} does not fall on a UTF-8 character boundary", + InvalidArgument: "Offset {} at index {index} does not fall on a UTF-8 character boundary", offset.as_usize() ); } @@ -176,7 +176,7 @@ fn validate_live_values_utf8( } let bytes = value_at(index, window[0].as_usize(), window[1].as_usize())?; utf8_from_bytes(bytes) - .map_err(|err| vortex_err!("Encountered non UTF-8 data at index {index}: {err}"))?; + .map_err(|err| vortex_err!(InvalidArgument: "Encountered non UTF-8 data at index {index}: {err}"))?; } Ok(()) } diff --git a/vortex-arrow/src/executor/decimal.rs b/vortex-arrow/src/executor/decimal.rs index d86406277bd..6896b81f814 100644 --- a/vortex-arrow/src/executor/decimal.rs +++ b/vortex-arrow/src/executor/decimal.rs @@ -32,7 +32,7 @@ pub(super) fn to_arrow_decimal( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::Decimal(..)), - "Cannot convert Vortex array with dtype {} to an Arrow {} array", + MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow {} array", array.dtype(), data_type ); @@ -68,24 +68,27 @@ fn to_arrow_decimal32(array: DecimalArray, ctx: &mut ExecutionCtx) -> VortexResu .buffer::() .into_iter() .map(|x| { - x.to_i32() - .ok_or_else(|| vortex_err!("i64 to i32 narrowing cannot be done safely")) + x.to_i32().ok_or_else( + || vortex_err!(InvalidArgument: "i64 to i32 narrowing cannot be done safely"), + ) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, DecimalType::I128 => array .buffer::() .into_iter() .map(|x| { - x.to_i32() - .ok_or_else(|| vortex_err!("i128 to i32 narrowing cannot be done safely")) + x.to_i32().ok_or_else( + || vortex_err!(InvalidArgument: "i128 to i32 narrowing cannot be done safely"), + ) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, DecimalType::I256 => array .buffer::() .into_iter() .map(|x| { - x.to_i32() - .ok_or_else(|| vortex_err!("i256 to i32 narrowing cannot be done safely")) + x.to_i32().ok_or_else( + || vortex_err!(InvalidArgument: "i256 to i32 narrowing cannot be done safely"), + ) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, }; @@ -120,16 +123,18 @@ fn to_arrow_decimal64(array: DecimalArray, ctx: &mut ExecutionCtx) -> VortexResu .buffer::() .into_iter() .map(|x| { - x.to_i64() - .ok_or_else(|| vortex_err!("i128 to i64 narrowing cannot be done safely")) + x.to_i64().ok_or_else( + || vortex_err!(InvalidArgument: "i128 to i64 narrowing cannot be done safely"), + ) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, DecimalType::I256 => array .buffer::() .into_iter() .map(|x| { - x.to_i64() - .ok_or_else(|| vortex_err!("i256 to i64 narrowing cannot be done safely")) + x.to_i64().ok_or_else( + || vortex_err!(InvalidArgument: "i256 to i64 narrowing cannot be done safely"), + ) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, }; @@ -167,8 +172,9 @@ fn to_arrow_decimal128(array: DecimalArray, ctx: &mut ExecutionCtx) -> VortexRes .buffer::() .into_iter() .map(|x| { - x.to_i128() - .ok_or_else(|| vortex_err!("i256 to i128 narrowing cannot be done safely")) + x.to_i128().ok_or_else( + || vortex_err!(InvalidArgument: "i256 to i128 narrowing cannot be done safely"), + ) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, }; diff --git a/vortex-arrow/src/executor/dictionary.rs b/vortex-arrow/src/executor/dictionary.rs index 343c08357af..fd2528d91aa 100644 --- a/vortex-arrow/src/executor/dictionary.rs +++ b/vortex-arrow/src/executor/dictionary.rs @@ -115,7 +115,7 @@ fn zeroed_codes_array(codes_type: &DataType, len: usize) -> VortexResult Arc::new(PrimitiveArray::::from_value(0, len)), DataType::UInt32 => Arc::new(PrimitiveArray::::from_value(0, len)), DataType::UInt64 => Arc::new(PrimitiveArray::::from_value(0, len)), - _ => vortex_bail!("Unsupported dictionary codes type: {:?}", codes_type), + _ => vortex_bail!(InvalidArgument: "Unsupported dictionary codes type: {:?}", codes_type), }) } @@ -150,7 +150,7 @@ fn make_dict_array( DataType::UInt64 => Arc::new(unsafe { DictionaryArray::new_unchecked(codes.as_primitive::().clone(), values) }), - _ => vortex_bail!("Unsupported dictionary codes type: {:?}", codes_type), + _ => vortex_bail!(InvalidArgument: "Unsupported dictionary codes type: {:?}", codes_type), }) } diff --git a/vortex-arrow/src/executor/fixed_size_list.rs b/vortex-arrow/src/executor/fixed_size_list.rs index b830af710dd..222b7279d2d 100644 --- a/vortex-arrow/src/executor/fixed_size_list.rs +++ b/vortex-arrow/src/executor/fixed_size_list.rs @@ -26,7 +26,7 @@ pub(super) fn to_arrow_fixed_list( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::FixedSizeList(..)), - "Cannot convert Vortex array with dtype {} to an Arrow FixedSizeList array", + MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow FixedSizeList array", array.dtype() ); @@ -55,7 +55,7 @@ fn list_to_list( ) -> VortexResult { vortex_ensure!( Ok(list_size) == i32::try_from(array.list_size()), - "Cannot convert FixedSizeList with list size {} to Arrow array with list size {}", + InvalidArgument: "Cannot convert FixedSizeList with list size {} to Arrow array with list size {}", array.list_size(), list_size ); @@ -64,7 +64,7 @@ fn list_to_list( exporter.execute_arrow(array.elements().clone(), Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - "Cannot convert FixedSizeListArray to non-nullable Arrow array when elements are nullable" + InvalidArgument: "Cannot convert FixedSizeListArray to non-nullable Arrow array when elements are nullable" ); let null_buffer = to_arrow_null_buffer(array.validity()?, array.len(), ctx)?; diff --git a/vortex-arrow/src/executor/list.rs b/vortex-arrow/src/executor/list.rs index 8246f36155f..115076927c4 100644 --- a/vortex-arrow/src/executor/list.rs +++ b/vortex-arrow/src/executor/list.rs @@ -55,7 +55,7 @@ pub(super) fn to_arrow_list( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::List(..)), - "Cannot convert Vortex array with dtype {} to an Arrow list array", + MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow list array", array.dtype() ); @@ -123,7 +123,7 @@ fn list_to_list( exporter.execute_arrow(array.elements().clone(), Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - "Cannot convert to non-nullable Arrow array with null elements" + InvalidArgument: "Cannot convert to non-nullable Arrow array with null elements" ); let null_buffer = to_arrow_null_buffer(array.validity()?, array.len(), ctx)?; @@ -199,7 +199,7 @@ fn list_view_zctl( let elements = exporter.execute_arrow(elements, Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - "Cannot convert to non-nullable Arrow array with null elements" + InvalidArgument: "Cannot convert to non-nullable Arrow array with null elements" ); let null_buffer = to_arrow_null_buffer(validity, sizes.len(), ctx)?; diff --git a/vortex-arrow/src/executor/list_view.rs b/vortex-arrow/src/executor/list_view.rs index 2bae37f5835..ea339d2cb63 100644 --- a/vortex-arrow/src/executor/list_view.rs +++ b/vortex-arrow/src/executor/list_view.rs @@ -35,7 +35,7 @@ pub(super) fn to_arrow_list_view( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::List(..)), - "Cannot convert Vortex array with dtype {} to an Arrow list-view array", + MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow list-view array", array.dtype() ); @@ -89,14 +89,14 @@ fn list_view_to_list_view( let elements = exporter.execute_arrow(elements, Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - "Elements field is non-nullable but elements array contains nulls" + InvalidArgument: "Elements field is non-nullable but elements array contains nulls" ); // The unchecked construction below needs the views in bounds of the *exported* elements, so // confirm the export preserved the length the Vortex invariant was checked against. vortex_ensure_eq!( elements.len(), n_elements, - "Arrow export changed the elements length" + AssertionFailed: "Arrow export changed the elements length" ); let offsets = offsets diff --git a/vortex-arrow/src/executor/map.rs b/vortex-arrow/src/executor/map.rs index fb6c9239b55..820a94cace1 100644 --- a/vortex-arrow/src/executor/map.rs +++ b/vortex-arrow/src/executor/map.rs @@ -41,7 +41,7 @@ pub(super) fn to_arrow_map( vortex_ensure!( !keys_sorted || array.keys_sorted(), - "Cannot convert unsorted Vortex map to Arrow MapArray with keys_sorted=true" + InvalidArgument: "Cannot convert unsorted Vortex map to Arrow MapArray with keys_sorted=true" ); let entries = array.entries().clone(); @@ -50,7 +50,7 @@ pub(super) fn to_arrow_map( vortex_ensure_eq!( entries_list.data_type(), &entries_list_type, - "Arrow Map entries converted to an unexpected type" + AssertionFailed: "Arrow Map entries converted to an unexpected type" ); let entries_list = entries_list.as_list::(); diff --git a/vortex-arrow/src/executor/mod.rs b/vortex-arrow/src/executor/mod.rs index bc2256584fc..308c4aca357 100644 --- a/vortex-arrow/src/executor/mod.rs +++ b/vortex-arrow/src/executor/mod.rs @@ -207,14 +207,14 @@ pub(crate) fn execute_arrow_naive( | DataType::Duration(_) | DataType::Interval(_) | DataType::Union(..) => { - vortex_bail!("Conversion to Arrow type {resolved_type} is not supported"); + vortex_bail!(InvalidArgument: "Conversion to Arrow type {resolved_type} is not supported"); } }?; vortex_ensure_eq!( arrow.len(), len, - "Arrow array length does not match Vortex array length after conversion to {:?}", + AssertionFailed: "Arrow array length does not match Vortex array length after conversion to {:?}", arrow ); diff --git a/vortex-arrow/src/executor/null.rs b/vortex-arrow/src/executor/null.rs index 7e5dac3e9c4..b04a6955dbf 100644 --- a/vortex-arrow/src/executor/null.rs +++ b/vortex-arrow/src/executor/null.rs @@ -23,7 +23,7 @@ pub(super) fn to_arrow_null( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::Null), - "Cannot convert Vortex array with dtype {} to an Arrow Null array", + MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow Null array", array.dtype() ); let null_array = array.execute::(ctx)?; diff --git a/vortex-arrow/src/executor/run_end.rs b/vortex-arrow/src/executor/run_end.rs index ef8a124eef7..d4690802b38 100644 --- a/vortex-arrow/src/executor/run_end.rs +++ b/vortex-arrow/src/executor/run_end.rs @@ -97,7 +97,7 @@ fn run_end_to_arrow( DataType::Int16 => build_run_array::(&arrow_ends, &arrow_values, offset, length), DataType::Int32 => build_run_array::(&arrow_ends, &arrow_values, offset, length), DataType::Int64 => build_run_array::(&arrow_ends, &arrow_values, offset, length), - _ => vortex_bail!("Unsupported run-end index type: {:?}", ends_type), + _ => vortex_bail!(InvalidArgument: "Unsupported run-end index type: {:?}", ends_type), } } @@ -111,9 +111,9 @@ where R::Native: std::ops::Sub + Ord, { let offset_native = R::Native::from_usize(offset) - .ok_or_else(|| vortex_err!("Offset {offset} exceeds run-end index capacity"))?; + .ok_or_else(|| vortex_err!(Overflow: "Offset {offset} exceeds run-end index capacity"))?; let length_native = R::Native::from_usize(length) - .ok_or_else(|| vortex_err!("Length {length} exceeds run-end index capacity"))?; + .ok_or_else(|| vortex_err!(Overflow: "Length {length} exceeds run-end index capacity"))?; let ends_prim = ends.as_primitive::(); if offset == 0 && ends_prim.values().last() == Some(&length_native) { @@ -171,7 +171,7 @@ fn constant_to_run_end( DataType::Int16 => build_constant_run_array::(len, &values), DataType::Int32 => build_constant_run_array::(len, &values), DataType::Int64 => build_constant_run_array::(len, &values), - _ => vortex_bail!("Unsupported run-end index type: {:?}", ends_type), + _ => vortex_bail!(InvalidArgument: "Unsupported run-end index type: {:?}", ends_type), } } @@ -179,8 +179,9 @@ fn build_constant_run_array( len: usize, values: &ArrowArrayRef, ) -> VortexResult { - let end = R::Native::from_usize(len) - .ok_or_else(|| vortex_err!("Array length {len} exceeds run-end index capacity"))?; + let end = R::Native::from_usize(len).ok_or_else( + || vortex_err!(Overflow: "Array length {len} exceeds run-end index capacity"), + )?; let run_ends = arrow_array::PrimitiveArray::::from_value(end, 1); Ok(Arc::new(RunArray::::try_new(&run_ends, values)?) as ArrowArrayRef) } @@ -313,7 +314,7 @@ mod tests { let ree_arrow = result .as_any() .downcast_ref::>() - .ok_or_else(|| vortex_err!("expected Int32 run-end array"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int32 run-end array"))?; assert_eq!(ree_arrow.run_ends().values(), &[2, 4]); // The RunEnd fast path exports the values buffer zero-copy; the flat-then-recode @@ -322,7 +323,7 @@ mod tests { .values() .as_any() .downcast_ref::() - .ok_or_else(|| vortex_err!("expected Int64 values"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int64 values"))?; assert_eq!(arrow_values.values().as_ptr(), values_ptr); let expected = RunArray::::try_new( &Int32Array::from(vec![2, 4]), @@ -369,13 +370,13 @@ mod tests { let ree = result .as_any() .downcast_ref::>() - .ok_or_else(|| vortex_err!("expected Int32 run-end array"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int32 run-end array"))?; assert_eq!(ree.run_ends().values(), expected_ends); let values = ree .values() .as_any() .downcast_ref::() - .ok_or_else(|| vortex_err!("expected Int64 values"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int64 values"))?; assert_eq!(values.values(), expected_values); Ok(()) } diff --git a/vortex-arrow/src/executor/struct_.rs b/vortex-arrow/src/executor/struct_.rs index 76946d8f01a..2e3d80c534c 100644 --- a/vortex-arrow/src/executor/struct_.rs +++ b/vortex-arrow/src/executor/struct_.rs @@ -149,7 +149,7 @@ fn create_from_fields( vortex_ensure_eq!( vortex_fields.len(), fields.len(), - "StructArray field count must match the target Arrow type" + InvalidArgument: "StructArray field count must match the target Arrow type" ); let mut arrow_arrays = Vec::with_capacity(vortex_fields.len()); @@ -160,7 +160,7 @@ fn create_from_fields( exporter.execute_arrow(vx_field.clone(), Some(field.as_ref()), ctx)?; vortex_ensure!( field.is_nullable() || arrow_field.null_count() == 0, - "Cannot convert field '{}' to non-nullable Arrow field because it contains nulls", + InvalidArgument: "Cannot convert field '{}' to non-nullable Arrow field because it contains nulls", field.name() ); arrow_arrays.push(arrow_field); diff --git a/vortex-arrow/src/executor/temporal.rs b/vortex-arrow/src/executor/temporal.rs index 220afdb9bbc..8a21939a07a 100644 --- a/vortex-arrow/src/executor/temporal.rs +++ b/vortex-arrow/src/executor/temporal.rs @@ -147,7 +147,7 @@ fn validate_temporal_extension(array: &ArrayRef, target: &DataType) -> VortexRes }; let Some(temporal) = ext.metadata_opt::() else { vortex_bail!( - "Cannot convert extension {} to Arrow type {target}", + MismatchedTypes: "Cannot convert extension {} to Arrow type {target}", ext.id() ); }; @@ -171,18 +171,18 @@ fn validate_temporal_extension(array: &ArrayRef, target: &DataType) -> VortexRes let src_arrow_unit = crate::dtype::to_arrow_time_unit(*unit)?; if src_arrow_unit != *arrow_unit { vortex_bail!( - "Cannot convert Timestamp({unit}) to Arrow Timestamp({arrow_unit:?}): unit mismatch" + MismatchedTypes: "Cannot convert Timestamp({unit}) to Arrow Timestamp({arrow_unit:?}): unit mismatch" ); } if src_tz != tgt_tz { vortex_bail!( - "Cannot convert Timestamp(tz={src_tz:?}) to Arrow Timestamp(tz={tgt_tz:?}): timezone mismatch" + MismatchedTypes: "Cannot convert Timestamp(tz={src_tz:?}) to Arrow Timestamp(tz={tgt_tz:?}): timezone mismatch" ); } Ok(()) } (temporal, target) => vortex_bail!( - "Cannot convert {} to Arrow type {target}", + MismatchedTypes: "Cannot convert {} to Arrow type {target}", match temporal { TemporalMetadata::Date(unit) => format!("Date({unit})"), TemporalMetadata::Time(unit) => format!("Time({unit})"), diff --git a/vortex-arrow/src/run_end_import.rs b/vortex-arrow/src/run_end_import.rs index abae401f506..bc1966a38f9 100644 --- a/vortex-arrow/src/run_end_import.rs +++ b/vortex-arrow/src/run_end_import.rs @@ -36,7 +36,7 @@ where vortex_ensure_eq!( ends.len(), values.len(), - "Arrow run-end array must have one value per run end" + InvalidArgument: "Arrow run-end array must have one value per run end" ); // Arrow slices a RunArray by adjusting the logical offset/length while keeping the full diff --git a/vortex-arrow/src/scalar.rs b/vortex-arrow/src/scalar.rs index 5039e2d0907..efd1c0bad4d 100644 --- a/vortex-arrow/src/scalar.rs +++ b/vortex-arrow/src/scalar.rs @@ -75,14 +75,22 @@ impl ToArrowDatum for Scalar { DType::Decimal(..) => decimal_to_arrow(value.as_decimal()), DType::Utf8(_) => utf8_to_arrow(value.as_utf8()), DType::Binary(_) => binary_to_arrow(value.as_binary()), - DType::List(..) => vortex_bail!("list scalar conversion is not supported"), + DType::List(..) => { + vortex_bail!(InvalidArgument: "list scalar conversion is not supported") + } DType::FixedSizeList(..) => { - vortex_bail!("fixed-size list scalar conversion is not supported") + vortex_bail!(InvalidArgument: "fixed-size list scalar conversion is not supported") } DType::Map(..) => map_to_arrow(value.as_map()), - DType::Struct(..) => vortex_bail!("struct scalar conversion is not supported"), - DType::Union(..) => vortex_bail!("union scalar conversion is not supported"), - DType::Variant(_) => vortex_bail!("Variant scalar conversion is not supported"), + DType::Struct(..) => { + vortex_bail!(InvalidArgument: "struct scalar conversion is not supported") + } + DType::Union(..) => { + vortex_bail!(InvalidArgument: "union scalar conversion is not supported") + } + DType::Variant(_) => { + vortex_bail!(InvalidArgument: "Variant scalar conversion is not supported") + } DType::Extension(..) => extension_to_arrow(value.as_extension()), } } @@ -113,7 +121,7 @@ fn primitive_to_arrow(scalar: PrimitiveScalar<'_>) -> Result, Vor /// Convert a [`DecimalScalar`] to an Arrow [`Datum`]. fn decimal_to_arrow(scalar: DecimalScalar<'_>) -> Result, VortexError> { let DType::Decimal(decimal_dtype, _) = scalar.dtype() else { - vortex_bail!("Expected decimal scalar, got {}", scalar.dtype()); + vortex_bail!(MismatchedTypes: "Expected decimal scalar, got {}", scalar.dtype()); }; let precision = decimal_dtype.precision(); let scale = decimal_dtype.scale(); @@ -124,7 +132,7 @@ fn decimal_to_arrow(scalar: DecimalScalar<'_>) -> Result, VortexE if precision <= 38 { let value = value.maybe_i128().ok_or_else(|| { vortex_err!( - "Decimal value {value} cannot fit in Arrow Decimal128 for precision {precision}" + Overflow: "Decimal value {value} cannot fit in Arrow Decimal128 for precision {precision}" ) })?; decimal128_scalar(value, precision, scale) @@ -201,7 +209,7 @@ fn map_to_arrow(scalar: MapScalar<'_>) -> Result, VortexError> { let entries_len = entries.len(); let entries_len = i32::try_from(entries_len).map_err(|_| { vortex_err!( - "Cannot convert map scalar with {entries_len} entries to Arrow: MapArray offsets are i32" + MismatchedTypes: "Cannot convert map scalar with {entries_len} entries to Arrow: MapArray offsets are i32" ) })?; let offsets = OffsetBuffer::new(vec![0_i32, entries_len].into()); @@ -241,7 +249,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr let ext_dtype = scalar.ext_dtype(); let Some(temporal) = ext_dtype.metadata_opt::() else { vortex_bail!( - "Cannot convert extension scalar {} to Arrow", + MismatchedTypes: "Cannot convert extension scalar {} to Arrow", ext_dtype.id() ) }; @@ -249,7 +257,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr let storage_scalar = scalar.to_storage_scalar(); let primitive = storage_scalar .as_primitive_opt() - .ok_or_else(|| vortex_err!("Expected primitive scalar"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected primitive scalar"))?; match temporal { TemporalMetadata::Timestamp(unit, tz) => { @@ -268,7 +276,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr timestamp_to_arrow_scalar!(value, tz.clone(), TimestampSecondArray) } TimeUnit::Days => { - vortex_bail!("Unsupported TimeUnit {unit} for {}", ext_dtype.id()) + vortex_bail!(InvalidArgument: "Unsupported TimeUnit {unit} for {}", ext_dtype.id()) } } } @@ -280,7 +288,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr value_to_arrow_scalar!(primitive.as_::(), Date32Array) } TimeUnit::Nanoseconds | TimeUnit::Microseconds | TimeUnit::Seconds => { - vortex_bail!("Unsupported TimeUnit {unit} for {}", ext_dtype.id()) + vortex_bail!(InvalidArgument: "Unsupported TimeUnit {unit} for {}", ext_dtype.id()) } }, TemporalMetadata::Time(unit) => match unit { @@ -297,7 +305,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr value_to_arrow_scalar!(primitive.as_::(), Time32SecondArray) } TimeUnit::Days => { - vortex_bail!("Unsupported TimeUnit {unit} for {}", ext_dtype.id()) + vortex_bail!(InvalidArgument: "Unsupported TimeUnit {unit} for {}", ext_dtype.id()) } }, } @@ -852,11 +860,11 @@ mod tests { } fn serialize_metadata(&self, _options: &Self::Metadata) -> VortexResult> { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!("not implemented") + vortex_bail!(NotImplemented: "not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { diff --git a/vortex-arrow/src/session.rs b/vortex-arrow/src/session.rs index 32108a4f599..a847bac834f 100644 --- a/vortex-arrow/src/session.rs +++ b/vortex-arrow/src/session.rs @@ -333,7 +333,7 @@ impl ArrowSession { return Ok(field); } } - vortex_bail!("extension type cannot be converted to Arrow without a plugin: {ext}"); + vortex_bail!(InvalidArgument: "extension type cannot be converted to Arrow without a plugin: {ext}"); } DType::Variant(_) => { // TODO(Adam): This currently encodes information about parquet-variant @@ -371,7 +371,7 @@ impl ArrowSession { /// extensions are preserved via [`Self::to_arrow_field`]. pub fn to_arrow_schema(&self, dtype: &DType) -> VortexResult { let DType::Struct(struct_dtype, _) = dtype else { - vortex_bail!("to_arrow_schema requires a top-level struct dtype, got {dtype}"); + vortex_bail!(InvalidArgument: "to_arrow_schema requires a top-level struct dtype, got {dtype}"); }; let mut fields = Vec::with_capacity(struct_dtype.names().len()); for (name, field_dtype) in struct_dtype.names().iter().zip(struct_dtype.fields()) { @@ -447,22 +447,22 @@ impl ArrowSession { DataType::Map(entries, keys_sorted) => { vortex_ensure!( !entries.is_nullable(), - "Arrow map entries field must be non-nullable" + InvalidArgument: "Arrow map entries field must be non-nullable" ); let DataType::Struct(fields) = entries.data_type() else { vortex_bail!( - "Arrow map entries field must have Struct type, got {:?}", + MismatchedTypes: "Arrow map entries field must have Struct type, got {:?}", entries.data_type() ); }; vortex_ensure_eq!( fields.len(), 2, - "Arrow map entries struct must contain exactly two fields" + InvalidArgument: "Arrow map entries struct must contain exactly two fields" ); vortex_ensure!( !fields[0].is_nullable(), - "Arrow map key field must be non-nullable" + InvalidArgument: "Arrow map key field must be non-nullable" ); DType::map( self.from_arrow_field(fields[0].as_ref())?, @@ -516,7 +516,7 @@ impl ArrowSession { batch: RecordBatch, schema: &Schema, ) -> VortexResult { - vortex_ensure_eq!(batch.num_columns(), schema.fields().len()); + vortex_ensure_eq!(batch.num_columns(), schema.fields().len(), InvalidArgument); let length = batch.num_rows(); let names = FieldNames::from_iter( schema @@ -634,7 +634,7 @@ impl ArrowSession { vortex_ensure_eq!( arr.len(), len, - "Arrow importer {} returned {} elements for an array of {}", + AssertionFailed: "Arrow importer {} returned {} elements for an array of {}", plugin.arrow_ext_id(), arr.len(), len @@ -645,7 +645,7 @@ impl ArrowSession { vortex_ensure_eq!( arr.len(), len, - "Arrow importer {} declined and returned {} elements for an array of {}", + AssertionFailed: "Arrow importer {} declined and returned {} elements for an array of {}", plugin.arrow_ext_id(), arr.len(), len @@ -786,7 +786,7 @@ impl ArrowSession { DataType::Int32 => self.run_end_from_arrow::(array, &values_field), DataType::Int64 => self.run_end_from_arrow::(array, &values_field), ends_dt => vortex_bail!( - "Arrow run-end array run ends must be Int16, Int32 or Int64, got {ends_dt}" + InvalidArgument: "Arrow run-end array run ends must be Int16, Int32 or Int64, got {ends_dt}" ), } } @@ -822,7 +822,7 @@ impl ArrowSession { let run_array = array .as_any() .downcast_ref::>() - .ok_or_else(|| vortex_err!("expected an Arrow RunArray, got {}", array.data_type()))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected an Arrow RunArray, got {}", array.data_type()))?; let values = self.from_arrow_array_inner(ArrowArrayRef::clone(run_array.values()), values_field)?; run_end_from_arrow(run_array, values) @@ -901,7 +901,7 @@ impl ArrowExporter<'_> { vortex_ensure_eq!( arrow.len(), len, - "Arrow array length does not match Vortex array length after conversion to {:?}", + AssertionFailed: "Arrow array length does not match Vortex array length after conversion to {:?}", arrow ); return Ok(arrow); diff --git a/vortex-bench/src/conversions.rs b/vortex-bench/src/conversions.rs index 1398ea37835..376a6d2085c 100644 --- a/vortex-bench/src/conversions.rs +++ b/vortex-bench/src/conversions.rs @@ -549,7 +549,8 @@ fn wkb_field_to_little_endian(field: &ArrayRef, ctx: &mut ExecutionCtx) -> Vorte return Ok(None); } let wkb = values.bytes_at(i); - let geometry = read_wkb(wkb.as_slice()).map_err(|e| vortex_err!("invalid WKB: {e}"))?; + let geometry = read_wkb(wkb.as_slice()) + .map_err(|e| vortex_err!(InvalidArgument: "invalid WKB: {e}"))?; let mut encoded = Vec::with_capacity(wkb.len()); write_geometry( &mut encoded, @@ -558,7 +559,7 @@ fn wkb_field_to_little_endian(field: &ArrayRef, ctx: &mut ExecutionCtx) -> Vorte endianness: Endianness::LittleEndian, }, ) - .map_err(|e| vortex_err!("re-encoding WKB as little-endian: {e}"))?; + .map_err(|e| vortex_err!(Serde: "re-encoding WKB as little-endian: {e}"))?; Ok(Some(encoded)) }) .collect::>()?; diff --git a/vortex-bench/src/datasets/mod.rs b/vortex-bench/src/datasets/mod.rs index 89b3a6782b2..d7dde97f544 100644 --- a/vortex-bench/src/datasets/mod.rs +++ b/vortex-bench/src/datasets/mod.rs @@ -183,7 +183,7 @@ impl BenchmarkDataset { ], BenchmarkDataset::ClickBench { .. } | BenchmarkDataset::ClickBenchSorted => &["hits"], BenchmarkDataset::PublicBi { .. } => { - vortex_panic!("PublicBi table names are not implemented") + vortex_panic!(NotImplemented: "PublicBi table names are not implemented") } BenchmarkDataset::SpatialBench { .. } => &["trip", "building", "customer", "zone"], BenchmarkDataset::StatPopGen { .. } => &["statpopgen"], diff --git a/vortex-bench/src/lib.rs b/vortex-bench/src/lib.rs index 03172307dce..2162c9a6f15 100644 --- a/vortex-bench/src/lib.rs +++ b/vortex-bench/src/lib.rs @@ -107,14 +107,14 @@ impl FromStr for Target { fn from_str(target_string: &str) -> Result { let split = target_string.split(":").collect_vec(); let [engine_str, format_str] = split.as_slice() else { - vortex_panic!("invalid target string {}", target_string); + vortex_panic!(InvalidArgument: "invalid target string {}", target_string); }; Ok(Self { engine: Engine::from_str(engine_str, true) - .map_err(|e| { + .map_err(|e| { vortex_err!( - "cannot convert str ({}) to an Engine oneof([{}]), got error {}", + MismatchedTypes: "cannot convert str ({}) to an Engine oneof([{}]), got error {}", *engine_str, Engine::value_variants().iter().join(","), e @@ -122,9 +122,9 @@ impl FromStr for Target { }) .vortex_expect("operation should succeed in benchmark"), format: Format::from_str(format_str, true) - .map_err(|e| { + .map_err(|e| { vortex_err!( - "cannot convert str ({}) to a Format oneof([{}]), got error {}", + MismatchedTypes: "cannot convert str ({}) to a Format oneof([{}]), got error {}", *format_str, Format::value_variants().iter().join(","), e diff --git a/vortex-bench/src/measurements.rs b/vortex-bench/src/measurements.rs index 6eeceda6dbb..01c9a89ce90 100644 --- a/vortex-bench/src/measurements.rs +++ b/vortex-bench/src/measurements.rs @@ -74,7 +74,9 @@ impl Div for MeasurementValue { (MeasurementValue::Int(a), MeasurementValue::Int(b)) => { MeasurementValue::Float(a as f64 / b as f64) } - _ => vortex_panic!("Can't divide two measurement values of different kinds"), + _ => { + vortex_panic!(MismatchedTypes: "Can't divide two measurement values of different kinds") + } } } } @@ -99,7 +101,9 @@ impl Add for MeasurementValue { MeasurementValue::Float(a + b) } (MeasurementValue::Int(a), MeasurementValue::Int(b)) => MeasurementValue::Int(a + b), - _ => vortex_panic!("Can't subtract two measurement values of different kinds"), + _ => { + vortex_panic!(MismatchedTypes: "Can't subtract two measurement values of different kinds") + } } } } @@ -113,7 +117,9 @@ impl Sub for MeasurementValue { MeasurementValue::Float(a - b) } (MeasurementValue::Int(a), MeasurementValue::Int(b)) => MeasurementValue::Int(a - b), - _ => vortex_panic!("Can't subtract two measurement values of different kinds"), + _ => { + vortex_panic!(MismatchedTypes: "Can't subtract two measurement values of different kinds") + } } } } @@ -178,7 +184,7 @@ impl TimingMeasurement { pub fn mean_time(&self) -> Duration { let len = self.runs.len(); if len == 0 { - vortex_panic!("cannot have no runs"); + vortex_panic!(InvalidArgument: "cannot have no runs"); } let total_nanos: u128 = self.runs.iter().map(|d| d.as_nanos()).sum(); @@ -194,7 +200,7 @@ impl TimingMeasurement { pub fn median_time(&self) -> Duration { let len = self.runs.len(); if len == 0 { - vortex_panic!("cannot have no runs"); + vortex_panic!(InvalidArgument: "cannot have no runs"); } let mut sorted_runs = self.runs.clone(); @@ -253,7 +259,7 @@ impl QueryMeasurement { pub fn median_run(&self) -> Duration { let len = self.runs.len(); if len == 0 { - vortex_panic!("cannot have no runs"); + vortex_panic!(InvalidArgument: "cannot have no runs"); } let mut sorted_runs = self.runs.clone(); @@ -356,7 +362,7 @@ impl ToJson for CompressionTimingMeasurement { Format::Parquet => (format!("parquet_rs-zstd {}", self.name), Engine::Vortex), Format::Lance => (format!("lance {}", self.name), Engine::Vortex), _ => vortex_panic!( - "CompressionTimingMeasurement only supports arrow-ipc, vortex, lance, and parquet formats" + NotImplemented: "CompressionTimingMeasurement only supports arrow-ipc, vortex, lance, and parquet formats" ), }; diff --git a/vortex-bench/src/public_bi.rs b/vortex-bench/src/public_bi.rs index 3e651df5bb7..35879cd6d2e 100644 --- a/vortex-bench/src/public_bi.rs +++ b/vortex-bench/src/public_bi.rs @@ -150,10 +150,11 @@ impl PBIDatasets { let name = path .file_name() .into_string() - .map_err(|e| vortex_err!("Not a unicode name: {e:?}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "Not a unicode name: {e:?}"))?; Ok(( - ::from_str(name.trim(), true) - .map_err(|_e| vortex_err!("unsupported dataset: {} {_e}", &name))?, + ::from_str(name.trim(), true).map_err( + |_e| vortex_err!(InvalidArgument: "unsupported dataset: {} {_e}", &name), + )?, PBIBenchmark { name, base_path: path.path(), @@ -167,7 +168,7 @@ impl PBIDatasets { pub fn get(&self, dataset: PBIDataset) -> &PBIBenchmark { self.benchmarks .get(&dataset) - .ok_or_else(|| vortex_err!("{:?} not found", dataset)) + .ok_or_else(|| vortex_err!(NotFound: "{:?} not found", dataset)) .unwrap() } } @@ -193,14 +194,14 @@ impl PBIBenchmark { let file_name = sql_file .file_name() .into_string() - .map_err(|e| vortex_err!("Not a unicode name: {e:?}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "Not a unicode name: {e:?}"))?; let query_idx = file_name .strip_suffix(".sql") .ok_or_else(|| { - vortex_err!("found non-sql file under queries folder {file_name}") + vortex_err!(InvalidArgument: "found non-sql file under queries folder {file_name}") })? .parse() - .map_err(|_| vortex_err!("non numeric filename {file_name}"))?; + .map_err(|_| vortex_err!(InvalidArgument: "non numeric filename {file_name}"))?; let query = fs::read_to_string(sql_file.path())?; Ok((query_idx, query)) }) diff --git a/vortex-bench/src/runner.rs b/vortex-bench/src/runner.rs index d0795fca288..d47b5cc5a51 100644 --- a/vortex-bench/src/runner.rs +++ b/vortex-bench/src/runner.rs @@ -322,8 +322,8 @@ impl SqlBenchmarkRunner { tracing::debug!(%format, query_idx, "Running query"); self.run_query(query_idx, format, iterations, || { execute(&mut ctx, query_idx, format, query.as_str()).unwrap_or_else( - |err| { - vortex_panic!("query {query_idx} failed: {err}"); + |err| { + vortex_panic!(AssertionFailed: "query {query_idx} failed: {err}"); }, ) }); @@ -403,8 +403,8 @@ impl SqlBenchmarkRunner { let start = Instant::now(); let (timing, result) = execute(query_idx, &ctx, query.as_str()) .await - .unwrap_or_else(|err| { - vortex_panic!("query {query_idx} failed: {err}"); + .unwrap_or_else(|err| { + vortex_panic!(AssertionFailed: "query {query_idx} failed: {err}"); }); let elapsed = timing.unwrap_or_else(|| start.elapsed()); runs.push(elapsed); diff --git a/vortex-bench/src/statpopgen/builder.rs b/vortex-bench/src/statpopgen/builder.rs index 4e11b4e43e4..cf406527c2e 100644 --- a/vortex-bench/src/statpopgen/builder.rs +++ b/vortex-bench/src/statpopgen/builder.rs @@ -277,7 +277,7 @@ impl<'a> GnomADBuilder<'a> { self.POS_builder.append_value( record .variant_start() - .ok_or_else(|| vortex_err!("pos must not be null"))?? + .ok_or_else(|| vortex_err!(InvalidArgument: "pos must not be null"))?? .get() as u64, ); self.ID_builder.append_value(record.ids().as_ref()); @@ -341,7 +341,7 @@ impl<'a> GnomADBuilder<'a> { .SB_builder .values() .append_option(parse_list_int32_format(value)?), - _ => vortex_bail!("unknown field {field}"), + _ => vortex_bail!(NotFound: "unknown field {field}"), } } } diff --git a/vortex-bench/src/statpopgen/vcf_conversion.rs b/vortex-bench/src/statpopgen/vcf_conversion.rs index 8df82ee26f7..4eb1721803f 100644 --- a/vortex-bench/src/statpopgen/vcf_conversion.rs +++ b/vortex-bench/src/statpopgen/vcf_conversion.rs @@ -29,13 +29,17 @@ pub fn builder_from_info(info: &Map) -> InfoArrayBuilder { (Number::Count(1), Type::Float) => InfoArrayBuilder::Float(Default::default()), (Number::Count(0), Type::Flag) => InfoArrayBuilder::Flag(Default::default()), (Number::Count(1), Type::Character) => { - vortex_panic!("Character INFO fields are not supported") + vortex_panic!(NotImplemented: "Character INFO fields are not supported") } (Number::Count(1), Type::String) => InfoArrayBuilder::String(Default::default()), (_, Type::Integer) => InfoArrayBuilder::ListInteger(Default::default()), (_, Type::Float) => InfoArrayBuilder::ListFloat(Default::default()), - (_, Type::Flag) => vortex_panic!("Flag INFO fields with a count are not supported"), - (_, Type::Character) => vortex_panic!("Character INFO fields are not supported"), + (_, Type::Flag) => { + vortex_panic!(NotImplemented: "Flag INFO fields with a count are not supported") + } + (_, Type::Character) => { + vortex_panic!(NotImplemented: "Character INFO fields are not supported") + } (_, Type::String) => InfoArrayBuilder::ListString(Default::default()), } } @@ -50,13 +54,17 @@ pub fn data_type_from_info(info: &Map) -> DataType { (Number::Count(1), Type::Float) => Float32, (Number::Count(0), Type::Flag) => Boolean, (Number::Count(1), Type::Character) => { - vortex_panic!("Character INFO fields are not supported") + vortex_panic!(NotImplemented: "Character INFO fields are not supported") } (Number::Count(1), Type::String) => Utf8, (_, Type::Integer) => list(Int32), (_, Type::Float) => list(Float32), - (_, Type::Flag) => vortex_panic!("Flag INFO fields with a count are not supported"), - (_, Type::Character) => vortex_panic!("Character INFO fields are not supported"), + (_, Type::Flag) => { + vortex_panic!(NotImplemented: "Flag INFO fields with a count are not supported") + } + (_, Type::Character) => { + vortex_panic!(NotImplemented: "Character INFO fields are not supported") + } (_, Type::String) => list(Utf8), } } @@ -66,7 +74,7 @@ pub fn value_int32(v: Option) -> VortexResult> { None => None, Some(Value::Integer(x)) => Some(x), - _ => vortex_bail!("expected int32 {:?}", v), + _ => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), }) } @@ -74,7 +82,7 @@ pub fn value_float32(v: Option) -> VortexResult> { Ok(match v { None => None, Some(Value::Float(x)) => Some(x), - _ => vortex_bail!("expected f64 {:?}", v), + _ => vortex_bail!(InvalidArgument: "expected f64 {:?}", v), }) } @@ -82,7 +90,7 @@ pub fn value_string(v: Option) -> VortexResult>> { Ok(match v { None => None, Some(Value::String(x)) => Some(x), - _ => vortex_bail!("expected string {:?}", v), + _ => vortex_bail!(InvalidArgument: "expected string {:?}", v), }) } @@ -90,7 +98,7 @@ pub fn value_boolean(v: Option) -> VortexResult { Ok(match v { None => false, Some(Value::Flag) => true, - _ => vortex_bail!("expected bool {:?}", v), + _ => vortex_bail!(MismatchedTypes: "expected bool {:?}", v), }) } @@ -101,9 +109,9 @@ pub fn value_list_int32<'a>( None => None, Some(Value::Array(a)) => match a { Array::Integer(values) => Some(values), - v => vortex_bail!("expected int32 {:?}", v), + v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), }, - v => vortex_bail!("expected int32 {:?}", v), + v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), }) } @@ -114,9 +122,9 @@ pub fn value_list_float32<'a>( None => None, Some(Value::Array(a)) => match a { Array::Float(values) => Some(values), - v => vortex_bail!("expected int32 {:?}", v), + v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), }, - v => vortex_bail!("expected f64 {:?}", v), + v => vortex_bail!(InvalidArgument: "expected f64 {:?}", v), }) } @@ -127,9 +135,9 @@ pub fn value_list_string<'a>( None => None, Some(Value::Array(a)) => match a { Array::String(values) => Some(values), - v => vortex_bail!("expected int32 {:?}", v), + v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), }, - v => vortex_bail!("expected string {:?}", v), + v => vortex_bail!(InvalidArgument: "expected string {:?}", v), }) } @@ -138,7 +146,7 @@ pub fn parse_genotype(gt: Option) -> VortexResult> { return Ok(None); }; let EntryValue::Genotype(gt) = gt else { - vortex_bail!("expected genotype {:?}", gt) + vortex_bail!(InvalidArgument: "expected genotype {:?}", gt) }; match gt .iter() @@ -146,7 +154,7 @@ pub fn parse_genotype(gt: Option) -> VortexResult> { { [None, None] => Ok(None), [Some(l), Some(r)] => Ok(Some(l as u64 + r as u64)), - _ => vortex_bail!("wtf {:?}", gt), + _ => vortex_bail!(AssertionFailed: "wtf {:?}", gt), } } @@ -155,7 +163,7 @@ pub fn parse_int32_format(x: Option) -> VortexResult> { return Ok(None); }; let EntryValue::Integer(x) = x else { - vortex_bail!("expected int32 {:?}", x) + vortex_bail!(MismatchedTypes: "expected int32 {:?}", x) }; Ok(Some(x)) } @@ -171,7 +179,7 @@ pub fn parse_pgt_format(x: Option) -> VortexResult> { EntryValue::String(x) if x == "0|1" => Some(1), EntryValue::String(x) if x == "1|0" => Some(2), EntryValue::String(x) if x == "1|1" => Some(3), - _ => vortex_bail!("expected biallelic phased genotype {:?}", x), + _ => vortex_bail!(InvalidArgument: "expected biallelic phased genotype {:?}", x), }) } @@ -181,7 +189,7 @@ pub fn parse_string_format<'a>(x: Option>) -> VortexResult

() - .ok_or_else(|| vortex_err!("Expected non-null primitive scalar value"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null primitive scalar value"))?; // Allocate output buffer on device let mut output_buffer = ctx.device_alloc::

(array_len)?; @@ -154,12 +154,12 @@ where let decimal_scalar = array.scalar().as_decimal(); let decimal_value = decimal_scalar .decimal_value() - .ok_or_else(|| vortex_err!("Expected non-null decimal scalar value"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null decimal scalar value"))?; // Cast the decimal value to the native type let value: D = decimal_value .cast::() - .ok_or_else(|| vortex_err!("Failed to cast decimal value to native type"))?; + .ok_or_else(|| vortex_err!(Overflow: "Failed to cast decimal value to native type"))?; // Allocate output buffer on device let mut output_buffer = ctx.device_alloc::(array_len)?; diff --git a/vortex-cuda/src/kernel/arrays/dict.rs b/vortex-cuda/src/kernel/arrays/dict.rs index e9bb20daa94..c3d9754c6e5 100644 --- a/vortex-cuda/src/kernel/arrays/dict.rs +++ b/vortex-cuda/src/kernel/arrays/dict.rs @@ -63,7 +63,7 @@ impl CudaExecute for DictExecutor { DType::Decimal(..) => execute_dict_decimal(dict_array, ctx).await, DType::Primitive(..) => execute_dict_prim(dict_array, ctx).await, DType::Utf8(..) | DType::Binary(..) => execute_dict_varbinview(dict_array, ctx).await, - dt => vortex_bail!("unsupported decompress for DType={dt}"), + dt => vortex_bail!(InvalidArgument: "unsupported decompress for DType={dt}"), } } } @@ -117,7 +117,7 @@ async fn execute_dict_bool_typed( codes: PrimitiveArray, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - vortex_ensure!(!codes.is_empty(), "cannot CUDA-decode an empty dictionary"); + vortex_ensure!(!codes.is_empty(), InvalidArgument: "cannot CUDA-decode an empty dictionary"); let codes_len = codes.len(); let values_len = values.len(); diff --git a/vortex-cuda/src/kernel/arrays/list.rs b/vortex-cuda/src/kernel/arrays/list.rs index 167c12df9c4..66236e4630e 100644 --- a/vortex-cuda/src/kernel/arrays/list.rs +++ b/vortex-cuda/src/kernel/arrays/list.rs @@ -50,7 +50,7 @@ impl CudaExecute for ListExecutor { ) -> VortexResult { let list = array .try_downcast::() - .map_err(|_| vortex_err!("Expected ListArray"))?; + .map_err(|_| vortex_err!(MismatchedTypes: "Expected ListArray"))?; let list_len = list.len(); let validity = execute_validity_cuda(list.list_validity(), list_len, ctx).await?; @@ -81,7 +81,7 @@ impl CudaExecute for ListExecutor { vortex_ensure_eq!( offsets.len(), list_len + 1, - "ListArray must have one more offset than lists" + InvalidArgument: "ListArray must have one more offset than lists" ); let offsets_ptype = offsets.ptype(); diff --git a/vortex-cuda/src/kernel/arrays/masked.rs b/vortex-cuda/src/kernel/arrays/masked.rs index c318f7a8af9..371708bd5bc 100644 --- a/vortex-cuda/src/kernel/arrays/masked.rs +++ b/vortex-cuda/src/kernel/arrays/masked.rs @@ -37,7 +37,7 @@ impl CudaExecute for MaskedExecutor { ) -> VortexResult { let masked = array .try_downcast::() - .map_err(|_| vortex_err!("Expected MaskedArray"))?; + .map_err(|_| vortex_err!(InvalidArgument: "Expected MaskedArray"))?; let len = masked.len(); let validity = masked.masked_validity(); @@ -46,7 +46,7 @@ impl CudaExecute for MaskedExecutor { // output validity. Combining two device-resident bitmaps would need a CPU compute pass. if matches!(masked.child().validity()?, Validity::Array(_)) { vortex_bail!( - "MaskedArray child carries a per-element validity bitmap, which cannot be combined with the mask on the GPU" + InvalidArgument: "MaskedArray child carries a per-element validity bitmap, which cannot be combined with the mask on the GPU" ); } diff --git a/vortex-cuda/src/kernel/encodings/alp.rs b/vortex-cuda/src/kernel/encodings/alp.rs index e543db1aca0..07db995116b 100644 --- a/vortex-cuda/src/kernel/encodings/alp.rs +++ b/vortex-cuda/src/kernel/encodings/alp.rs @@ -47,7 +47,7 @@ impl CudaExecute for ALPExecutor { ) -> VortexResult { let array = array .try_downcast::() - .map_err(|_| vortex_err!("Expected ALPArray"))?; + .map_err(|_| vortex_err!(InvalidArgument: "Expected ALPArray"))?; match_each_alp_float_ptype!(array.dtype().as_ptype(), |A| { decode_alp::(array, ctx).await @@ -66,7 +66,7 @@ where A::ALPInt: NativePType + DeviceRepr + Send + Sync + 'static, { let array_len = array.encoded().len(); - vortex_ensure!(array_len > 0, "ALP array must not be empty"); + vortex_ensure!(array_len > 0, InvalidArgument: "ALP array must not be empty"); // Get the exponent factors from the lookup tables. let exponents = array.exponents(); diff --git a/vortex-cuda/src/kernel/encodings/bitpacked.rs b/vortex-cuda/src/kernel/encodings/bitpacked.rs index 3b28692722c..df92f479877 100644 --- a/vortex-cuda/src/kernel/encodings/bitpacked.rs +++ b/vortex-cuda/src/kernel/encodings/bitpacked.rs @@ -66,7 +66,7 @@ pub(crate) fn bitpacked_slice_view( let block_stop = offset_stop.div_ceil(PATCH_CHUNK_SIZE) * PATCH_CHUNK_SIZE; let BitWidthsView::Global(bit_width) = bp.bit_widths() else { - vortex_bail!("CUDA does not support BitPacked arrays with per-block bit widths"); + vortex_bail!(NotImplemented: "CUDA does not support BitPacked arrays with per-block bit widths"); }; let encoded_start = (block_start / 8) * bit_width as usize; let encoded_stop = (block_stop / 8) * bit_width as usize; @@ -122,8 +122,8 @@ impl CudaExecute for BitPackedExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let (array, patch_range) = - Self::try_specialize(array)?.ok_or_else(|| vortex_err!("Expected BitPackedArray"))?; + let (array, patch_range) = Self::try_specialize(array)? + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected BitPackedArray"))?; let ptype = array.ptype(array.dtype()); match_each_integer_ptype!(ptype, |A| { @@ -178,10 +178,10 @@ where validity, } = BitPacked::into_parts(array); let BitWidths::Global(bit_width) = bit_widths else { - vortex_bail!("CUDA does not support BitPacked arrays with per-block bit widths"); + vortex_bail!(NotImplemented: "CUDA does not support BitPacked arrays with per-block bit widths"); }; - vortex_ensure!(len > 0, "Non empty array"); + vortex_ensure!(len > 0, InvalidArgument: "Non empty array"); let offset = offset as usize; let device_input = ctx.ensure_on_device(packed).await?; diff --git a/vortex-cuda/src/kernel/encodings/date_time_parts.rs b/vortex-cuda/src/kernel/encodings/date_time_parts.rs index 9a1a339aa67..ae98090309d 100644 --- a/vortex-cuda/src/kernel/encodings/date_time_parts.rs +++ b/vortex-cuda/src/kernel/encodings/date_time_parts.rs @@ -53,15 +53,15 @@ impl CudaExecute for DateTimePartsExecutor { let output_len = array.len(); let array = array .try_downcast::() - .map_err(|_| vortex_err!("Expected DateTimePartsArray"))?; + .map_err(|_| vortex_err!(InvalidArgument: "Expected DateTimePartsArray"))?; // Extract the temporal metadata from the dtype let DType::Extension(ext) = array.dtype().clone() else { - vortex_bail!("DateTimePartsArray dtype must be an Extension type") + vortex_bail!(InvalidArgument: "DateTimePartsArray dtype must be an Extension type") }; let Some(options) = ext.metadata_opt::() else { - vortex_bail!("DateTimePartsArray must have Timestamp metadata") + vortex_bail!(MismatchedTypes: "DateTimePartsArray must have Timestamp metadata") }; let time_unit = options.unit; @@ -93,7 +93,9 @@ impl CudaExecute for DateTimePartsExecutor { TimeUnit::Microseconds => 1_000_000, TimeUnit::Milliseconds => 1_000, TimeUnit::Seconds => 1, - TimeUnit::Days => vortex_bail!("Cannot decode DateTimeParts with TimeUnit::Days"), + TimeUnit::Days => { + vortex_bail!(NotImplemented: "Cannot decode DateTimeParts with TimeUnit::Days") + } }; let days_canonical = array.days().clone().execute_cuda(ctx).await?; diff --git a/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs b/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs index ee3814ca9fc..e560e30c194 100644 --- a/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs +++ b/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs @@ -32,7 +32,7 @@ impl CudaExecute for DecimalBytePartsExecutor { ctx: &mut CudaExecutionCtx, ) -> VortexResult { let Ok(array) = array.try_downcast::() else { - vortex_bail!("cannot downcast to DecimalBytePartsArray") + vortex_bail!(MismatchedTypes: "cannot downcast to DecimalBytePartsArray") }; let decimal_dtype = *array @@ -43,7 +43,7 @@ impl CudaExecute for DecimalBytePartsExecutor { // Reassembling lower parts into wide decimals is not implemented on the GPU; the MSP // alone is not the value. if !array.lower_parts().is_empty() { - vortex_bail!("DecimalBytePartsArray with lower parts is not supported on GPU") + vortex_bail!(InvalidArgument: "DecimalBytePartsArray with lower parts is not supported on GPU") } let msp = array.msp().clone(); diff --git a/vortex-cuda/src/kernel/encodings/delta.rs b/vortex-cuda/src/kernel/encodings/delta.rs index 0d01b3789c9..2213b7041e4 100644 --- a/vortex-cuda/src/kernel/encodings/delta.rs +++ b/vortex-cuda/src/kernel/encodings/delta.rs @@ -60,7 +60,7 @@ impl CudaExecute for DeltaExecutor { ) -> VortexResult { let delta = array .try_downcast::() - .map_err(|_| vortex_err!("Expected DeltaArray"))?; + .map_err(|_| vortex_err!(InvalidArgument: "Expected DeltaArray"))?; decode_delta(delta, ctx).await } } @@ -98,11 +98,11 @@ async fn decode_delta(array: DeltaArray, ctx: &mut CudaExecutionCtx) -> VortexRe vortex_ensure_eq!( deltas_len % FL_CHUNK, 0, - "Delta deltas child must be padded to a multiple of {FL_CHUNK}, got {deltas_len}" + InvalidArgument: "Delta deltas child must be padded to a multiple of {FL_CHUNK}, got {deltas_len}" ); vortex_ensure!( offset + len <= deltas_len, - "Delta slice {offset}..{} exceeds its {deltas_len} decoded values", + InvalidArgument: "Delta slice {offset}..{} exceeds its {deltas_len} decoded values", offset + len ); let num_chunks = deltas_len / FL_CHUNK; @@ -110,7 +110,7 @@ async fn decode_delta(array: DeltaArray, ctx: &mut CudaExecutionCtx) -> VortexRe let required_bases = num_chunks * lanes; vortex_ensure!( bases.len() >= required_bases, - "Delta needs {required_bases} bases for {num_chunks} chunks, got {}", + InvalidArgument: "Delta needs {required_bases} bases for {num_chunks} chunks, got {}", bases.len() ); diff --git a/vortex-cuda/src/kernel/encodings/for_.rs b/vortex-cuda/src/kernel/encodings/for_.rs index bcec39213a2..ac5d98fb5f6 100644 --- a/vortex-cuda/src/kernel/encodings/for_.rs +++ b/vortex-cuda/src/kernel/encodings/for_.rs @@ -58,12 +58,13 @@ impl CudaExecute for FoRExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected FoRArray"))?; + let array = Self::try_specialize(array) + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected FoRArray"))?; // Per-chunk references have no CUDA kernel yet, so decode them on the CPU. // TODO(mk): implement CUDA FoR decoding for blocked references. let FoRReferences::Global(reference) = array.references() else { - vortex_bail!("CUDA FoR decoding requires a global reference") + vortex_bail!(NotImplemented: "CUDA FoR decoding requires a global reference") }; let reference = reference.clone(); @@ -105,10 +106,10 @@ where P: NativePType + DeviceRepr + Send + Sync + 'static, { let array_len = array.encoded().len(); - vortex_ensure!(array_len > 0, "FoR encoded array must not be empty"); + vortex_ensure!(array_len > 0, InvalidArgument: "FoR encoded array must not be empty"); let FoRReferences::Global(reference) = array.references() else { - vortex_bail!("CUDA FoR decoding requires a global reference") + vortex_bail!(NotImplemented: "CUDA FoR decoding requires a global reference") }; let reference: P = reference .as_primitive() diff --git a/vortex-cuda/src/kernel/encodings/fsst.rs b/vortex-cuda/src/kernel/encodings/fsst.rs index efa499b60ec..bfc8caadee0 100644 --- a/vortex-cuda/src/kernel/encodings/fsst.rs +++ b/vortex-cuda/src/kernel/encodings/fsst.rs @@ -79,7 +79,7 @@ async fn cuda_validity( )), Validity::Array(array) => { let bool_array = array.try_downcast::().map_err(|array| { - vortex_err!("CUDA validity execution produced {}", array.dtype()) + vortex_err!(MismatchedTypes: "CUDA validity execution produced {}", array.dtype()) })?; let BoolDataParts { bits, meta } = bool_array.into_data().into_parts(len); let bit_offset = meta.offset(); @@ -107,7 +107,8 @@ impl CudaExecute for FSSTExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let fsst = Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected FSSTArray"))?; + let fsst = Self::try_specialize(array) + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected FSSTArray"))?; let dtype = fsst.dtype().clone(); let validity = fsst.codes().validity()?; diff --git a/vortex-cuda/src/kernel/encodings/onpair.rs b/vortex-cuda/src/kernel/encodings/onpair.rs index a97aca0941b..c4a98468243 100644 --- a/vortex-cuda/src/kernel/encodings/onpair.rs +++ b/vortex-cuda/src/kernel/encodings/onpair.rs @@ -114,7 +114,7 @@ impl CudaExecute for OnPairExecutor { ) -> VortexResult { let onpair = array .as_typed::() - .ok_or_else(|| vortex_err!("Expected OnPairArray"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected OnPairArray"))?; decode_onpair(onpair, ctx).await } } @@ -153,7 +153,7 @@ async fn decode_onpair( vortex_ensure_eq!( row_total, total_size as u64, - "OnPair uncompressed_lengths total does not match the decoded codes size" + Serde: "OnPair uncompressed_lengths total does not match the decoded codes size" ); let row_offsets_view = row_offsets.cuda_view::()?; let bytes_view = bytes.cuda_view::()?; @@ -185,7 +185,7 @@ async fn decode_onpair( vortex_ensure_eq!( row_total, total_size as u64, - "OnPair uncompressed_lengths total does not match the decoded codes size" + Serde: "OnPair uncompressed_lengths total does not match the decoded codes size" ); let host_bytes = bytes.try_to_host()?.await?; @@ -238,7 +238,7 @@ pub(crate) async fn decode_onpair_varbin( vortex_ensure_eq!( row_total, total_size as u64, - "OnPair uncompressed_lengths total does not match the decoded codes size" + Serde: "OnPair uncompressed_lengths total does not match the decoded codes size" ); Ok(DecodedVarBin { @@ -309,7 +309,9 @@ async fn decode_onpair_bytes( match codes.ptype() { PType::U8 => decode_window::(codes, codes_offsets, lengths, dict, ctx).await, PType::U16 => decode_window::(codes, codes_offsets, lengths, dict, ctx).await, - other => vortex_bail!("OnPair codes must decompress to u8 or u16, got {other}"), + other => { + vortex_bail!(MismatchedTypes: "OnPair codes must decompress to u8 or u16, got {other}") + } } } @@ -382,7 +384,7 @@ where let mut status = ctx.device_alloc::(1)?; ctx.stream() .memset_zeros(&mut status) - .map_err(|e| vortex_err!("Failed to zero OnPair status flag: {e}"))?; + .map_err(|e| vortex_err!(Io: "Failed to zero OnPair status flag: {e}"))?; let staged = stage_codes(codes, &dict, &mut status, ctx).await?; @@ -450,7 +452,7 @@ where let scratch = ctx .stream() .clone_dtoh(&scratch) - .map_err(|e| vortex_err!("Failed to copy OnPair window scratch to host: {e}"))?; + .map_err(|e| vortex_err!(Io: "Failed to copy OnPair window scratch to host: {e}"))?; let [ token_start, token_end, @@ -460,19 +462,19 @@ where status, ] = scratch[..] else { - vortex_bail!("OnPair window resolution returned no bounds"); + vortex_bail!(AssertionFailed: "OnPair window resolution returned no bounds"); }; if status != 0 { - vortex_bail!("OnPair code out of dictionary range"); + vortex_bail!(OutOfBounds: "OnPair code out of dictionary range"); } let heap_size = usize::try_from(chunk_total)?; vortex_ensure!( token_start <= token_end, - "OnPair codes_offsets must be nondecreasing" + InvalidArgument: "OnPair codes_offsets must be nondecreasing" ); vortex_ensure!( token_end <= num_tokens_u64, - "OnPair codes_offsets end {token_end} exceeds codes len {num_tokens_u64}" + InvalidArgument: "OnPair codes_offsets end {token_end} exceeds codes len {num_tokens_u64}" ); if token_start == token_end { // No codes in the window (e.g. a slice covering only null rows). @@ -484,12 +486,12 @@ where let byte_end = usize::try_from(byte_end)?; vortex_ensure!( byte_start <= byte_end && byte_end <= heap_size, - "OnPair window bounds [{byte_start}, {byte_end}) exceed decoded heap size {heap_size}" + OutOfBounds: "OnPair window bounds [{byte_start}, {byte_end}) exceed decoded heap size {heap_size}" ); let total_size = byte_end - byte_start; // A conformant dictionary has no zero-length tokens, so a non-empty code window decodes to at // least one byte. - vortex_ensure!(total_size > 0, "OnPair has codes but decodes to zero bytes"); + vortex_ensure!(total_size > 0, Serde: "OnPair has codes but decodes to zero bytes"); // Decode only batches intersecting the visible token window. The kernel's drain gates 16-byte // stores on `out_start % 16` relative to the buffer base, so the base must be 16-aligned. @@ -641,7 +643,7 @@ async fn ensure_zero_lengths( .await? .into_primitive(); let total = sum_lengths(&lengths)?; - vortex_ensure_eq!(total, 0, "OnPair records decoded bytes but has no codes"); + vortex_ensure_eq!(total, 0, Serde: "OnPair records decoded bytes but has no codes"); Ok(()) } @@ -654,7 +656,7 @@ fn sum_lengths(lengths: &PrimitiveArray) -> VortexResult { for &length in lengths.as_slice::

() { acc = acc .checked_add(AsPrimitive::::as_(length)) - .ok_or_else(|| vortex_err!("OnPair decoded size overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "OnPair decoded size overflow"))?; } Ok(acc) }) @@ -715,7 +717,7 @@ mod tests { let onpair = onpair_compress(&varbin, DEFAULT_CONFIG, ctx.execution_ctx())?; vortex_ensure!( onpair.as_opt::().is_some(), - "expected OnPair array, got {}", + MismatchedTypes: "expected OnPair array, got {}", onpair.encoding_id() ); Ok(onpair) @@ -1029,7 +1031,7 @@ mod tests { &mut cuda_ctx, )? .try_downcast::() - .map_err(|array| vortex_err!("expected OnPair array, got {}", array.encoding_id()))?; + .map_err(|array| vortex_err!(MismatchedTypes: "expected OnPair array, got {}", array.encoding_id()))?; let output = decode_onpair_varbin(onpair, &mut cuda_ctx).await?; assert_eq!(output.dtype, DType::Utf8(Nullability::NonNullable)); diff --git a/vortex-cuda/src/kernel/encodings/runend.rs b/vortex-cuda/src/kernel/encodings/runend.rs index 5519e3de79c..c1113d98299 100644 --- a/vortex-cuda/src/kernel/encodings/runend.rs +++ b/vortex-cuda/src/kernel/encodings/runend.rs @@ -55,11 +55,11 @@ impl CudaExecute for RunEndExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = - Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected RunEndArray"))?; + let array = Self::try_specialize(array) + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected RunEndArray"))?; if !array.dtype().is_primitive() { - vortex_bail!("RunEndExecutor only supports primitive types") + vortex_bail!(NotImplemented: "RunEndExecutor only supports primitive types") } let offset = array.offset(); @@ -103,10 +103,10 @@ async fn decode_runend_typed VortexResult { let num_runs = ends.len(); - vortex_ensure!(num_runs > 0, "run-end array must have at least one run"); + vortex_ensure!(num_runs > 0, InvalidArgument: "run-end array must have at least one run"); vortex_ensure!( output_len > 0, - "run-end output length must be greater than zero" + InvalidArgument: "run-end output length must be greater than zero" ); let PrimitiveDataParts { @@ -402,7 +402,7 @@ mod tests { .execute(runend_array.clone().into_array(), &mut cuda_ctx) .await?; let Validity::Array(validity) = gpu_result.clone().into_primitive().validity()? else { - vortex_bail!("expected expanded validity bitmap"); + vortex_bail!(InvalidArgument: "expected expanded validity bitmap"); }; let bits = &validity.buffer_handles()[0]; let logical_bytes = runend_array.len().div_ceil(8); diff --git a/vortex-cuda/src/kernel/encodings/sequence.rs b/vortex-cuda/src/kernel/encodings/sequence.rs index 86bf56107d4..2a018dcf3da 100644 --- a/vortex-cuda/src/kernel/encodings/sequence.rs +++ b/vortex-cuda/src/kernel/encodings/sequence.rs @@ -37,9 +37,9 @@ impl CudaExecute for SequenceExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = array - .try_downcast::() - .map_err(|_| vortex_err!("SequenceExecutor can only accept SequenceArray"))?; + let array = array.try_downcast::().map_err( + |_| vortex_err!(MismatchedTypes: "SequenceExecutor can only accept SequenceArray"), + )?; let len = array.len(); let nullability = array.dtype().nullability(); diff --git a/vortex-cuda/src/kernel/encodings/zigzag.rs b/vortex-cuda/src/kernel/encodings/zigzag.rs index 33b22bdc29f..38af97f738a 100644 --- a/vortex-cuda/src/kernel/encodings/zigzag.rs +++ b/vortex-cuda/src/kernel/encodings/zigzag.rs @@ -49,8 +49,8 @@ impl CudaExecute for ZigZagExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = - Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected ZigZagArray"))?; + let array = Self::try_specialize(array) + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected ZigZagArray"))?; // The encoded array is unsigned, we decode to signed of the same width. let encoded_ptype = array.encoded().dtype().as_ptype(); @@ -58,7 +58,7 @@ impl CudaExecute for ZigZagExecutor { vortex_ensure_eq!( output_ptype, encoded_ptype.to_signed(), - "ZigZag output type must be the signed equivalent of the encoded type" + MismatchedTypes: "ZigZag output type must be the signed equivalent of the encoded type" ); match_each_unsigned_integer_ptype!(encoded_ptype, |U| { @@ -76,7 +76,7 @@ where U: NativePType + DeviceRepr + Send + Sync + 'static, { let array_len = array.encoded().len(); - vortex_ensure!(array_len > 0, "ZigZag array must not be empty"); + vortex_ensure!(array_len > 0, InvalidArgument: "ZigZag array must not be empty"); // Execute child and copy to device let canonical = array.encoded().clone().execute_cuda(ctx).await?; @@ -110,7 +110,7 @@ where let mut output = ctx.device_alloc::(array_len)?; ctx.stream() .memcpy_dtod(&input_view, &mut output) - .map_err(|err| vortex_err!("Failed to copy shared ZigZag input: {err}"))?; + .map_err(|err| vortex_err!(Io: "Failed to copy shared ZigZag input: {err}"))?; ctx.launch_kernel(&cuda_function, array_len, |args| { args.arg(&mut output).arg(&array_len_u64); })?; diff --git a/vortex-cuda/src/kernel/encodings/zstd.rs b/vortex-cuda/src/kernel/encodings/zstd.rs index 0266fd573aa..3df0b11e129 100644 --- a/vortex-cuda/src/kernel/encodings/zstd.rs +++ b/vortex-cuda/src/kernel/encodings/zstd.rs @@ -109,7 +109,7 @@ pub async fn zstd_kernel_prepare( // Temporary internal buffer size for nvCOMP ZSTD decompression. let nvcomp_temp_buffer_size = nvcomp_zstd::get_decompress_temp_size(num_frames, output_size_max, output_size_total) - .map_err(|e| vortex_err!("nvcomp get_decompress_temp_size failed: {}", e))?; + .map_err(|e| vortex_err!(Io: "nvcomp get_decompress_temp_size failed: {}", e))?; // Async copy frames to the device. let frame_futs = frames @@ -200,7 +200,8 @@ impl CudaExecute for ZstdExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let zstd = Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected ZstdArray"))?; + let zstd = Self::try_specialize(array) + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected ZstdArray"))?; match zstd.dtype() { DType::Binary(_) | DType::Utf8(_) => decode_zstd(zstd, ctx).await, @@ -231,7 +232,7 @@ async fn decode_zstd(array: ZstdArray, ctx: &mut CudaExecutionCtx) -> VortexResu // nvCOMP doesn't support ZSTD dictionaries. if dictionary.is_some() { - return Err(vortex_err!("ZSTD dictionary not supported on GPU")); + return Err(vortex_err!(InvalidArgument: "ZSTD dictionary not supported on GPU")); } if frames.is_empty() { @@ -294,7 +295,7 @@ async fn decode_zstd(array: ZstdArray, ctx: &mut CudaExecutionCtx) -> VortexResu device_statuses_ptr as _, stream.cu_stream().cast(), ) - .map_err(|e| vortex_err!("nvcomp decompress_async failed: {}", e)) + .map_err(|e| vortex_err!(Io: "nvcomp decompress_async failed: {}", e)) } })?; drop(frame_ptr_records); @@ -344,7 +345,7 @@ async fn decode_zstd(array: ZstdArray, ctx: &mut CudaExecutionCtx) -> VortexResu })) } _ => { - vortex_bail!("CUDA ZSTD decompression does not yet support arrays with nulls") + vortex_bail!(NotImplemented: "CUDA ZSTD decompression does not yet support arrays with nulls") } } } diff --git a/vortex-cuda/src/kernel/encodings/zstd_buffers.rs b/vortex-cuda/src/kernel/encodings/zstd_buffers.rs index 2ea33dff00b..7b7cc2e37b3 100644 --- a/vortex-cuda/src/kernel/encodings/zstd_buffers.rs +++ b/vortex-cuda/src/kernel/encodings/zstd_buffers.rs @@ -43,7 +43,7 @@ impl CudaExecute for ZstdBuffersExecutor { ) -> VortexResult { let zstd_buffers = array .try_downcast::() - .map_err(|_| vortex_err!("expected zstd buffers array"))?; + .map_err(|_| vortex_err!(InvalidArgument: "expected zstd buffers array"))?; decode_zstd_buffers(zstd_buffers, ctx).await } } @@ -65,7 +65,7 @@ async fn decode_zstd_buffers( plan.output_size_max(), plan.output_size_total(), ) - .map_err(|e| vortex_err!("nvcomp get_decompress_temp_size failed: {}", e))?; + .map_err(|e| vortex_err!(Io: "nvcomp get_decompress_temp_size failed: {}", e))?; let device_frame_handles = move_frames_to_device(compressed_buffers, ctx).await?; let mut device_output = ctx.device_alloc::(plan.output_size_total())?; @@ -138,7 +138,7 @@ async fn decode_zstd_buffers( device_statuses_ptr as _, stream.cu_stream().cast(), ) - .map_err(|e| vortex_err!("nvcomp decompress_async failed: {}", e)) + .map_err(|e| vortex_err!(Io: "nvcomp decompress_async failed: {}", e)) } })?; drop(frame_ptr_records); @@ -200,14 +200,14 @@ async fn validate_decompress_results( { if status != sys::nvcompStatus_t_nvcompSuccess { return Err(vortex_err!( - "nvcomp chunk {} failed with status {}", + Io: "nvcomp chunk {} failed with status {}", idx, status )); } if actual != expected { return Err(vortex_err!( - "nvcomp chunk {} decompressed size mismatch: expected {}, got {}", + MismatchedTypes: "nvcomp chunk {} decompressed size mismatch: expected {}, got {}", idx, expected, actual diff --git a/vortex-cuda/src/kernel/filter/mod.rs b/vortex-cuda/src/kernel/filter/mod.rs index 3bb02d7f8db..973ca5d3f3b 100644 --- a/vortex-cuda/src/kernel/filter/mod.rs +++ b/vortex-cuda/src/kernel/filter/mod.rs @@ -52,7 +52,7 @@ impl CudaExecute for FilterExecutor { ) -> VortexResult { let filter_array = array .try_downcast::() - .map_err(|_| vortex_err!("Expected FilterArray"))?; + .map_err(|_| vortex_err!(InvalidArgument: "Expected FilterArray"))?; let child = filter_array.child().clone(); let mask = filter_array.data().filter_mask().clone(); @@ -83,7 +83,9 @@ impl CudaExecute for FilterExecutor { Canonical::VarBinView(varbinview) => { filter_varbinview(varbinview, m, ctx).await } - c => vortex_bail!("CUDA filter kernel is not implemented for {}", c.dtype()), + c => { + vortex_bail!(NotImplemented: "CUDA filter kernel is not implemented for {}", c.dtype()) + } } } } @@ -107,7 +109,7 @@ async fn filter_sized(temp_bytes.max(1))?; @@ -122,7 +124,7 @@ async fn filter_sized() - .ok_or_else(|| vortex_err!("Expected CudaDeviceBuffer for input, was {d_input:?}",))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "Expected CudaDeviceBuffer for input, was {d_input:?}",))?; let d_input_view = d_input_cuda.as_view::(); let (d_input_ptr, record_d_input) = d_input_view.device_ptr(stream); @@ -131,7 +133,9 @@ async fn filter_sized() - .ok_or_else(|| vortex_err!("Expected CudaDeviceBuffer for packed flags"))?; + .ok_or_else( + || vortex_err!(InvalidArgument: "Expected CudaDeviceBuffer for packed flags"), + )?; let d_packed_view = d_packed_cuda.as_view::(); let (d_packed_ptr, record_d_packed) = d_packed_view.device_ptr(stream); @@ -152,7 +156,7 @@ async fn filter_sized LaunchStrategyExt for S { let before = stream .record_event(Some(flags)) - .map_err(|e| vortex_err!("record_event: {e}"))?; + .map_err(|e| vortex_err!(Io: "record_event: {e}"))?; func()?; let after = stream .record_event(Some(flags)) - .map_err(|e| vortex_err!("record_event: {e}"))?; + .map_err(|e| vortex_err!(Io: "record_event: {e}"))?; self.on_complete( &CudaKernelEvents { @@ -183,10 +183,10 @@ pub(crate) fn launch_cuda_kernel_with_config( unsafe { launch_builder .launch(config) - .map_err(|e| vortex_err!("Failed to launch kernel: {}", e)) + .map_err(|e| vortex_err!(Io: "Failed to launch kernel: {}", e)) .and_then(|events| { events - .ok_or_else(|| vortex_err!("CUDA events not recorded")) + .ok_or_else(|| vortex_err!(AssertionFailed: "CUDA events not recorded")) .map(|(before_launch, after_launch)| CudaKernelEvents { before_launch, after_launch, @@ -246,7 +246,7 @@ impl KernelLoader { // Load the CUDA function from the compiled module. module .load_function(&kernel_name) - .map_err(|e| vortex_err!("Failed to load kernel function '{}': {}", kernel_name, e)) + .map_err(|e| vortex_err!(Io: "Failed to load kernel function '{}': {}", kernel_name, e)) } /// Loads a CUDA module from a fatbin embedded in the binary. @@ -254,12 +254,12 @@ impl KernelLoader { module_name: &str, cuda_context: &Arc, ) -> VortexResult> { - let fatbin = embedded_kernels::embedded_kernel(module_name).ok_or_else(|| { - vortex_err!("CUDA module {module_name} was not embedded at build time") - })?; + let fatbin = embedded_kernels::embedded_kernel(module_name).ok_or_else( + || vortex_err!(NotFound: "CUDA module {module_name} was not embedded at build time"), + )?; cuda_context .load_module(Ptx::from_binary(fatbin.to_vec())) - .map_err(|e| vortex_err!("Failed to load embedded CUDA module {module_name}: {e}")) + .map_err(|e| vortex_err!(Io: "Failed to load embedded CUDA module {module_name}: {e}")) } } diff --git a/vortex-cuda/src/kernel/patches/mod.rs b/vortex-cuda/src/kernel/patches/mod.rs index 101d3c8ff7f..d5f4c8c6aa9 100644 --- a/vortex-cuda/src/kernel/patches/mod.rs +++ b/vortex-cuda/src/kernel/patches/mod.rs @@ -51,7 +51,7 @@ pub(crate) fn ptype_to_chunk_offset_type(ptype: PType) -> VortexResult Ok(ChunkOffsetType_CO_U16), PType::U32 => Ok(ChunkOffsetType_CO_U32), PType::U64 => Ok(ChunkOffsetType_CO_U64), - _ => vortex_bail!("Invalid PType for chunk_offsets: {:?}", ptype), + _ => vortex_bail!(InvalidArgument: "Invalid PType for chunk_offsets: {:?}", ptype), } } diff --git a/vortex-cuda/src/kernel/patches/types.rs b/vortex-cuda/src/kernel/patches/types.rs index 77c9e15814e..80c5611e4bd 100644 --- a/vortex-cuda/src/kernel/patches/types.rs +++ b/vortex-cuda/src/kernel/patches/types.rs @@ -58,7 +58,7 @@ pub(crate) async fn load_device_patches( let offset_within_chunk = patches.offset_within_chunk().unwrap_or_default(); // Get or compute chunk_offsets let Some(co) = patches.chunk_offsets() else { - vortex_bail!("cannot load CUDA patches without chunk_offsets") + vortex_bail!(NotImplemented: "cannot load CUDA patches without chunk_offsets") }; let (chunk_offsets, chunk_offset_ptype, n_chunks) = { diff --git a/vortex-cuda/src/kernel/slice/mod.rs b/vortex-cuda/src/kernel/slice/mod.rs index 5bf5a485e08..542fa46f500 100644 --- a/vortex-cuda/src/kernel/slice/mod.rs +++ b/vortex-cuda/src/kernel/slice/mod.rs @@ -29,7 +29,7 @@ impl CudaExecute for SliceExecutor { ) -> VortexResult { let slice_array = array.try_downcast::().map_err(|array| { vortex_err!( - "SliceExecutor requires input of SliceArray, was {}", + InvalidArgument: "SliceExecutor requires input of SliceArray, was {}", array.encoding_id() ) })?; @@ -62,7 +62,7 @@ impl CudaExecute for SliceExecutor { .into_array() .slice(range)? .execute::(ctx.execution_ctx()), - c => vortex_bail!("Slice kernel not implemented for {}", c.dtype()), + c => vortex_bail!(NotImplemented: "Slice kernel not implemented for {}", c.dtype()), } } } diff --git a/vortex-cuda/src/layout.rs b/vortex-cuda/src/layout.rs index a8128963eee..b9864da6d5a 100644 --- a/vortex-cuda/src/layout.rs +++ b/vortex-cuda/src/layout.rs @@ -167,10 +167,10 @@ impl VTable for CudaFlat { metadata: &CudaFlatLayoutMetadata, ) -> VortexResult { if args.segment_ids.len() != 1 { - vortex_bail!("CudaFlatLayout must have exactly one segment ID"); + vortex_bail!(InvalidArgument: "CudaFlatLayout must have exactly one segment ID"); } if args.children.nchildren() != 0 { - vortex_bail!("CudaFlatLayout must not have children"); + vortex_bail!(InvalidArgument: "CudaFlatLayout must not have children"); } let host_buffers = metadata .host_buffers @@ -186,11 +186,11 @@ impl VTable for CudaFlat { } fn child_dtype(_layout: &Layout, idx: usize) -> VortexResult { - vortex_bail!("CudaFlatLayout has no child {idx}"); + vortex_bail!(OutOfBounds: "CudaFlatLayout has no child {idx}"); } fn child_type(_layout: &Layout, _idx: usize) -> LayoutChildType { - vortex_panic!("CudaFlatLayout has no children"); + vortex_panic!(OutOfBounds: "CudaFlatLayout has no children"); } fn new_reader( @@ -435,7 +435,7 @@ impl LayoutStrategy for CudaFlatLayoutStrategy { ) -> VortexResult { let options = self.clone(); let Some(chunk) = stream.next().await else { - vortex_bail!("CudaFlatLayoutStrategy needs a single chunk"); + vortex_bail!(InvalidArgument: "CudaFlatLayoutStrategy needs a single chunk"); }; let (sequence_id, chunk) = chunk?; let row_count = chunk.len() as u64; @@ -499,7 +499,7 @@ impl LayoutStrategy for CudaFlatLayoutStrategy { let segment_id = segment_sink.write(sequence_id, buffers).await?; let None = stream.next().await else { - vortex_bail!("CudaFlatLayoutStrategy received stream with more than a single chunk"); + vortex_bail!(InvalidArgument: "CudaFlatLayoutStrategy received stream with more than a single chunk"); }; let host_buffer_map: HashMap = host_buffers diff --git a/vortex-cuda/src/pinned.rs b/vortex-cuda/src/pinned.rs index 3ef8362d136..1ec06799924 100644 --- a/vortex-cuda/src/pinned.rs +++ b/vortex-cuda/src/pinned.rs @@ -54,24 +54,24 @@ impl PinnedByteBuffer { ) -> VortexResult { vortex_ensure!( capacity < isize::MAX as usize, - "pinned host buffer capacity is too large: {capacity}" + Overflow: "pinned host buffer capacity is too large: {capacity}" ); vortex_ensure!( logical_len <= capacity, - "pinned host buffer length {logical_len} exceeds capacity {capacity}" + Overflow: "pinned host buffer length {logical_len} exceeds capacity {capacity}" ); let event = ctx .new_event(Some(CUevent_flags::CU_EVENT_DISABLE_TIMING)) - .map_err(|e| vortex_err!("failed to create pinned host buffer event: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to create pinned host buffer event: {e}"))?; // Bind explicitly rather than relying on event creation to bind this worker thread. ctx.bind_to_thread() - .map_err(|e| vortex_err!("failed to bind pinned host buffer context: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to bind pinned host buffer context: {e}"))?; // Keep file-I/O staging cacheable: cudarc's allocator uses write-combined memory, // which makes CPU reads expensive. let ptr = unsafe { result::malloc_host(capacity, 0) } - .map_err(|e| vortex_err!("failed to allocate pinned host buffer: {e}"))? + .map_err(|e| vortex_err!(Io: "failed to allocate pinned host buffer: {e}"))? .cast::(); - vortex_ensure!(!ptr.is_null(), "CUDA returned a null pinned host buffer"); + vortex_ensure!(!ptr.is_null(), Io: "CUDA returned a null pinned host buffer"); Ok(Self { ptr, capacity, @@ -84,7 +84,7 @@ impl PinnedByteBuffer { pub(crate) fn as_mut_slice(&mut self) -> VortexResult<&mut [u8]> { self.event .synchronize() - .map_err(|e| vortex_err!("failed to access pinned host buffer: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to access pinned host buffer: {e}"))?; Ok(unsafe { std::slice::from_raw_parts_mut(self.ptr, self.logical_len) }) } @@ -255,7 +255,7 @@ impl PinnedByteBufferPool { } self.ctx .bind_to_thread() - .map_err(|e| vortex_err!("Failed to bind CUDA context: {e}"))?; + .map_err(|e| vortex_err!(Io: "Failed to bind CUDA context: {e}"))?; let mut idx = 0usize; while idx < inflight.len() { if !inflight[idx].buffer.event.is_complete() { @@ -365,27 +365,27 @@ impl PooledPinnedBuffer { ) -> VortexResult<()> { vortex_ensure!( &self.pool.ctx == stream.context(), - "pinned buffer and transfer stream must use the same CUDA context" + InvalidArgument: "pinned buffer and transfer stream must use the same CUDA context" ); let pinned = self.inner.as_mut().vortex_expect("buffer already consumed"); vortex_ensure!( range.start <= range.end && range.end <= pinned.logical_len, - "invalid pinned host buffer range {:?} for length {}", + InvalidArgument: "invalid pinned host buffer range {:?} for length {}", range, pinned.logical_len ); vortex_ensure_eq!( range.len(), destination.len(), - "pinned host buffer range length does not match destination length" + InvalidArgument: "pinned host buffer range length does not match destination length" ); // Chain the old transfer before this stream replaces the completion fence, even for // buffers returned directly to a bucket. Check the wait before creating a source guard: // on failure, preserve the old fence rather than recording over it on this stream. - stream - .wait(&pinned.event) - .map_err(|error| vortex_err!("Failed to wait for pinned source transfer: {error}"))?; + stream.wait(&pinned.event).map_err( + |error| vortex_err!(Io: "Failed to wait for pinned source transfer: {error}"), + )?; let source = PinnedByteBufferView { buffer: pinned, range, @@ -411,10 +411,10 @@ impl PooledPinnedBuffer { let _leaked = ManuallyDrop::new(self.inner.take().vortex_expect("buffer already consumed")); return Err(vortex_err!( - "H2D transfer fence failed: {error}; stream synchronization failed: {sync_error}" + Io: "H2D transfer fence failed: {error}; stream synchronization failed: {sync_error}" )); } - return Err(vortex_err!("H2D transfer fence failed: {error}")); + return Err(vortex_err!(Io: "H2D transfer fence failed: {error}")); } let inner = self.inner.take().vortex_expect("buffer already consumed"); @@ -449,11 +449,12 @@ mod tests { use super::*; fn setup() -> VortexResult<(Arc, VortexCudaStream)> { - let ctx = CudaContext::new(0).map_err(|e| vortex_err!("Failed to initialize CUDA: {e}"))?; + let ctx = + CudaContext::new(0).map_err(|e| vortex_err!(Io: "Failed to initialize CUDA: {e}"))?; let pool = Arc::new(PinnedByteBufferPool::new(Arc::clone(&ctx))); let stream = VortexCudaStream( ctx.new_stream() - .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, ); Ok((pool, stream)) } @@ -512,7 +513,7 @@ mod tests { let mut expected = vec![0xA5u8; 12]; let mut destination = stream .clone_htod(&expected) - .map_err(|e| vortex_err!("Failed to initialize destination: {e}"))?; + .map_err(|e| vortex_err!(Io: "Failed to initialize destination: {e}"))?; let result = pinned.copy_to_device( &stream, start..end, @@ -565,7 +566,7 @@ mod tests { } stream .synchronize() - .map_err(|e| vortex_err!("Failed to sync stream: {e}"))?; + .map_err(|e| vortex_err!(Io: "Failed to sync stream: {e}"))?; let mut reused = pool.get(1024)?; assert_eq!(reused.as_mut_slice().as_ptr(), allocation); @@ -583,7 +584,7 @@ mod tests { stream .context() .new_stream() - .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, ); let second = reused.transfer_to_device(&other_stream)?; let host = second.copy_to_host_sync(Alignment::of::())?; @@ -616,11 +617,11 @@ mod tests { )> { // Other tests synchronize the primary context. Keep the gated DMA independent of them. let ctx = CudaContext::new_non_primary(0, 0) - .map_err(|e| vortex_err!("Failed to initialize CUDA: {e}"))?; + .map_err(|e| vortex_err!(Io: "Failed to initialize CUDA: {e}"))?; let pool = Arc::new(PinnedByteBufferPool::new(Arc::clone(&ctx))); let stream = VortexCudaStream( ctx.new_stream() - .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, ); if !automatic_tracking { // SAFETY: Each destination stays on its allocation stream. The pool fences sources. @@ -629,7 +630,7 @@ mod tests { let other = VortexCudaStream( pool.ctx .new_stream() - .map_err(|error| vortex_err!("{error}"))?, + .map_err(|error| vortex_err!(AssertionFailed: "{error}"))?, ); Ok((pool, stream, other)) } @@ -661,7 +662,7 @@ mod tests { stream .context() .bind_to_thread() - .map_err(|e| vortex_err!("{e}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; unsafe extern "C" fn wait(data: *mut std::ffi::c_void) { // SAFETY: Registration transfers sole ownership of the boxed receiver here. let receiver = unsafe { Box::from_raw(data.cast::>()) }; @@ -675,7 +676,7 @@ mod tests { result::stream::launch_host_function(stream.cu_stream(), wait, data.cast()).map_err( |error| { drop(Box::from_raw(data)); - vortex_err!("Failed to block test stream: {error}") + vortex_err!(Io: "Failed to block test stream: {error}") }, )?; } @@ -715,7 +716,9 @@ mod tests { pinned.as_mut_slice().fill(0x5A); let mut first = stream.device_alloc::(len)?; let mut second = other.device_alloc::(len)?; - pool.ctx.synchronize().map_err(|e| vortex_err!("{e}"))?; + pool.ctx + .synchronize() + .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; // Declare the gate last so unwinding releases it before CUDA allocations are dropped. let gate = block_stream(&stream)?; submit_to_bucket(pinned, &stream, &mut first)?; @@ -723,7 +726,9 @@ mod tests { pinned.copy_to_device(&other, 0..len, &mut second.slice_mut(..))?; assert_source_retained(&pool)?; drop(gate); - other.synchronize().map_err(|e| vortex_err!("{e}"))?; + other + .synchronize() + .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; pool.reclaim_completed()?; assert!(pool.inflight.lock().is_empty()); pool.get(len)?.as_mut_slice().fill(0xA5); @@ -743,7 +748,7 @@ mod tests { let mut first = stream.device_alloc::(len)?; let mut second = other .clone_htod(&vec![0xCCu8; len]) - .map_err(|e| vortex_err!("{e}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; submit_to_bucket(pinned, &stream, &mut first)?; let pinned = pool.get(len)?; // Consumed by wait -> bind_to_thread -> check_err; the error text checks that path. @@ -806,11 +811,11 @@ mod tests { fn rejects_transfer_between_contexts() -> VortexResult<()> { let (pool, _) = setup()?; let context = CudaContext::new_non_primary(0, 0) - .map_err(|e| vortex_err!("Failed to create context: {e}"))?; + .map_err(|e| vortex_err!(Io: "Failed to create context: {e}"))?; let stream = VortexCudaStream( context .new_stream() - .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, ); let mut pinned = pool.get(1024)?; pinned.as_mut_slice().fill(0xFF); diff --git a/vortex-cuda/src/pooled_read_at.rs b/vortex-cuda/src/pooled_read_at.rs index 96b8697090c..777f5b27914 100644 --- a/vortex-cuda/src/pooled_read_at.rs +++ b/vortex-cuda/src/pooled_read_at.rs @@ -131,7 +131,7 @@ impl VortexReadAt for PooledObjectStoreReadAt { async move { let end = offset.checked_add(length as u64).ok_or_else(|| { vortex_err!( - "Object store read range overflow: offset={}, length={}", + Overflow: "Object store read range overflow: offset={}, length={}", offset, length ) @@ -170,7 +170,7 @@ impl VortexReadAt for PooledObjectStoreReadAt { let end = filled + bytes.len(); vortex_ensure!( end <= length, - "Object store stream returned more bytes than expected (expected {} bytes, got at least {} bytes, range: {:?})", + Io: "Object store stream returned more bytes than expected (expected {} bytes, got at least {} bytes, range: {:?})", length, end, range @@ -182,7 +182,7 @@ impl VortexReadAt for PooledObjectStoreReadAt { vortex_ensure_eq!( filled, length, - "Object store stream returned too few bytes (range: {:?})", + Io: "Object store stream returned too few bytes (range: {:?})", range ); } @@ -251,8 +251,9 @@ impl VortexReadAt for PooledByteBufferReadAt { let pool = Arc::clone(&self.pool); async move { - let offset = usize::try_from(offset) - .map_err(|_| vortex_err!("Byte buffer read offset overflow: offset={}", offset))?; + let offset = usize::try_from(offset).map_err( + |_| vortex_err!(Overflow: "Byte buffer read offset overflow: offset={}", offset), + )?; let src = &buffer.as_ref()[offset..offset + length]; let mut target = pool.get(length)?; diff --git a/vortex-cuda/src/pooled_read_at/file.rs b/vortex-cuda/src/pooled_read_at/file.rs index afa8d736f2e..7cab5a5042c 100644 --- a/vortex-cuda/src/pooled_read_at/file.rs +++ b/vortex-cuda/src/pooled_read_at/file.rs @@ -140,7 +140,7 @@ unsafe extern "C" { fn page_size() -> VortexResult { // SAFETY: getpagesize has no preconditions. let page = usize::try_from(unsafe { getpagesize() })?; - vortex_ensure!(page.is_power_of_two(), "invalid page size {page}"); + vortex_ensure!(page.is_power_of_two(), AssertionFailed: "invalid page size {page}"); Ok(page) } @@ -286,7 +286,7 @@ impl MappedFile { .attribute( CUdevice_attribute::CU_DEVICE_ATTRIBUTE_PAGEABLE_MEMORY_ACCESS_USES_HOST_PAGE_TABLES, ) - .map_err(|error| vortex_err!("Failed to query pageable memory access: {error}"))?; + .map_err(|error| vortex_err!(Io: "Failed to query pageable memory access: {error}"))?; if uses_host_page_tables != 1 { return Ok(None); } @@ -350,7 +350,7 @@ impl MappedFile { self.stream .context() .bind_to_thread() - .map_err(|error| vortex_err!("Failed to bind CUDA context: {error}"))?; + .map_err(|error| vortex_err!(Io: "Failed to bind CUDA context: {error}"))?; // The guard records the queued copies as the output's write when this scope ends, // including on error, so frees and readers on other streams wait for them. let (base, write) = output.device_ptr_mut(&self.stream); @@ -377,7 +377,7 @@ impl MappedFile { // SAFETY: The source range is mapped and in bounds, the target covers `pad + length` // bytes, and both share the same offset within 16 bytes, as the kernel requires. unsafe { launch.launch(config) } - .map_err(|error| vortex_err!("Failed to launch mapped copy: {error}"))?; + .map_err(|error| vortex_err!(Io: "Failed to launch mapped copy: {error}"))?; } drop(write); Ok(output) @@ -503,7 +503,7 @@ impl PooledFileReadAt { let permit = Arc::clone(&self.read_slots) .acquire_owned() .await - .map_err(|error| vortex_err!("file read semaphore closed: {error}"))?; + .map_err(|error| vortex_err!(Io: "file read semaphore closed: {error}"))?; self.handle .spawn_blocking(move || { // A started blocking read cannot be cancelled. Keep its permit and buffer owners @@ -543,7 +543,7 @@ impl VortexReadAt for PooledFileReadAt { async move { vortex_ensure!( offset.checked_add(u64::try_from(length)?).is_some(), - "file read range overflow: offset={offset}, length={length}" + Overflow: "file read range overflow: offset={offset}, length={length}" ); if let Some(buffer) = reader.read_mapped(offset, length).await? { return Ok(buffer); diff --git a/vortex-cuda/src/pooled_read_at/file/direct.rs b/vortex-cuda/src/pooled_read_at/file/direct.rs index afe9dc73f63..cecf2cc818c 100644 --- a/vortex-cuda/src/pooled_read_at/file/direct.rs +++ b/vortex-cuda/src/pooled_read_at/file/direct.rs @@ -86,7 +86,7 @@ impl FileReadBackend for DirectFileReadBackend { let address = buffer.as_mut_slice().as_ptr() as usize; vortex_ensure!( address.is_multiple_of(self.constraints.memory_alignment), - "pinned buffer address {address:#x} is not aligned to {} bytes", + InvalidArgument: "pinned buffer address {address:#x} is not aligned to {} bytes", self.constraints.memory_alignment ); @@ -106,7 +106,7 @@ impl FileReadBackend for DirectFileReadBackend { } fn direct_io_range(offset: u64, length: usize, alignment: usize) -> VortexResult { - vortex_ensure!(alignment > 0, "direct I/O alignment must be non-zero"); + vortex_ensure!(alignment > 0, InvalidArgument: "direct I/O alignment must be non-zero"); if length == 0 { return Ok(DirectIoRange { read_offset: offset, @@ -117,18 +117,18 @@ fn direct_io_range(offset: u64, length: usize, alignment: usize) -> VortexResult let alignment_u64 = u64::try_from(alignment)?; let length_u64 = u64::try_from(length)?; - let requested_end = offset.checked_add(length_u64).ok_or_else(|| { - vortex_err!("direct I/O range overflow: offset={offset}, length={length}") - })?; + let requested_end = offset.checked_add(length_u64).ok_or_else( + || vortex_err!(Overflow: "direct I/O range overflow: offset={offset}, length={length}"), + )?; let read_offset = offset - offset % alignment_u64; let read_end = requested_end .checked_next_multiple_of(alignment_u64) - .ok_or_else(|| vortex_err!("direct I/O aligned end overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "direct I/O aligned end overflow"))?; let read_length = usize::try_from(read_end - read_offset)?; let slice_start = usize::try_from(offset - read_offset)?; - let slice_end = slice_start.checked_add(length).ok_or_else(|| { - vortex_err!("direct I/O range overflow: offset={offset}, length={length}") - })?; + let slice_end = slice_start.checked_add(length).ok_or_else( + || vortex_err!(Overflow: "direct I/O range overflow: offset={offset}, length={length}"), + )?; Ok(DirectIoRange { read_offset, @@ -204,11 +204,11 @@ fn direct_io_constraints(file: &File) -> VortexResult { } vortex_ensure!( memory_alignment.is_power_of_two(), - "direct I/O memory alignment must be a power of two, got {memory_alignment}" + InvalidArgument: "direct I/O memory alignment must be a power of two, got {memory_alignment}" ); vortex_ensure!( offset_alignment.is_power_of_two(), - "direct I/O offset alignment must be a power of two, got {offset_alignment}" + InvalidArgument: "direct I/O offset alignment must be a power of two, got {offset_alignment}" ); Ok(DirectIoConstraints { diff --git a/vortex-cuda/src/pooled_read_at/file/tests.rs b/vortex-cuda/src/pooled_read_at/file/tests.rs index c2a5121c216..a304a347993 100644 --- a/vortex-cuda/src/pooled_read_at/file/tests.rs +++ b/vortex-cuda/src/pooled_read_at/file/tests.rs @@ -75,7 +75,7 @@ impl FileReadBackend for FakeFileReadBackend { self.requests.lock().push((offset, length)); let end = offset .checked_add(u64::try_from(length)?) - .ok_or_else(|| vortex_err!("overflow reached fake backend"))?; + .ok_or_else(|| vortex_err!(Overflow: "overflow reached fake backend"))?; let alignment = if self.padded { 4096 } else { 1 }; let prefix = usize::try_from(offset % alignment as u64)?; let source_len = (prefix + length).next_multiple_of(alignment); @@ -96,9 +96,9 @@ impl FileReadBackend for FakeFileReadBackend { release, finished: completion, }) - .map_err(|_| vortex_err!("fake read controller dropped"))?; + .map_err(|_| vortex_err!(Io: "fake read controller dropped"))?; wait.recv_timeout(WAIT) - .map_err(|error| vortex_err!("fake read was not released: {error}"))?; + .map_err(|error| vortex_err!(Io: "fake read was not released: {error}"))?; Some(finished) } else { None diff --git a/vortex-cuda/src/session.rs b/vortex-cuda/src/session.rs index 2d4ff54e65f..10085c162d8 100644 --- a/vortex-cuda/src/session.rs +++ b/vortex-cuda/src/session.rs @@ -135,14 +135,14 @@ impl CudaSession { // loaded, so catch any unwind here to uphold this constructor's no-panic contract. match catch_unwind(AssertUnwindSafe(|| -> VortexResult { let context = CudaContext::new(0) - .map_err(|err| vortex_err!("failed to initialize CUDA device 0: {err}"))?; + .map_err(|err| vortex_err!(Io: "failed to initialize CUDA device 0: {err}"))?; let this = Self::new(context); initialize_cuda(&this); Ok(this) })) { Ok(result) => result, Err(_) => Err(vortex_err!( - "failed to initialize CUDA: the driver library is unavailable" + Io: "failed to initialize CUDA: the driver library is unavailable" )), } } diff --git a/vortex-cuda/src/stream.rs b/vortex-cuda/src/stream.rs index a6515b1f8db..1f1396f2185 100644 --- a/vortex-cuda/src/stream.rs +++ b/vortex-cuda/src/stream.rs @@ -57,7 +57,7 @@ impl VortexCudaStream { // SAFETY: No safety guarantees for allocations on the GPU. unsafe { self.alloc::(len) - .map_err(|e| vortex_err!("Failed to allocate device memory: {}", e)) + .map_err(|e| vortex_err!(Io: "Failed to allocate device memory: {}", e)) } } @@ -101,7 +101,7 @@ impl VortexCudaStream { let mut values = cuda_slice.slice_mut(..host_slice.len()); self.memcpy_htod(host_slice, &mut values) - .map_err(|e| vortex_err!("Failed to schedule H2D copy: {}", e))?; + .map_err(|e| vortex_err!(Io: "Failed to schedule H2D copy: {}", e))?; zero_padding(self, &mut cuda_slice, host_slice.len())?; @@ -143,7 +143,7 @@ impl VortexCudaStream { let mut values = cuda_slice.slice_mut(..data.len()); self.memcpy_htod(data, &mut values) - .map_err(|e| vortex_err!("Failed to schedule H2D copy: {}", e))?; + .map_err(|e| vortex_err!(Io: "Failed to schedule H2D copy: {}", e))?; zero_padding(self, &mut cuda_slice, data.len())?; @@ -161,7 +161,7 @@ fn padded_device_allocation_len(byte_count: usize) -> VortexResult { let element_size = size_of::(); vortex_ensure!( element_size != 0, - "cannot copy zero-sized values to CUDA device" + InvalidArgument: "cannot copy zero-sized values to CUDA device" ); let min_allocation_bytes = byte_count.next_multiple_of(CUDF_VALIDITY_BUFFER_PADDING); Ok(min_allocation_bytes.div_ceil(element_size)) @@ -184,7 +184,7 @@ pub(crate) fn zero_padding( let mut padding = cuda_slice.slice_mut(initialized_count..); stream .memset_zeros(&mut padding) - .map_err(|e| vortex_err!("Failed to zero device buffer padding: {}", e)) + .map_err(|e| vortex_err!(Io: "Failed to zero device buffer padding: {}", e)) } /// Registers a callback and asynchronously waits for its completion. @@ -208,7 +208,7 @@ pub(crate) async fn await_stream_callback(stream: &CudaStream) -> VortexResult<( rx.recv() .await - .map_err(|e| vortex_err!("CUDA stream callback channel closed unexpectedly: {}", e)) + .map_err(|e| vortex_err!(Io: "CUDA stream callback channel closed unexpectedly: {}", e)) } /// Registers a host function callback on the stream. @@ -229,7 +229,7 @@ fn register_stream_callback(stream: &CudaStream) -> VortexResult VortexResult VortexResult<()> { - let context = - CudaContext::new(0).map_err(|e| vortex_err!("Failed to create CUDA context: {e}"))?; + let context = CudaContext::new(0) + .map_err(|e| vortex_err!(Io: "Failed to create CUDA context: {e}"))?; let pool = VortexCudaStreamPool::new(context, 3); assert_eq!(pool.max_capacity(), 3); @@ -118,8 +118,8 @@ mod tests { #[crate::test] fn round_robin_reuse() -> VortexResult<()> { - let context = - CudaContext::new(0).map_err(|e| vortex_err!("Failed to create CUDA context: {e}"))?; + let context = CudaContext::new(0) + .map_err(|e| vortex_err!(Io: "Failed to create CUDA context: {e}"))?; let pool = VortexCudaStreamPool::new(context, 3); let streams = (0..pool.max_capacity()) .map(|_| pool.stream()) @@ -143,8 +143,8 @@ mod tests { #[crate::test] fn concurrent_initialization_respects_capacity() -> VortexResult<()> { - let context = - CudaContext::new(0).map_err(|e| vortex_err!("Failed to create CUDA context: {e}"))?; + let context = CudaContext::new(0) + .map_err(|e| vortex_err!(Io: "Failed to create CUDA context: {e}"))?; for capacity in [1, 4] { let pool = VortexCudaStreamPool::new(Arc::clone(&context), capacity); let barrier = Barrier::new(32); diff --git a/vortex-datafusion/examples/vortex_table.rs b/vortex-datafusion/examples/vortex_table.rs index 90a7ba5e1e4..baedac2f61b 100644 --- a/vortex-datafusion/examples/vortex_table.rs +++ b/vortex-datafusion/examples/vortex_table.rs @@ -67,7 +67,7 @@ async fn main() -> anyhow::Result<()> { let table_url = ListingTableUrl::parse( filepath .to_str() - .ok_or_else(|| vortex_err!("Path is not valid UTF-8"))?, + .ok_or_else(|| vortex_err!(InvalidArgument: "Path is not valid UTF-8"))?, )?; let config = ListingTableConfig::new(table_url) .with_listing_options(ListingOptions::new(format)) diff --git a/vortex-datafusion/src/convert/scalars.rs b/vortex-datafusion/src/convert/scalars.rs index 1b5a2d8e95f..49244291223 100644 --- a/vortex-datafusion/src/convert/scalars.rs +++ b/vortex-datafusion/src/convert/scalars.rs @@ -66,7 +66,7 @@ impl TryToDataFusion for Scalar { Some(v32) => ScalarValue::Decimal32(Some(v32), precision, scale), None => { vortex_bail!( - "invalid ScalarValue {value} for decimal with precision {precision}", + InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -78,7 +78,7 @@ impl TryToDataFusion for Scalar { Some(v64) => ScalarValue::Decimal64(Some(v64), precision, scale), None => { vortex_bail!( - "invalid ScalarValue {value} for decimal with precision {precision}", + InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -90,7 +90,7 @@ impl TryToDataFusion for Scalar { Some(v128) => ScalarValue::Decimal128(Some(v128), precision, scale), None => { vortex_bail!( - "invalid ScalarValue {value} for decimal with precision {precision}", + InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -104,7 +104,7 @@ impl TryToDataFusion for Scalar { } None => { vortex_bail!( - "invalid ScalarValue {value} for decimal with precision {precision}", + InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -122,19 +122,21 @@ impl TryToDataFusion for Scalar { .map(|b| Vec::::from(b.into_bytes())), ), dtype @ DType::List(..) => vortex_bail!( - "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), dtype @ DType::FixedSizeList(..) => vortex_bail!( - "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), dtype @ DType::Map(..) => vortex_bail!( - "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), DType::Struct(..) => struct_to_df(self)?, dtype @ DType::Union(..) => vortex_bail!( - "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), - DType::Variant(_) => vortex_bail!("Variant scalars aren't supported with DF"), + DType::Variant(_) => { + vortex_bail!(NotImplemented: "Variant scalars aren't supported with DF") + } DType::Extension(ext) => { let storage_scalar = self.as_extension().to_storage_scalar(); @@ -316,7 +318,7 @@ pub fn scalar_from_df(value: &ScalarValue, session: &VortexSession) -> VortexRes ScalarValue::Dictionary(_, v) => scalar_from_df(v.as_ref(), session)?, ScalarValue::Struct(array) => struct_from_df(array, session), ScalarValue::RunEndEncoded(_, _, v) => scalar_from_df(v.as_ref(), session)?, - _ => vortex_bail!("Can't convert {value:?} value to a Vortex scalar"), + _ => vortex_bail!(MismatchedTypes: "Can't convert {value:?} value to a Vortex scalar"), }) } @@ -336,12 +338,11 @@ fn struct_to_df(scalar: &Scalar) -> VortexResult { } else { scalar .field_by_idx(idx) - .ok_or_else(|| vortex_err!("missing struct field {name}"))? + .ok_or_else(|| vortex_err!(NotFound: "missing struct field {name}"))? }; - let array = child - .try_to_df()? - .to_array() - .map_err(|e| vortex_err!("failed to build struct field array: {e}"))?; + let array = child.try_to_df()?.to_array().map_err( + |e| vortex_err!(InvalidArgument: "failed to build struct field array: {e}"), + )?; Ok(( Field::new(name.as_ref(), array.data_type().clone(), nullable), array, @@ -356,7 +357,7 @@ fn struct_to_df(scalar: &Scalar) -> VortexResult { StructArray::new_null(fields, 1) } else { StructArray::try_new(fields, arrays, None) - .map_err(|e| vortex_err!("failed to build struct scalar array: {e}"))? + .map_err(|e| vortex_err!(InvalidArgument: "failed to build struct scalar array: {e}"))? }; Ok(ScalarValue::Struct(Arc::new(struct_array))) } @@ -385,7 +386,7 @@ fn struct_from_df(array: &StructArray, session: &VortexSession) -> Scalar { .from_arrow_array(ArrowArrayRef::clone(column), field) .and_then(|column| column.execute_scalar(0, &mut ctx)) .unwrap_or_else(|e| { - vortex_panic!("cannot convert struct field to a Vortex scalar: {e}") + vortex_panic!(e, "cannot convert struct field to a Vortex scalar") }) }) .collect::>(); diff --git a/vortex-datafusion/src/convert/stats/tests.rs b/vortex-datafusion/src/convert/stats/tests.rs index e2e7e0fc67f..58acf2bfc30 100644 --- a/vortex-datafusion/src/convert/stats/tests.rs +++ b/vortex-datafusion/src/convert/stats/tests.rs @@ -18,7 +18,7 @@ fn bounds_stats(value: &DFScalarValue) -> VortexResult<(StatsSet, DType)> { let value = scalar .value() .cloned() - .ok_or_else(|| vortex_err!("expected non-null bounds"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "expected non-null bounds"))?; let mut stats = StatsSet::of(Stat::Min, VortexPrecision::exact(value.clone())); stats.set(Stat::Max, VortexPrecision::exact(value)); stats.set(Stat::NullCount, VortexPrecision::exact(0u64)); diff --git a/vortex-datafusion/src/persistent/format.rs b/vortex-datafusion/src/persistent/format.rs index 7e69693400b..d33983291a5 100644 --- a/vortex-datafusion/src/persistent/format.rs +++ b/vortex-datafusion/src/persistent/format.rs @@ -652,7 +652,7 @@ impl FileFormat for VortexFormat { return Ok(Statistics { num_rows: DFPrecision::Exact( usize::try_from(row_count) - .map_err(|_| vortex_err!("Row count overflow")) + .map_err(|_| vortex_err!(Overflow: "Row count overflow")) .vortex_expect("Row count overflow"), ), total_byte_size: DFPrecision::Absent, @@ -713,7 +713,7 @@ impl FileFormat for VortexFormat { Ok(Statistics { num_rows: DFPrecision::Exact( usize::try_from(row_count) - .map_err(|_| vortex_err!("Row count overflow")) + .map_err(|_| vortex_err!(Overflow: "Row count overflow")) .vortex_expect("Row count overflow"), ), total_byte_size, @@ -891,7 +891,7 @@ mod tests { let value = scalar .value() .cloned() - .ok_or_else(|| vortex_err!("expected non-null scalar"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected non-null scalar"))?; let target_dtype = expected.data_type(); let (value, expected) = if exact { (Precision::Exact(value), DFPrecision::Exact(expected)) @@ -927,7 +927,7 @@ mod tests { let value = scalar .value() .cloned() - .ok_or_else(|| vortex_err!("expected non-null scalar"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected non-null scalar"))?; assert_eq!( scalar_stat_to_df(stat, Precision::Exact(value), scalar.dtype(), &target_dtype), DFPrecision::Absent diff --git a/vortex-datafusion/src/v2/source.rs b/vortex-datafusion/src/v2/source.rs index ae7902b3e30..04807bb9d34 100644 --- a/vortex-datafusion/src/v2/source.rs +++ b/vortex-datafusion/src/v2/source.rs @@ -242,7 +242,7 @@ impl VortexDataSourceBuilder { } let DType::Struct(fields, ..) = projection.return_dtype(self.data_source.dtype())? else { - vortex_bail!("Projection does not evaluate to a struct"); + vortex_bail!(MismatchedTypes: "Projection does not evaluate to a struct"); }; // We now compute initial statistics. diff --git a/vortex-duckdb/src/convert/dtype.rs b/vortex-duckdb/src/convert/dtype.rs index e80542e9327..b911e168e03 100644 --- a/vortex-duckdb/src/convert/dtype.rs +++ b/vortex-duckdb/src/convert/dtype.rs @@ -88,7 +88,9 @@ impl FromLogicalType for DType { nullability: Nullability, ) -> VortexResult { Ok(match logical_type.as_type_id() { - DUCKDB_TYPE::DUCKDB_TYPE_INVALID => vortex_bail!("invalid duckdb type"), + DUCKDB_TYPE::DUCKDB_TYPE_INVALID => { + vortex_bail!(InvalidArgument: "invalid duckdb type") + } DUCKDB_TYPE::DUCKDB_TYPE_SQLNULL => DType::Null, DUCKDB_TYPE::DUCKDB_TYPE_BOOLEAN => DType::Bool(nullability), DUCKDB_TYPE::DUCKDB_TYPE_TINYINT => DType::Primitive(I8, nullability), @@ -99,8 +101,12 @@ impl FromLogicalType for DType { DUCKDB_TYPE::DUCKDB_TYPE_USMALLINT => DType::Primitive(U16, nullability), DUCKDB_TYPE::DUCKDB_TYPE_UINTEGER => DType::Primitive(U32, nullability), DUCKDB_TYPE::DUCKDB_TYPE_UBIGINT => DType::Primitive(U64, nullability), - DUCKDB_TYPE::DUCKDB_TYPE_HUGEINT => vortex_bail!("I128 is not in Vortex type system"), - DUCKDB_TYPE::DUCKDB_TYPE_UHUGEINT => vortex_bail!("U128 is not in Vortex type system"), + DUCKDB_TYPE::DUCKDB_TYPE_HUGEINT => { + vortex_bail!(NotImplemented: "I128 is not in Vortex type system") + } + DUCKDB_TYPE::DUCKDB_TYPE_UHUGEINT => { + vortex_bail!(NotImplemented: "U128 is not in Vortex type system") + } DUCKDB_TYPE::DUCKDB_TYPE_FLOAT => DType::Primitive(F32, nullability), DUCKDB_TYPE::DUCKDB_TYPE_DOUBLE => DType::Primitive(F64, nullability), DUCKDB_TYPE::DUCKDB_TYPE_VARCHAR => DType::Utf8(nullability), @@ -206,7 +212,7 @@ impl FromLogicalType for DType { | DUCKDB_TYPE::DUCKDB_TYPE_BIGNUM | DUCKDB_TYPE::DUCKDB_TYPE_STRING_LITERAL | DUCKDB_TYPE::DUCKDB_TYPE_INTEGER_LITERAL) => { - vortex_bail!("{other:?} -> DType conversion is not supported") + vortex_bail!(InvalidArgument: "{other:?} -> DType conversion is not supported") } }) } @@ -265,8 +271,10 @@ impl TryFrom<&DType> for LogicalType { return LogicalType::map_type(&key_logical_type, &value_logical_type); } // TODO(connor): Union - DType::Union(..) => vortex_bail!("Vortex Union isn't supported"), - DType::Variant(_) => vortex_bail!("Vortex Variant array aren't supported"), + DType::Union(..) => vortex_bail!(NotImplemented: "Vortex Union isn't supported"), + DType::Variant(_) => { + vortex_bail!(NotImplemented: "Vortex Variant array aren't supported") + } DType::Extension(ext_dtype) => { // Handle first-party extension types that have DuckDB equivalents. if let Some(temporal) = ext_dtype.metadata_opt::() { @@ -290,7 +298,7 @@ impl TryFrom<&DType> for LogicalType { return LogicalType::geometry_type(spatial_metadata.crs.as_deref()); } - vortex_bail!("Unsupported extension type \"{}\"", ext_dtype.id()); + vortex_bail!(InvalidArgument: "Unsupported extension type \"{}\"", ext_dtype.id()); } }; @@ -313,14 +321,14 @@ fn temporal_to_duckdb(temporal: TemporalMetadata) -> VortexResult { TimeUnit::Microseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIMESTAMP, TimeUnit::Milliseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIMESTAMP_MS, TimeUnit::Seconds => DUCKDB_TYPE::DUCKDB_TYPE_TIMESTAMP_S, - _ => vortex_bail!("Invalid TimeUnit {} for timestamp", unit), + _ => vortex_bail!(InvalidArgument: "Invalid TimeUnit {} for timestamp", unit), }, // TIMESTAMP_TZ's timezone is a display unit, time is stored in UTC // microseconds TemporalMetadata::Timestamp(unit, Some(_)) => { if unit != &TimeUnit::Microseconds { vortex_bail!( - "Invalid TimeUnit {} for timestamp_tz, must be Microseconds", + InvalidArgument: "Invalid TimeUnit {} for timestamp_tz, must be Microseconds", unit ); } @@ -328,12 +336,12 @@ fn temporal_to_duckdb(temporal: TemporalMetadata) -> VortexResult { } TemporalMetadata::Date(unit) => match unit { TimeUnit::Days => DUCKDB_TYPE::DUCKDB_TYPE_DATE, - _ => vortex_bail!("Invalid TimeUnit {} for date", unit), + _ => vortex_bail!(InvalidArgument: "Invalid TimeUnit {} for date", unit), }, TemporalMetadata::Time(unit) => match unit { TimeUnit::Microseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIME, TimeUnit::Nanoseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIME_NS, - _ => vortex_bail!("Invalid TimeUnit {} for time", unit), + _ => vortex_bail!(InvalidArgument: "Invalid TimeUnit {} for time", unit), }, }; @@ -363,10 +371,11 @@ impl TryFrom<&StructFields> for LogicalType { .iter() .map(|field_name| { if name_set.replace(field_name.as_ref()).is_some() { - vortex_bail!("Duplicate field '{field_name}'"); + vortex_bail!(InvalidArgument: "Duplicate field '{field_name}'"); } - CString::new(field_name.as_ref()) - .map_err(|e| vortex_err!("Invalid field name '{field_name}': {e}")) + CString::new(field_name.as_ref()).map_err( + |e| vortex_err!(InvalidArgument: "Invalid field name '{field_name}': {e}"), + ) }) .collect::>()?; @@ -389,7 +398,9 @@ impl TryFrom for LogicalType { U64 => LogicalType::new(DUCKDB_TYPE::DUCKDB_TYPE_UBIGINT), F32 => LogicalType::new(DUCKDB_TYPE::DUCKDB_TYPE_FLOAT), F64 => LogicalType::new(DUCKDB_TYPE::DUCKDB_TYPE_DOUBLE), - PType::F16 => return Err(vortex_err!("F16 type not supported in DuckDB")), + PType::F16 => { + return Err(vortex_err!(InvalidArgument: "F16 type not supported in DuckDB")); + } }) } } diff --git a/vortex-duckdb/src/convert/expr.rs b/vortex-duckdb/src/convert/expr.rs index 7d7cf0e6aa8..382c1bc2f00 100644 --- a/vortex-duckdb/src/convert/expr.rs +++ b/vortex-duckdb/src/convert/expr.rs @@ -85,7 +85,9 @@ use crate::projection::DuckdbField; fn from_bound_str(value: &ExpressionRef) -> VortexResult { match value.as_class().vortex_expect("unknown class") { BoundConstant(constant) => Ok(constant.value.as_string().as_str().to_owned()), - _ => vortex_bail!("Expected string expression, got {:?}", value.as_class_id()), + _ => { + vortex_bail!(MismatchedTypes: "Expected string expression, got {:?}", value.as_class_id()) + } } } @@ -600,7 +602,7 @@ fn try_from_expression_inner( Ok(Some(match class { BoundRef => { let Some(col) = ctx.col_sub else { - vortex_bail!("BoundRef requested but no column supplied"); + vortex_bail!(InvalidArgument: "BoundRef requested but no column supplied"); }; col.clone() } @@ -718,7 +720,9 @@ fn try_from_expression_inner( DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_CONJUNCTION_OR => { or_collect(children).vortex_expect("cannot be empty") } - _ => vortex_bail!("unexpected operator {:?} in bound conjunction", conj.op), + _ => { + vortex_bail!(AssertionFailed: "unexpected operator {:?} in bound conjunction", conj.op) + } } } ExpressionClass::BoundAggregate(_) => return Ok(None), @@ -760,14 +764,16 @@ impl TryFrom for Operator { fn try_from(value: DUCKDB_VX_EXPR_TYPE) -> VortexResult { Ok(match value { - DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_INVALID => vortex_bail!("invalid expression"), + DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_INVALID => { + vortex_bail!(InvalidArgument: "invalid expression") + } DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_EQUAL => Operator::Eq, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_NOTEQUAL => Operator::NotEq, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_LESSTHAN => Operator::Lt, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_GREATERTHAN => Operator::Gt, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_LESSTHANOREQUALTO => Operator::Lte, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_GREATERTHANOREQUALTO => Operator::Gte, - _ => vortex_bail!("cannot convert {:?}", value), + _ => vortex_bail!(MismatchedTypes: "cannot convert {:?}", value), }) } } diff --git a/vortex-duckdb/src/convert/scalar.rs b/vortex-duckdb/src/convert/scalar.rs index f4478091b31..00361e595c8 100644 --- a/vortex-duckdb/src/convert/scalar.rs +++ b/vortex-duckdb/src/convert/scalar.rs @@ -86,10 +86,14 @@ impl ToDuckDBScalar for Scalar { DType::Binary(_) => self.as_binary().try_to_duckdb_scalar(), DType::List(..) | DType::FixedSizeList(..) => self.as_list().try_to_duckdb_scalar(), DType::Map(..) => self.as_map().try_to_duckdb_scalar(), - DType::Variant(_) => vortex_bail!("Vortex Variant scalars aren't supported"), + DType::Variant(_) => { + vortex_bail!(NotImplemented: "Vortex Variant scalars aren't supported") + } DType::Struct(..) => self.as_struct().try_to_duckdb_scalar(), // TODO(connor): Union - DType::Union(..) => vortex_bail!("Vortex Union scalars aren't supported"), + DType::Union(..) => { + vortex_bail!(NotImplemented: "Vortex Union scalars aren't supported") + } DType::Extension(..) => self.as_extension().try_to_duckdb_scalar(), } } @@ -126,7 +130,7 @@ impl ToDuckDBScalar for DecimalScalar<'_> { let decimal_type = self .dtype() .as_decimal_opt() - .ok_or_else(|| vortex_err!("decimal scalar without decimal dtype"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "decimal scalar without decimal dtype"))?; let Some(decimal_value) = self.decimal_value() else { let lt = LogicalType::try_from(self.dtype())?; @@ -139,7 +143,9 @@ impl ToDuckDBScalar for DecimalScalar<'_> { DecimalValue::I32(v) => v as i128, DecimalValue::I64(v) => v as i128, DecimalValue::I128(v) => v, - DecimalValue::I256(_) => vortex_bail!("cannot handle a i256 decimal in duckdb"), + DecimalValue::I256(_) => { + vortex_bail!(NotImplemented: "cannot handle a i256 decimal in duckdb") + } }; Ok(Value::new_decimal( @@ -238,9 +244,9 @@ impl ToDuckDBScalar for ExtScalar<'_> { fn try_to_duckdb_scalar(&self) -> VortexResult { if let Some(wkb) = self.ext_dtype().metadata_opt::() { let storage = self.to_storage_scalar(); - let binary = storage - .as_binary_opt() - .ok_or_else(|| vortex_err!("WellKnownBinary storage must be a binary scalar"))?; + let binary = storage.as_binary_opt().ok_or_else( + || vortex_err!(InvalidArgument: "WellKnownBinary storage must be a binary scalar"), + )?; return Ok(match binary.value() { Some(bytes) => Value::new_geometry(bytes.as_slice(), wkb.crs.as_deref())?, None => Value::null(&*ext_logical_type(self)?), @@ -248,14 +254,14 @@ impl ToDuckDBScalar for ExtScalar<'_> { } let Some(temporal) = self.ext_dtype().metadata_opt::() else { - vortex_bail!("Cannot convert non-temporal extension scalar to duckdb value"); + vortex_bail!(MismatchedTypes: "Cannot convert non-temporal extension scalar to duckdb value"); }; let storage = PrimitiveScalar::try_new(self.ext_dtype().storage_dtype(), self.value())?; let value = || { storage .as_::() - .ok_or_else(|| vortex_err!("temporal types must be convertible to i64")) + .ok_or_else(|| vortex_err!(Overflow: "temporal types must be convertible to i64")) }; Ok(match temporal { @@ -274,7 +280,7 @@ impl ToDuckDBScalar for ExtScalar<'_> { TimeUnit::Milliseconds => Value::new_timestamp_ms(value()?), TimeUnit::Seconds => Value::new_timestamp_s(value()?), TimeUnit::Days => { - vortex_bail!("timestamp(d) is cannot be converted to duckdb scalar") + vortex_bail!(InvalidArgument: "timestamp(d) is cannot be converted to duckdb scalar") } } } @@ -283,7 +289,9 @@ impl ToDuckDBScalar for ExtScalar<'_> { Some(days) => Value::new_date(days), None => Value::null(&*ext_logical_type(self)?), }, - _ => vortex_bail!("cannot have TimeUnit {unit}, so represent a day"), + _ => { + vortex_bail!(InvalidArgument: "cannot have TimeUnit {unit}, so represent a day") + } }, TemporalMetadata::Time(unit) => match unit { TimeUnit::Microseconds => Value::new_time(value()?), @@ -291,7 +299,7 @@ impl ToDuckDBScalar for ExtScalar<'_> { TimeUnit::Seconds => Value::new_time(value()? * 1000 * 1000), TimeUnit::Nanoseconds => Value::new_time_ns(value()?), TimeUnit::Days => { - vortex_bail!("cannot convert timeunit {unit} to a duckdb time") + vortex_bail!(MismatchedTypes: "cannot convert timeunit {unit} to a duckdb time") } }, }) @@ -303,13 +311,14 @@ fn ext_logical_type(scalar: &ExtScalar<'_>) -> VortexResult { } fn timestamp_tz_micros(unit: TimeUnit, raw: i64) -> VortexResult { - let overflow = || vortex_err!("timestamp_tz overflow rescaling {raw}{unit} to micros"); + let overflow = + || vortex_err!(Overflow: "timestamp_tz overflow rescaling {raw}{unit} to micros"); match unit { TimeUnit::Seconds => raw.checked_mul(1_000_000).ok_or_else(overflow), TimeUnit::Milliseconds => raw.checked_mul(1_000).ok_or_else(overflow), TimeUnit::Microseconds => Ok(raw), TimeUnit::Nanoseconds => Ok(raw / 1_000), - TimeUnit::Days => vortex_bail!("timestamp_tz cannot have a day time unit"), + TimeUnit::Days => vortex_bail!(InvalidArgument: "timestamp_tz cannot have a day time unit"), } } @@ -343,10 +352,10 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { ExtractedValue::Integer(v) => Ok(Scalar::primitive(v, Nullable)), ExtractedValue::BigInt(v) => Ok(Scalar::primitive(v, Nullable)), ExtractedValue::HugeInt(_) => { - vortex_bail!("DuckDB HugeInt is not yet supported in Vortex"); + vortex_bail!(NotImplemented: "DuckDB HugeInt is not yet supported in Vortex"); } ExtractedValue::UHugeInt(_) => { - vortex_bail!("DuckDB UHugeInt is not yet supported in Vortex"); + vortex_bail!(NotImplemented: "DuckDB UHugeInt is not yet supported in Vortex"); } ExtractedValue::UTinyInt(v) => Ok(Scalar::primitive(v, Nullable)), ExtractedValue::USmallInt(v) => Ok(Scalar::primitive(v, Nullable)), @@ -362,7 +371,7 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { Scalar::binary(b, Nullable), )), DType::Extension(ext) if ext.is::() => { - vortex_ensure_eq!(b.len(), 16, "UUID blob must be 16 bytes"); + vortex_ensure_eq!(b.len(), 16, InvalidArgument: "UUID blob must be 16 bytes"); let children = b .iter() .map(|&byte| Scalar::primitive(byte, NonNullable)) @@ -374,7 +383,9 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { ); Ok(Scalar::extension_ref(ext.clone(), storage)) } - _ => vortex_bail!("Cannot convert DuckDB blob to Vortex scalar of dtype {dtype}"), + _ => { + vortex_bail!(MismatchedTypes: "Cannot convert DuckDB blob to Vortex scalar of dtype {dtype}") + } }, ExtractedValue::Date(days) => Ok(Scalar::extension::( TimeUnit::Days, @@ -474,11 +485,11 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { .collect::>>()?, )), _ => { - vortex_bail!("List value must be a list, fixed-size list or struct dtype") + vortex_bail!(MismatchedTypes: "List value must be a list, fixed-size list or struct dtype") } }, ExtractedValue::Unsupported(type_id) => { - vortex_bail!("Unsupported DuckDB value type {type_id:?}") + vortex_bail!(InvalidArgument: "Unsupported DuckDB value type {type_id:?}") } } } diff --git a/vortex-duckdb/src/convert/table_filter.rs b/vortex-duckdb/src/convert/table_filter.rs index 00d3decaf5e..f331e1a284d 100644 --- a/vortex-duckdb/src/convert/table_filter.rs +++ b/vortex-duckdb/src/convert/table_filter.rs @@ -101,7 +101,7 @@ pub fn try_from_table_filter( } } TableFilterClass::Bloom => { - vortex_bail!("bloom filter table filter is not supported") + vortex_bail!(InvalidArgument: "bloom filter table filter is not supported") } })) } @@ -122,7 +122,9 @@ pub(super) fn dynamic_filter_expr( DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_GREATERTHANOREQUALTO => { CompareOperator::Gte } - _ => vortex_bail!("unsupported dynamic filter operator {:?}", dynamic.operator), + _ => { + vortex_bail!(InvalidArgument: "unsupported dynamic filter operator {:?}", dynamic.operator) + } }; let data = dynamic.data; @@ -143,14 +145,14 @@ pub(super) fn dynamic_filter_expr( fn nonnegative_number_from_value(value: &ValueRef) -> VortexResult { match value.extract() { ExtractedValue::BigInt(i) => { - u64::try_from(i).map_err(|_| vortex_err!("negative value: {i}")) + u64::try_from(i).map_err(|_| vortex_err!(Overflow: "negative value: {i}")) } ExtractedValue::Integer(i) => { - u64::try_from(i).map_err(|_| vortex_err!("negative value: {i}")) + u64::try_from(i).map_err(|_| vortex_err!(Overflow: "negative value: {i}")) } ExtractedValue::UBigInt(u) => Ok(u), ExtractedValue::UInteger(u) => Ok(u64::from(u)), - _ => vortex_bail!("unexpected value type"), + _ => vortex_bail!(MismatchedTypes: "unexpected value type"), } } diff --git a/vortex-duckdb/src/convert/vector.rs b/vortex-duckdb/src/convert/vector.rs index 77e57226928..ab8002197a3 100644 --- a/vortex-duckdb/src/convert/vector.rs +++ b/vortex-duckdb/src/convert/vector.rs @@ -332,7 +332,7 @@ pub fn flat_vector_to_vortex(vector: &VectorRef, len: usize) -> VortexResult vortex_bail!("Unsupported decimal precision: {precision}"), + _ => vortex_bail!(InvalidArgument: "Unsupported decimal precision: {precision}"), } .map(|a| a.into_array()) } @@ -406,7 +406,9 @@ pub fn flat_vector_to_vortex(vector: &VectorRef, len: usize) -> VortexResult vortex_bail!("{type_id:?} flat Vector to Vortex array not supported"), + type_id => { + vortex_bail!(InvalidArgument: "{type_id:?} flat Vector to Vortex array not supported") + } } } @@ -1067,14 +1069,14 @@ mod tests { &point!(x: 1.0_f64, y: 2.0_f64), &WriteOptions::default(), ) - .map_err(|e| vortex::error::vortex_err!("writing WKB point: {e}"))?; + .map_err(|e| vortex::error::vortex_err!(Serde: "writing WKB point: {e}"))?; let mut wkb_b: Vec = Vec::new(); write_point( &mut wkb_b, &point!(x: 3.5_f64, y: -4.25_f64), &WriteOptions::default(), ) - .map_err(|e| vortex::error::vortex_err!("writing WKB point: {e}"))?; + .map_err(|e| vortex::error::vortex_err!(Serde: "writing WKB point: {e}"))?; let len = 3; let logical_type = LogicalType::geometry_type(Some("EPSG:4326"))?; diff --git a/vortex-duckdb/src/copy.rs b/vortex-duckdb/src/copy.rs index 6d3dbbbd952..a4c09b52f7c 100644 --- a/vortex-duckdb/src/copy.rs +++ b/vortex-duckdb/src/copy.rs @@ -98,7 +98,7 @@ fn push_to_writer(global: &CopyFunctionGlobal, array: ArrayRef) -> VortexResult< let mut sink = global .sink .as_ref() - .ok_or_else(|| vortex_err!("sink closed early"))? + .ok_or_else(|| vortex_err!(Io: "sink closed early"))? .clone(); RUNTIME.block_on(async { // send may error with "receiver is gone" which isn't the real error @@ -110,7 +110,7 @@ fn push_to_writer(global: &CopyFunctionGlobal, array: ArrayRef) -> VortexResult< // we can get the real error (i.e invalid path) from here task.await?; } - vortex_bail!("Writer stopped before all data was written") + vortex_bail!(Io: "Writer stopped before all data was written") }) } @@ -236,11 +236,11 @@ fn column_stats_from_summary( let file_stats = summary .footer() .statistics() - .ok_or_else(|| vortex_err!("written file has no statistics"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "written file has no statistics"))?; let stats_sets = file_stats.stats_sets(); if column_index >= stats_sets.len() { vortex_bail!( - "column index {column_index} out of range for {} statistics sets", + OutOfBounds: "column index {column_index} out of range for {} statistics sets", stats_sets.len() ); } diff --git a/vortex-duckdb/src/duckdb/connection.rs b/vortex-duckdb/src/duckdb/connection.rs index 719cc104e95..7acaee68a96 100644 --- a/vortex-duckdb/src/duckdb/connection.rs +++ b/vortex-duckdb/src/duckdb/connection.rs @@ -35,8 +35,8 @@ impl ConnectionRef { /// Execute SQL query and return the result. pub fn query(&self, query: &str) -> VortexResult { let mut result: cpp::duckdb_result = unsafe { std::mem::zeroed() }; - let query_cstr = - std::ffi::CString::new(query).map_err(|_| vortex_err!("Invalid query string"))?; + let query_cstr = std::ffi::CString::new(query) + .map_err(|_| vortex_err!(InvalidArgument: "Invalid query string"))?; let status = unsafe { cpp::duckdb_query(self.as_ptr(), query_cstr.as_ptr(), &raw mut result) }; @@ -52,7 +52,7 @@ impl ConnectionRef { }; unsafe { cpp::duckdb_destroy_result(&raw mut result) }; - return Err(vortex_err!("Failed to execute query: {}", error_msg)); + return Err(vortex_err!(InvalidArgument: "Failed to execute query: {}", error_msg)); } Ok(unsafe { QueryResult::new(result) }) diff --git a/vortex-duckdb/src/duckdb/data_chunk.rs b/vortex-duckdb/src/duckdb/data_chunk.rs index dce2a5637bf..02f228473b3 100644 --- a/vortex-duckdb/src/duckdb/data_chunk.rs +++ b/vortex-duckdb/src/duckdb/data_chunk.rs @@ -82,14 +82,14 @@ impl TryFrom<&DataChunkRef> for String { cpp::duckdb_data_chunk_verify(value.as_ptr(), &raw mut err); if !err.is_null() { vortex_bail!( - "{}", + InvalidArgument: "{}", CStr::from_ptr(cpp::duckdb_vx_error_value(err)).to_string_lossy() ) } }; let debug = unsafe { cpp::duckdb_data_chunk_to_string(value.as_ptr(), &raw mut err) }; if !err.is_null() { - vortex_bail!("{}", unsafe { + vortex_bail!(InvalidArgument: "{}", unsafe { CStr::from_ptr(cpp::duckdb_vx_error_value(err)).to_string_lossy() }) } diff --git a/vortex-duckdb/src/duckdb/database.rs b/vortex-duckdb/src/duckdb/database.rs index 53967a89d97..6bde4c143de 100644 --- a/vortex-duckdb/src/duckdb/database.rs +++ b/vortex-duckdb/src/duckdb/database.rs @@ -36,12 +36,11 @@ impl Database { /// /// Creates a new file in case the path does not exist. pub fn open>(path: P) -> VortexResult { - let path_str = path - .as_ref() - .to_str() - .ok_or_else(|| vortex_err!("Invalid path: path contains non-UTF8 characters"))?; + let path_str = path.as_ref().to_str().ok_or_else( + || vortex_err!(InvalidArgument: "Invalid path: path contains non-UTF8 characters"), + )?; let path_cstr = CString::new(path_str) - .map_err(|_| vortex_err!("Invalid path: path contains null bytes"))?; + .map_err(|_| vortex_err!(InvalidArgument: "Invalid path: path contains null bytes"))?; let mut ptr: duckdb_database = ptr::null_mut(); duckdb_try!( @@ -63,8 +62,9 @@ impl DatabaseRef { } pub fn register_version_function(&self, version: &str) -> VortexResult<()> { - let version = CString::new(version) - .map_err(|_| vortex_err!("Invalid version: string contains null bytes"))?; + let version = CString::new(version).map_err( + |_| vortex_err!(InvalidArgument: "Invalid version: string contains null bytes"), + )?; duckdb_try!( unsafe { cpp::duckdb_vx_register_version_function(self.as_ptr(), version.as_ptr()) }, "Failed to register vortex_version function" diff --git a/vortex-duckdb/src/duckdb/function.rs b/vortex-duckdb/src/duckdb/function.rs index 0441fe43548..b70ba55fa9a 100644 --- a/vortex-duckdb/src/duckdb/function.rs +++ b/vortex-duckdb/src/duckdb/function.rs @@ -16,7 +16,7 @@ impl ScalarFunctionRef { let name_ptr = cpp::duckdb_vx_sfunc_name(self.as_ptr()); std::ffi::CStr::from_ptr(name_ptr) .to_str() - .map_err(|e| vortex_err!("invalid utf-8: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "invalid utf-8: {e}")) .vortex_expect("scalar function name should be valid UTF-8") } } @@ -28,7 +28,7 @@ impl AggregateFunctionRef { let name_ptr = cpp::duckdb_vx_agg_func_name(self.as_ptr()); std::ffi::CStr::from_ptr(name_ptr) .to_str() - .map_err(|e| vortex_err!("invalid utf-8: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "invalid utf-8: {e}")) .vortex_expect("aggregate function name should be valid UTF-8") } } diff --git a/vortex-duckdb/src/duckdb/logical_type.rs b/vortex-duckdb/src/duckdb/logical_type.rs index ea1443db50a..1cb25a7b43f 100644 --- a/vortex-duckdb/src/duckdb/logical_type.rs +++ b/vortex-duckdb/src/duckdb/logical_type.rs @@ -89,7 +89,7 @@ impl LogicalType { }; if struct_type_ptr.is_null() { - vortex_bail!("Failed to create struct logical type"); + vortex_bail!(InvalidArgument: "Failed to create struct logical type"); } Ok(unsafe { Self::own(struct_type_ptr) }) @@ -99,13 +99,13 @@ impl LogicalType { pub fn decimal_type(precision: u8, scale: u8) -> VortexResult { vortex_ensure!( precision <= DUCKDB_MAX_DECIMAL_PRECISION, - "DuckDB decimal type precision must be <= {DUCKDB_MAX_DECIMAL_PRECISION}. \ + InvalidArgument: "DuckDB decimal type precision must be <= {DUCKDB_MAX_DECIMAL_PRECISION}. \ precision: {precision}" ); let ptr = unsafe { duckdb_create_decimal_type(precision, scale) }; if ptr.is_null() { - vortex_bail!("Failed to create decimal type"); + vortex_bail!(InvalidArgument: "Failed to create decimal type"); } Ok(unsafe { Self::own(ptr) }) } @@ -115,7 +115,7 @@ impl LogicalType { let ptr = unsafe { duckdb_create_list_type(element_type.as_ptr()) }; if ptr.is_null() { - vortex_bail!("Failed to create list type"); + vortex_bail!(InvalidArgument: "Failed to create list type"); } Ok(unsafe { Self::own(ptr) }) } @@ -128,7 +128,7 @@ impl LogicalType { let ptr = unsafe { duckdb_create_array_type(element_type.as_ptr(), list_size as idx_t) }; if ptr.is_null() { - vortex_bail!("Failed to create fixed-size list (array) type"); + vortex_bail!(InvalidArgument: "Failed to create fixed-size list (array) type"); } // SAFETY: This pointer came directly from DuckDB, and we checked that it was not `NULL`. @@ -140,7 +140,7 @@ impl LogicalType { let ptr = unsafe { duckdb_create_map_type(key_type.as_ptr(), value_type.as_ptr()) }; if ptr.is_null() { - vortex_bail!("Failed to create map type"); + vortex_bail!(InvalidArgument: "Failed to create map type"); } Ok(unsafe { Self::own(ptr) }) } @@ -238,11 +238,11 @@ impl LogicalType { /// Pass `None` for a GEOMETRY with no associated CRS. pub fn geometry_type(crs: Option<&str>) -> VortexResult { let Ok(crs) = CString::new(crs.unwrap_or("")) else { - vortex_bail!("CRS must not contain NUL bytes"); + vortex_bail!(InvalidArgument: "CRS must not contain NUL bytes"); }; let ptr = unsafe { duckdb_vx_create_geometry(crs.as_ptr()) }; if ptr.is_null() { - vortex_bail!("Failed to create GEOMETRY logical type"); + vortex_bail!(InvalidArgument: "Failed to create GEOMETRY logical type"); } Ok(unsafe { Self::own(ptr) }) } @@ -456,7 +456,7 @@ macro_rules! match_each_primitive_type { $body } _ => vortex::error::vortex_panic!( - "Unexpected type for match_each_primitive_type: {:?}", + MismatchedTypes: "Unexpected type for match_each_primitive_type: {:?}", $self.as_type_id() ), } diff --git a/vortex-duckdb/src/duckdb/macro_.rs b/vortex-duckdb/src/duckdb/macro_.rs index 56d3aa273a4..1e454396834 100644 --- a/vortex-duckdb/src/duckdb/macro_.rs +++ b/vortex-duckdb/src/duckdb/macro_.rs @@ -6,21 +6,21 @@ macro_rules! duckdb_try { // Pattern: duckdb_try!(function_call) ($call:expr) => { if $call != $crate::cpp::duckdb_state::DuckDBSuccess { - vortex::error::vortex_bail!("DuckDB operation failed"); + vortex::error::vortex_bail!(Other: "DuckDB operation failed"); } }; // Pattern: duckdb_try!(function_call, "error message") - ($call:expr, $msg:expr) => { + ($call:expr, $msg:literal) => { if $call != $crate::cpp::duckdb_state::DuckDBSuccess { - vortex::error::vortex_bail!($msg); + vortex::error::vortex_bail!(Other: $msg); } }; // Pattern: duckdb_try!(function_call, "error message with {}", args...) - ($call:expr, $msg:expr, $($args:expr),+) => { + ($call:expr, $msg:literal, $($args:expr),+) => { if $call != $crate::cpp::duckdb_state::DuckDBSuccess { - vortex::error::vortex_bail!($msg, $($args),+); + vortex::error::vortex_bail!(Other: $msg, $($args),+); } }; } @@ -66,7 +66,7 @@ macro_rules! lifetime_wrapper { pub unsafe fn own(ptr: $ffi_type) -> Self { if ptr.is_null() { vortex::error::vortex_panic!( - "Attempted to create an owned wrapper from a null pointer" + InvalidArgument: "Attempted to create an owned wrapper from a null pointer" ); } Self(unsafe { std::ptr::NonNull::new_unchecked(ptr.cast()) }) @@ -80,7 +80,7 @@ macro_rules! lifetime_wrapper { pub unsafe fn borrow<'a>(ptr: $ffi_type) -> &'a [<$Name Ref>] { if ptr.is_null() { vortex::error::vortex_panic!( - "Attempted to borrow from a null pointer" + InvalidArgument: "Attempted to borrow from a null pointer" ); } unsafe { &*(ptr as *const [<$Name Ref>]) } @@ -95,7 +95,7 @@ macro_rules! lifetime_wrapper { pub unsafe fn borrow_mut<'a>(ptr: $ffi_type) -> &'a mut [<$Name Ref>] { if ptr.is_null() { vortex::error::vortex_panic!( - "Attempted to borrow_mut from a null pointer" + InvalidArgument: "Attempted to borrow_mut from a null pointer" ); } unsafe { &mut *(ptr as *mut [<$Name Ref>]) } diff --git a/vortex-duckdb/src/duckdb/query_result.rs b/vortex-duckdb/src/duckdb/query_result.rs index c32c1debf0d..109a9b23439 100644 --- a/vortex-duckdb/src/duckdb/query_result.rs +++ b/vortex-duckdb/src/duckdb/query_result.rs @@ -65,11 +65,11 @@ impl QueryResultRef { let name_ptr = cpp::duckdb_column_name(self.as_ptr(), col_idx as u64); if name_ptr.is_null() { - vortex_bail!("Invalid column index: {}", col_idx); + vortex_bail!(InvalidArgument: "Invalid column index: {}", col_idx); } CStr::from_ptr(name_ptr) .to_str() - .map_err(|_| vortex_err!("Invalid UTF-8 in column name")) + .map_err(|_| vortex_err!(InvalidArgument: "Invalid UTF-8 in column name")) } } diff --git a/vortex-duckdb/src/duckdb/table_filter.rs b/vortex-duckdb/src/duckdb/table_filter.rs index 79468315144..c0facf7bce2 100644 --- a/vortex-duckdb/src/duckdb/table_filter.rs +++ b/vortex-duckdb/src/duckdb/table_filter.rs @@ -52,7 +52,7 @@ impl<'a> IntoIterator for &'a TableFilterSetRef { fn into_iter(self) -> Self::IntoIter { Box::new((0..self.len()).map(move |i| { self.get(i) - .unwrap_or_else(|| vortex_panic!("inside filter set bounds {i}")) + .unwrap_or_else(|| vortex_panic!(AssertionFailed: "inside filter set bounds {i}")) })) } } diff --git a/vortex-duckdb/src/duckdb/value.rs b/vortex-duckdb/src/duckdb/value.rs index 506f047cf0e..fb980f7f9bd 100644 --- a/vortex-duckdb/src/duckdb/value.rs +++ b/vortex-duckdb/src/duckdb/value.rs @@ -36,7 +36,7 @@ impl ValueRef { pub fn as_string(&self) -> BufferString { let ExtractedValue::Varchar(string) = self.extract() else { - vortex_panic!("ValueRef is not a string"); + vortex_panic!(MismatchedTypes: "ValueRef is not a string"); }; string } @@ -47,7 +47,9 @@ impl ValueRef { return ExtractedValue::Null; } match self.logical_type().as_type_id() { - DUCKDB_TYPE::DUCKDB_TYPE_INVALID => vortex_panic!("Invalid type for DuckDB value"), + DUCKDB_TYPE::DUCKDB_TYPE_INVALID => { + vortex_panic!(MismatchedTypes: "Invalid type for DuckDB value") + } DUCKDB_TYPE::DUCKDB_TYPE_SQLNULL => ExtractedValue::Null, DUCKDB_TYPE::DUCKDB_TYPE_BOOLEAN => { ExtractedValue::Boolean(unsafe { cpp::duckdb_get_bool(self.as_ptr()) }) @@ -95,7 +97,7 @@ impl ValueRef { let cstr = unsafe { CStr::from_ptr(ptr) }; let string = BufferString::from( cstr.to_str() - .map_err(|e| vortex_err!("Invalid UTF-8 string from DuckDB: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "Invalid UTF-8 string from DuckDB: {e}")) .vortex_expect("Invalid UTF-8 string from DuckDB"), ); unsafe { cpp::duckdb_free(ptr.cast()) }; @@ -296,7 +298,7 @@ impl Value { let crs_c = crs .map(CString::new) .transpose() - .map_err(|_| vortex_err!("CRS must not contain NUL bytes"))?; + .map_err(|_| vortex_err!(InvalidArgument: "CRS must not contain NUL bytes"))?; let crs_ptr = crs_c.as_ref().map_or(ptr::null(), |c| c.as_ptr()); Ok(unsafe { Self::own(cpp::duckdb_vx_value_create_geometry( @@ -339,7 +341,7 @@ impl Value { vortex_ensure_eq!( fields.len(), struct_type.struct_type_child_count(), - "struct value field count must match its logical type" + InvalidArgument: "struct value field count must match its logical type" ); let mut ptrs = value_ptrs(fields); let ptr = @@ -356,7 +358,7 @@ impl Value { vortex_ensure_eq!( keys.len(), values.len(), - "map value must have as many keys as values" + InvalidArgument: "map value must have as many keys as values" ); let mut key_ptrs = value_ptrs(keys); let mut val_ptrs = value_ptrs(values); @@ -375,7 +377,7 @@ impl Value { /// invalid input. fn try_own(ptr: cpp::duckdb_value, kind: &str) -> VortexResult { if ptr.is_null() { - vortex_bail!("Failed to create DuckDB {kind} value"); + vortex_bail!(InvalidArgument: "Failed to create DuckDB {kind} value"); } Ok(unsafe { Self::own(ptr) }) } diff --git a/vortex-duckdb/src/duckdb/vector.rs b/vortex-duckdb/src/duckdb/vector.rs index 1d37ff9d6ef..3a7ce09a5cd 100644 --- a/vortex-duckdb/src/duckdb/vector.rs +++ b/vortex-duckdb/src/duckdb/vector.rs @@ -285,7 +285,7 @@ impl VectorRef { let state = unsafe { cpp::duckdb_list_vector_reserve(self.as_ptr(), required_capacity) }; match state { cpp::duckdb_state::DuckDBSuccess => Ok(()), - cpp::duckdb_state::DuckDBError => vortex_bail!("vector was nullptr!"), + cpp::duckdb_state::DuckDBError => vortex_bail!(InvalidArgument: "vector was nullptr!"), } } @@ -313,7 +313,7 @@ impl VectorRef { let state = unsafe { cpp::duckdb_list_vector_set_size(self.as_ptr(), size) }; match state { cpp::duckdb_state::DuckDBSuccess => Ok(()), - cpp::duckdb_state::DuckDBError => vortex_bail!("vector was nullptr!"), + cpp::duckdb_state::DuckDBError => vortex_bail!(InvalidArgument: "vector was nullptr!"), } } diff --git a/vortex-duckdb/src/exporter/canonical.rs b/vortex-duckdb/src/exporter/canonical.rs index e7374298c26..01a9b0122ea 100644 --- a/vortex-duckdb/src/exporter/canonical.rs +++ b/vortex-duckdb/src/exporter/canonical.rs @@ -30,15 +30,15 @@ pub(crate) fn new_exporter( Canonical::Decimal(array) => decimal::new_exporter(array, ctx), Canonical::VarBinView(array) => varbinview::new_exporter(array, ctx), Canonical::List(array) => list_view::new_exporter(array, cache, ctx), - Canonical::Map(_) => vortex_bail!("Map arrays can't be exported to DuckDB"), + Canonical::Map(_) => vortex_bail!(NotImplemented: "Map arrays can't be exported to DuckDB"), Canonical::FixedSizeList(array) => fixed_size_list::new_exporter(array, cache, ctx), Canonical::Struct(array) => struct_::new_exporter(array, cache, ctx), Canonical::Union(_) => { - vortex_bail!("TODO(connor)[Union]: implement DuckDB export for Union arrays") + vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement DuckDB export for Union arrays") } Canonical::Extension(ext) => extension::new_exporter(ext, ctx), Canonical::Variant(_) => { - vortex_bail!("Variant arrays can't be exported to DuckDB") + vortex_bail!(NotImplemented: "Variant arrays can't be exported to DuckDB") } } } diff --git a/vortex-duckdb/src/exporter/chunked.rs b/vortex-duckdb/src/exporter/chunked.rs index 78a4e0dfee3..2c8deee72a2 100644 --- a/vortex-duckdb/src/exporter/chunked.rs +++ b/vortex-duckdb/src/exporter/chunked.rs @@ -80,7 +80,7 @@ impl ColumnExporter for ChunkedExporter { let offset_in_chunk = offset - chunk_start; vortex_ensure!( offset + len <= chunk_end, - "chunked DuckDB export range {offset}..{} crosses chunk boundary at {chunk_end}", + InvalidArgument: "chunked DuckDB export range {offset}..{} crosses chunk boundary at {chunk_end}", offset + len ); diff --git a/vortex-duckdb/src/exporter/decimal.rs b/vortex-duckdb/src/exporter/decimal.rs index 8d2052a3215..7cf561892a3 100644 --- a/vortex-duckdb/src/exporter/decimal.rs +++ b/vortex-duckdb/src/exporter/decimal.rs @@ -123,7 +123,9 @@ pub fn precision_to_duckdb_storage_size(decimal_dtype: &DecimalDType) -> VortexR 5..=9 => DecimalType::I32, 10..=18 => DecimalType::I64, 19..=38 => DecimalType::I128, - decimal_dtype => vortex_bail!("cannot represent decimal in ducdkb {decimal_dtype}"), + decimal_dtype => { + vortex_bail!(NotImplemented: "cannot represent decimal in ducdkb {decimal_dtype}") + } }) } diff --git a/vortex-duckdb/src/exporter/extension.rs b/vortex-duckdb/src/exporter/extension.rs index ebebefd177c..5ac31b81ef1 100644 --- a/vortex-duckdb/src/exporter/extension.rs +++ b/vortex-duckdb/src/exporter/extension.rs @@ -69,5 +69,5 @@ pub(crate) fn new_exporter( return spatial::new_multipolygon_exporter(MultiPolygonData::try_from(ext)?, ctx); } - vortex_bail!("no non-temporal extension exporter") + vortex_bail!(NotImplemented: "no non-temporal extension exporter") } diff --git a/vortex-duckdb/src/exporter/mod.rs b/vortex-duckdb/src/exporter/mod.rs index 539a6d994a2..f8743af8fc2 100644 --- a/vortex-duckdb/src/exporter/mod.rs +++ b/vortex-duckdb/src/exporter/mod.rs @@ -103,7 +103,7 @@ impl ArrayExporter { let expected_cols = self.fields.len(); let chunk_cols = chunk.column_count(); if !zero_projection && chunk_cols != expected_cols { - vortex_bail!("Expected {expected_cols} columns in output chunk, got {chunk_cols}"); + vortex_bail!(MismatchedTypes: "Expected {expected_cols} columns in output chunk, got {chunk_cols}"); } let position = self.array_len - self.remaining; @@ -115,7 +115,7 @@ impl ArrayExporter { } vortex_ensure!( chunk_len > 0, - "column exporter returned zero rows for non-empty export" + AssertionFailed: "column exporter returned zero rows for non-empty export" ); self.remaining -= chunk_len; diff --git a/vortex-duckdb/src/exporter/uuid.rs b/vortex-duckdb/src/exporter/uuid.rs index 73a221033bc..a5cb990a935 100644 --- a/vortex-duckdb/src/exporter/uuid.rs +++ b/vortex-duckdb/src/exporter/uuid.rs @@ -44,7 +44,7 @@ pub(crate) fn new_exporter( vortex_ensure_eq!( bytes.len(), len * UUID_BYTE_LEN, - "UUID storage byte length mismatch" + InvalidArgument: "UUID storage byte length mismatch" ); let exporter = Box::new(UuidExporter { bytes }); diff --git a/vortex-duckdb/src/ffi.rs b/vortex-duckdb/src/ffi.rs index 01e6cf5a7e2..ea0323893ab 100644 --- a/vortex-duckdb/src/ffi.rs +++ b/vortex-duckdb/src/ffi.rs @@ -191,7 +191,8 @@ pub unsafe extern "C-unwind" fn duckdb_reader_open( let path = unsafe { std::slice::from_raw_parts(file_path.cast::(), file_path_len) }; try_or_null(error, || { - let path = str::from_utf8(path).map_err(|_| vortex_err!("invalid utf-8"))?; + let path = + str::from_utf8(path).map_err(|_| vortex_err!(InvalidArgument: "invalid utf-8"))?; let file = reader_open(path)?; Ok(Data::from(Box::new(file)).as_ptr()) }) @@ -242,7 +243,8 @@ pub unsafe extern "C-unwind" fn duckdb_footer_get_cached( let bind = unsafe { bind.cast::().as_mut() }.vortex_expect("null pointer"); let path = unsafe { std::slice::from_raw_parts(path.cast::(), len) }; try_or_null(error, || { - let path = str::from_utf8(path).map_err(|_| vortex_err!("invalid utf-8"))?; + let path = + str::from_utf8(path).map_err(|_| vortex_err!(InvalidArgument: "invalid utf-8"))?; Ok(match footer_get_cached(bind, path)? { Some(footer) => { unsafe { *row_count_out = footer.row_count() }; diff --git a/vortex-duckdb/src/lib.rs b/vortex-duckdb/src/lib.rs index 1209213135f..0201079ba40 100644 --- a/vortex-duckdb/src/lib.rs +++ b/vortex-duckdb/src/lib.rs @@ -14,7 +14,6 @@ use vortex::editions::CORE_2026_08_3; use vortex::editions::EditionSessionExt; use vortex::error::VortexExpect; use vortex::error::VortexResult; -use vortex::error::vortex_err; use vortex::io::runtime::BlockingRuntime; use vortex::io::runtime::current::CurrentThreadRuntime; use vortex::io::session::RuntimeSessionExt; @@ -51,7 +50,6 @@ static SESSION: LazyLock = LazyLock::new(|| { let session = VortexSession::default().with_handle(RUNTIME.handle()); session .enable_edition(CORE_2026_08_3) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("DuckDB-supported draft core edition is registered"); vortex_spatial::initialize(&session); session diff --git a/vortex-duckdb/src/projection.rs b/vortex-duckdb/src/projection.rs index beec2cc74db..b3bca3db2cc 100644 --- a/vortex-duckdb/src/projection.rs +++ b/vortex-duckdb/src/projection.rs @@ -267,9 +267,9 @@ impl Filter { } pub fn extract_schema_from_dtype(dtype: &DType) -> VortexResult> { - let struct_dtype = dtype - .as_struct_fields_opt() - .ok_or_else(|| vortex_err!("Vortex file must contain a struct array at the top level"))?; + let struct_dtype = dtype.as_struct_fields_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "Vortex file must contain a struct array at the top level"), + )?; let len = struct_dtype.names().len(); let mut fields = Vec::with_capacity(len); diff --git a/vortex-duckdb/src/table_function.rs b/vortex-duckdb/src/table_function.rs index ed751b1d64b..8bbd3758afa 100644 --- a/vortex-duckdb/src/table_function.rs +++ b/vortex-duckdb/src/table_function.rs @@ -394,7 +394,9 @@ fn aggregate_output_value(scalar: Scalar, expected: &LogicalTypeRef) -> VortexRe Ok(match primitive.ptype() { PType::I64 => primitive.typed_value::().map(i128::from), PType::U64 => primitive.typed_value::().map(i128::from), - other => vortex_bail!("expected {expected:?} output type, got {other}"), + other => { + vortex_bail!(MismatchedTypes: "expected {expected:?} output type, got {other}") + } }) }; match expected.as_type_id() { diff --git a/vortex-edition/src/lib.rs b/vortex-edition/src/lib.rs index ede2646bb17..f1b787c4e0a 100644 --- a/vortex-edition/src/lib.rs +++ b/vortex-edition/src/lib.rs @@ -95,13 +95,13 @@ impl EditionId { /// [`test_harness::validate_edition`]. pub fn validate(&self) -> VortexResult<()> { if self.family.is_empty() || !self.family.chars().all(|c| c.is_ascii_lowercase()) { - vortex_bail!("edition {self} must have a non-empty lowercase family, e.g. `core`"); + vortex_bail!(InvalidArgument: "edition {self} must have a non-empty lowercase family, e.g. `core`"); } if !(1000..=9999).contains(&self.year) { - vortex_bail!("edition {self} must have a four-digit year"); + vortex_bail!(InvalidArgument: "edition {self} must have a four-digit year"); } if !(1..=12).contains(&self.month) { - vortex_bail!("edition {self} must have a month in 01-12"); + vortex_bail!(InvalidArgument: "edition {self} must have a month in 01-12"); } Ok(()) } @@ -141,18 +141,18 @@ impl EditionFamily { pub fn validate(&self) -> VortexResult<()> { if self.name.is_empty() || !self.name.chars().all(|c| c.is_ascii_lowercase()) { vortex_bail!( - "edition family {:?} must have a non-empty lowercase name, e.g. `core`", + InvalidArgument: "edition family {:?} must have a non-empty lowercase name, e.g. `core`", self.name ); } if self.origin.trim().is_empty() { vortex_bail!( - "edition family {} must name its origin library or project", + InvalidArgument: "edition family {} must name its origin library or project", self.name ); } if self.doc.trim().is_empty() { - vortex_bail!("edition family {} must document what it is for", self.name); + vortex_bail!(InvalidArgument: "edition family {} must document what it is for", self.name); } Ok(()) } @@ -369,7 +369,7 @@ impl EditionInclusion { .all(|c| c.is_ascii_lowercase() || c.is_ascii_digit() || "._-".contains(c)); if !well_formed { vortex_bail!( - "invalid {} id {id:?}: expected lowercase `namespace.name`, e.g. `vortex.alp`", + InvalidArgument: "invalid {} id {id:?}: expected lowercase `namespace.name`, e.g. `vortex.alp`", self.kind ); } @@ -377,7 +377,7 @@ impl EditionInclusion { && parse_release(release).is_none() { vortex_bail!( - "{} {id} declares malformed required_vortex_release {release:?}", + Serde: "{} {id} declares malformed required_vortex_release {release:?}", self.kind ); } diff --git a/vortex-edition/src/session.rs b/vortex-edition/src/session.rs index 4b192e3d7d9..089c6e4ca40 100644 --- a/vortex-edition/src/session.rs +++ b/vortex-edition/src/session.rs @@ -106,7 +106,7 @@ impl EditionSession { pub fn declare_family(&self, family: &EditionFamily) -> VortexResult<()> { let mut inner = self.inner.write(); if inner.families.contains_key(family.name) { - vortex_bail!("duplicate edition family {}", family.name); + vortex_bail!(InvalidArgument: "duplicate edition family {}", family.name); } inner.families.insert(family.name.to_string(), *family); Ok(()) @@ -127,7 +127,7 @@ impl EditionSession { let mut inner = self.inner.write(); let key = edition.id.to_string(); if inner.editions.contains_key(&key) { - vortex_bail!("duplicate edition {key}"); + vortex_bail!(InvalidArgument: "duplicate edition {key}"); } inner.editions.insert(key, edition); Ok(()) @@ -153,7 +153,7 @@ impl EditionSession { if let Some(previous) = previous { vortex_bail!( - "{} {} already joined family {} in edition {}", + InvalidArgument: "{} {} already joined family {} in edition {}", inclusion.kind, inclusion.component_id, inclusion.since.family, @@ -234,7 +234,7 @@ impl EditionSession { edition.id.validate()?; if self.find_family(edition.id.family).is_none() { vortex_bail!( - "edition {} belongs to undeclared family {}; declare the family before \ + NotFound: "edition {} belongs to undeclared family {}; declare the family before \ its editions", edition.id, edition.id.family, @@ -244,7 +244,7 @@ impl EditionSession { && parse_release(version).is_none() { vortex_bail!( - "edition {} declares malformed min_library_version {version:?}", + Serde: "edition {} declares malformed min_library_version {version:?}", edition.id ); } @@ -256,7 +256,7 @@ impl EditionSession { let (prev, next) = (&pair[0], &pair[1]); if prev.id.family == next.id.family && prev.is_draft() && !next.is_draft() { vortex_bail!( - "frozen edition {} follows draft {}; drafts must be newest in a family", + InvalidArgument: "frozen edition {} follows draft {}; drafts must be newest in a family", next.id, prev.id, ); @@ -274,7 +274,7 @@ impl EditionSession { let Some(edition) = inner.editions.get(&inclusion.since.to_string()) else { vortex_bail!( - "{} {} is included in undeclared edition {}", + NotFound: "{} {} is included in undeclared edition {}", inclusion.kind, inclusion.component_id, inclusion.since @@ -286,7 +286,7 @@ impl EditionSession { && required > declared { vortex_bail!( - "{} {} requires release {}, newer than edition {}'s declared \ + InvalidArgument: "{} {} requires release {}, newer than edition {}'s declared \ min_library_version", inclusion.kind, inclusion.component_id, @@ -347,7 +347,7 @@ pub trait EditionSessionExt: SessionExt { /// silently produce an empty writable set. fn enable_edition(&self, edition: EditionId) -> VortexResult<()> { if self.editions().find(&edition).is_none() { - vortex_bail!("cannot enable unregistered edition {edition}"); + vortex_bail!(NotFound: "cannot enable unregistered edition {edition}"); } self.enabled_editions().enable(edition); Ok(()) diff --git a/vortex-edition/src/test_harness.rs b/vortex-edition/src/test_harness.rs index 0594ccf9756..105ba91bb76 100644 --- a/vortex-edition/src/test_harness.rs +++ b/vortex-edition/src/test_harness.rs @@ -28,7 +28,7 @@ use crate::EditionSession; pub fn validate_edition(editions: &EditionSession, edition: &EditionId) -> VortexResult<()> { edition.validate()?; if editions.find(edition).is_none() { - vortex_bail!("{edition} is not declared in the session"); + vortex_bail!(NotFound: "{edition} is not declared in the session"); } editions.validate() } diff --git a/vortex-edition/src/tests.rs b/vortex-edition/src/tests.rs index 7394414499d..786e46b9087 100644 --- a/vortex-edition/src/tests.rs +++ b/vortex-edition/src/tests.rs @@ -97,17 +97,17 @@ fn membership_is_transitive() -> VortexResult<()> { let alpha = second .iter() .find(|i| i.component_id.as_str() == "test.alpha") - .ok_or_else(|| vortex_err!("test.alpha is a member"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "test.alpha is a member"))?; assert_eq!(alpha.since, FIRST); let alpha_v2 = second .iter() .find(|i| i.component_id.as_str() == "test.alpha_v2") - .ok_or_else(|| vortex_err!("test.alpha_v2 is a member"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "test.alpha_v2 is a member"))?; assert_eq!(alpha_v2.since, SECOND); let beta = second .iter() .find(|i| i.component_id.as_str() == "test.beta") - .ok_or_else(|| vortex_err!("test.beta is a member"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "test.beta is a member"))?; assert_eq!(beta.since, FIRST); // The second edition's delta is exactly the members declared at it. diff --git a/vortex-error/src/lib.rs b/vortex-error/src/lib.rs index f8ebd0ecec6..ec9047f5418 100644 --- a/vortex-error/src/lib.rs +++ b/vortex-error/src/lib.rs @@ -5,6 +5,11 @@ //! This crate defines error & result types for Vortex. //! It also contains a variety of useful macros for error handling. +//! +//! Vortex models errors the way Python models exceptions: a small, stable set of classes +//! ([`VortexErrorKind`]) carrying a human-readable message, rather than one enum variant per +//! library that Vortex happens to depend on. An error from a dependency is attached as the +//! [`Error::source`] of a [`VortexError`] and is recovered by downcasting that source. use std::backtrace::Backtrace; use std::backtrace::BacktraceStatus; @@ -23,7 +28,7 @@ use std::sync::Arc; use std::sync::LazyLock; /// A string that can be used as an error message. -#[derive(Debug)] +#[derive(Debug, Clone)] pub struct ErrString(Cow<'static, str>); #[expect( @@ -73,194 +78,144 @@ impl Display for ErrString { } } -impl From for VortexError { - fn from(_: Infallible) -> Self { - unreachable!() +/// The classification of a [`VortexError`], analogous to a Python exception class. +/// +/// The set is deliberately small and is mirrored by the `vx_error_code` enum in the C API, so a +/// kind only earns its place if a caller would branch on it. Failures originating in a dependency +/// are classified by what they mean to Vortex, not by which crate produced them. +#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)] +#[non_exhaustive] +pub enum VortexErrorKind { + /// An otherwise unclassified error. The analogue of Python's `RuntimeError`. + Other, + /// An index is out of bounds. The analogue of Python's `IndexError`. + OutOfBounds, + /// A name was looked up and nothing was bound to it. The analogue of Python's `KeyError`. + NotFound, + /// A numeric value does not fit its target type. The analogue of Python's `OverflowError`. + Overflow, + /// An invalid argument was provided. The analogue of Python's `ValueError`. + InvalidArgument, + /// An error occurred while serializing or deserializing. Closest to Python's `ValueError`, + /// as raised by `json.JSONDecodeError`. + Serde, + /// An unimplemented function was called. The analogue of Python's `NotImplementedError`. + NotImplemented, + /// A value did not have the expected type. The analogue of Python's `TypeError`. + MismatchedTypes, + /// An internal invariant was violated. The analogue of Python's `AssertionError`. + AssertionFailed, + /// An IO operation, or a call into the operating system or a device driver, failed. The + /// analogue of Python's `OSError`, which covers any system function that reports an error. + Io, +} + +impl VortexErrorKind { + /// The human-readable prefix used when displaying an error of this kind. + const fn prefix(self) -> &'static str { + match self { + Self::Other => "Other error: ", + Self::OutOfBounds => "Out of bounds error: ", + Self::NotFound => "Not found error: ", + Self::Overflow => "Overflow error: ", + Self::InvalidArgument => "Invalid argument error: ", + Self::Serde => "Serde error: ", + Self::NotImplemented => "Not implemented error: ", + Self::MismatchedTypes => "Mismatched types error: ", + Self::AssertionFailed => "Assertion failed error: ", + Self::Io => "IO error: ", + } } } -const _: () = assert!(size_of::() < 128); - /// The top-level error type for Vortex. -#[non_exhaustive] -pub enum VortexError { - /// A catch-all error variant - Other(ErrString, Box), - /// A wrapped external error - External(Box, Box), - /// An index is out of bounds. - OutOfBounds(usize, usize, usize, Box), - /// An error occurred while executing a compute kernel. - Compute(ErrString, Box), - /// An invalid argument was provided. - InvalidArgument(ErrString, Box), - /// An error occurred while serializing or deserializing. - Serde(ErrString, Box), - /// An unimplemented function was called. - NotImplemented(ErrString, ErrString, Box), - /// A type mismatch occurred. - MismatchedTypes(ErrString, ErrString, Box), - /// An assertion failed. - AssertionFailed(ErrString, Box), - /// A wrapper for other errors, carrying additional context. - Context(ErrString, Box), - /// A wrapper for shared errors that require cloning. - Shared(Arc), - /// A wrapper for errors from the Arrow library. - Arrow(arrow_schema::ArrowError, Box), - /// A wrapper for errors from the FlatBuffers library. - #[cfg(feature = "flatbuffers")] - FlatBuffers(flatbuffers::InvalidFlatbuffer, Box), - /// A wrapper for formatting errors. - Fmt(fmt::Error, Box), - /// A wrapper for IO errors. - Io(io::Error, Box), - /// A wrapper for errors from the Object Store library. - #[cfg(feature = "object_store")] - ObjectStore(object_store::Error, Box), - /// A wrapper for errors from the Jiff library. - Jiff(jiff::Error, Box), - /// A wrapper for Tokio join error. - #[cfg(feature = "tokio")] - Join(tokio::task::JoinError, Box), - /// Wrap errors for fallible integer casting. - TryFromInt(TryFromIntError, Box), - /// Wrap protobuf-related errors - Prost(Box, Box), +/// +/// An error is a [`VortexErrorKind`], a message, an optional underlying error, and a backtrace +/// captured at construction. Cloning is cheap: the payload is shared, never copied. +#[derive(Clone)] +pub struct VortexError { + kind: VortexErrorKind, + /// `None` defers the message to `source`, keeping the `?` conversion path allocation-free. + message: Option, + source: Option>, + backtrace: Arc, } +const _: () = assert!(size_of::() <= 56); + impl VortexError { - /// Adds additional context to an error. - pub fn with_context>(self, msg: T) -> Self { - VortexError::Context(msg.into(), Box::new(self)) + /// Creates an error of the given kind carrying `message`. + pub fn new>(kind: VortexErrorKind, message: T) -> Self { + Self { + kind, + message: Some(message.into()), + source: None, + backtrace: Arc::new(Backtrace::capture()), + } } - /// Error prefix by variant - fn variant_prefix(&self) -> &'static str { - use VortexError::*; - - match self { - Other(..) => "Other error: ", - External(..) => "External error: ", - OutOfBounds(..) => "Out of bounds error: ", - Compute(..) => "Compute error: ", - InvalidArgument(..) => "Invalid argument error: ", - Serde(..) => "Serde error: ", - NotImplemented(..) => "Not implemented error: ", - MismatchedTypes(..) => "Mismatched types error: ", - AssertionFailed(..) => "Assertion failed error: ", - Context(..) | Shared(..) => "", // basically delegate to the underlying one - Arrow(..) => "Arrow error: ", - #[cfg(feature = "flatbuffers")] - FlatBuffers(..) => "Flat buffers error: ", - Fmt(..) => "Fmt: ", - Io(..) => "Io: ", - #[cfg(feature = "object_store")] - ObjectStore(..) => "Object store error: ", - Jiff(..) => "Jiff error: ", - #[cfg(feature = "tokio")] - Join(..) => "Tokio join error:", - TryFromInt(..) => "Try from int error:", - Prost(..) => "Prost error:", + /// Wraps an underlying error as a Vortex error of the given kind. + /// + /// The wrapped error is preserved as the [`Error::source`], so callers that care about the + /// concrete type can recover it with [`Error::source`] and `downcast_ref`. + pub fn wrap(kind: VortexErrorKind, source: E) -> Self + where + E: Into>, + { + Self { + kind, + message: None, + source: Some(Arc::from(source.into())), + backtrace: Arc::new(Backtrace::capture()), } } - fn backtrace(&self) -> Option<&Backtrace> { - use VortexError::*; + /// Wraps an underlying error that does not fit any more specific [`VortexErrorKind`]. + pub fn external(source: E) -> Self + where + E: Into>, + { + Self::wrap(VortexErrorKind::Other, source) + } - match self { - Other(.., bt) => Some(bt.as_ref()), - External(.., bt) => Some(bt.as_ref()), - OutOfBounds(.., bt) => Some(bt.as_ref()), - Compute(.., bt) => Some(bt.as_ref()), - InvalidArgument(.., bt) => Some(bt.as_ref()), - Serde(.., bt) => Some(bt.as_ref()), - NotImplemented(.., bt) => Some(bt.as_ref()), - MismatchedTypes(.., bt) => Some(bt.as_ref()), - AssertionFailed(.., bt) => Some(bt.as_ref()), - Arrow(.., bt) => Some(bt.as_ref()), - #[cfg(feature = "flatbuffers")] - FlatBuffers(.., bt) => Some(bt.as_ref()), - Fmt(.., bt) => Some(bt.as_ref()), - Io(.., bt) => Some(bt.as_ref()), - #[cfg(feature = "object_store")] - ObjectStore(.., bt) => Some(bt.as_ref()), - Jiff(.., bt) => Some(bt.as_ref()), - #[cfg(feature = "tokio")] - Join(.., bt) => Some(bt.as_ref()), - TryFromInt(.., bt) => Some(bt.as_ref()), - Prost(.., bt) => Some(bt.as_ref()), - Context(_, inner) => inner.backtrace(), - Shared(inner) => inner.backtrace(), - } + /// The classification of this error. + pub fn kind(&self) -> VortexErrorKind { + self.kind } - fn message(&self) -> String { - use VortexError::*; + /// Adds additional context to an error, preserving its kind, source and backtrace. + pub fn with_context>(mut self, msg: T) -> Self { + let msg: ErrString = msg.into(); + // Build the combined string directly: `msg` has already been through the + // `VORTEX_PANIC_ON_ERR` check and must not trip it a second time. + self.message = Some(ErrString(Cow::Owned(format!( + "{msg}:\n {}", + self.message_body() + )))); + self + } - match self { - Other(msg, _) => msg.to_string(), - External(err, _) => err.to_string(), - OutOfBounds(idx, start, stop, _) => { - format!("index {idx} out of bounds from {start} to {stop}") - } - Compute(msg, _) | InvalidArgument(msg, _) | Serde(msg, _) | AssertionFailed(msg, _) => { - format!("{msg}") - } - NotImplemented(func, by_whom, _) => { - format!("function {func} not implemented for {by_whom}") - } - MismatchedTypes(expected, actual, _) => { - format!("expected type: {expected} but instead got {actual}") - } - Context(msg, inner) => { - format!("{msg}:\n {inner}") - } - Shared(inner) => inner.message(), - Arrow(err, _) => { - format!("{err}") - } - #[cfg(feature = "flatbuffers")] - FlatBuffers(err, _) => { - format!("{err}") - } - Fmt(err, _) => { - format!("{err}") - } - Io(err, _) => { - format!("{err}") - } - #[cfg(feature = "object_store")] - ObjectStore(err, _) => { - format!("{err}") - } - Jiff(err, _) => { - format!("{err}") - } - #[cfg(feature = "tokio")] - Join(err, _) => { - format!("{err}") - } - TryFromInt(err, _) => { - format!("{err}") - } - Prost(err, _) => { - format!("{err}") - } + /// The error message, falling back to the underlying error when none was provided. + fn message_body(&self) -> Cow<'_, str> { + match (&self.message, &self.source) { + (Some(message), _) => Cow::Borrowed(message.as_ref()), + (None, Some(source)) => Cow::Owned(source.to_string()), + (None, None) => Cow::Borrowed(""), } } } impl Display for VortexError { fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { - write!(f, "{}", self.variant_prefix())?; - write!(f, "{}", self.message())?; - if let Some(backtrace) = self.backtrace() - && backtrace.status() == BacktraceStatus::Captured - { - write!(f, "\nBacktrace:\n{backtrace}")?; + f.write_str(self.kind.prefix())?; + match (&self.message, &self.source) { + (Some(message), _) => Display::fmt(message, f)?, + (None, Some(source)) => Display::fmt(source, f)?, + (None, None) => {} + } + if self.backtrace.status() == BacktraceStatus::Captured { + write!(f, "\nBacktrace:\n{}", self.backtrace)?; } - Ok(()) } } @@ -273,24 +228,9 @@ impl Debug for VortexError { impl Error for VortexError { fn source(&self) -> Option<&(dyn Error + 'static)> { - use VortexError::*; - - match self { - External(err, _) => Some(err.as_ref()), - Context(_, inner) => inner.source(), - Shared(inner) => inner.source(), - Arrow(err, _) => Some(err), - #[cfg(feature = "flatbuffers")] - FlatBuffers(err, _) => Some(err), - Io(err, _) => Some(err), - #[cfg(feature = "object_store")] - ObjectStore(err, _) => Some(err), - Jiff(err, _) => Some(err), - #[cfg(feature = "tokio")] - Join(err, _) => Some(err), - Prost(err, _) => Some(err.as_ref()), - _ => None, - } + self.source + .as_ref() + .map(|source| source.as_ref() as &(dyn Error + 'static)) } } @@ -302,18 +242,13 @@ pub type SharedVortexResult = Result>; impl From> for VortexError { fn from(value: Arc) -> Self { - Self::from(&value) + Arc::try_unwrap(value).unwrap_or_else(|value| (*value).clone()) } } impl From<&Arc> for VortexError { - fn from(e: &Arc) -> Self { - if let VortexError::Shared(e_inner) = e.as_ref() { - // don't re-wrap - VortexError::Shared(Arc::clone(e_inner)) - } else { - VortexError::Shared(Arc::clone(e)) - } + fn from(value: &Arc) -> Self { + (**value).clone() } } @@ -363,45 +298,44 @@ impl VortexExpect for Option { } /// A convenient macro for creating a VortexError. +/// +/// The leading `Kind:` names the [`VortexErrorKind`] and is required: pick the kind that says +/// what went wrong, and `Other` only when none does. Every kind takes the same +/// `Kind: "format", args..` shape, so no kind gets a bespoke argument grammar that a format string +/// could be mistaken for. +/// +/// ``` +/// use vortex_error::{VortexErrorKind, vortex_err}; +/// +/// let err = vortex_err!(InvalidArgument: "negative length {}", -1); +/// assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); +/// ``` +/// +/// A message without a kind does not compile: +/// +/// ```compile_fail +/// let err = vortex_error::vortex_err!("negative length {}", -1); +/// ``` #[macro_export] macro_rules! vortex_err { - (Other: $($tts:tt)*) => { - $crate::__private::fmt_err($crate::VortexError::Other, &format_args!($($tts)*)) - }; - (AssertionFailed: $($tts:tt)*) => { - $crate::__private::fmt_err($crate::VortexError::AssertionFailed, &format_args!($($tts)*)) - }; - (IOError: $($tts:tt)*) => {{ - use std::backtrace::Backtrace; - $crate::__private::must_use( - $crate::VortexError::IOError(err_string.into(), Box::new(Backtrace::capture())) - ) - }}; - (OutOfBounds: $idx:expr, $start:expr, $stop:expr) => { - $crate::__private::out_of_bounds($idx, $start, $stop) - }; - (NotImplemented: $func:expr, $by_whom:expr) => { - $crate::__private::not_implemented($func, &format_args!("{}", $by_whom)) - }; - (MismatchedTypes: $expected:expr, $actual:expr) => { - $crate::__private::mismatched_types(&$expected, &$actual) - }; (Context: $msg:literal, $err:expr) => { $crate::__private::context($msg, $err) }; - (External: $err:expr) => { + (External: $err:expr $(,)?) => { $crate::__private::external($err) }; - ($variant:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { - $crate::__private::fmt_err($crate::VortexError::$variant, &format_args!($fmt $(, $arg)*)) + ($kind:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { + $crate::__private::fmt_err($crate::VortexErrorKind::$kind, &format_args!($fmt $(, $arg)*)) }; - ($variant:ident: $err:expr $(,)?) => { - $crate::__private::must_use( - $crate::VortexError::$variant($err) - ) + ($kind:ident: $err:expr $(,)?) => { + $crate::__private::fmt_err($crate::VortexErrorKind::$kind, &format_args!("{}", $err)) }; - ($fmt:literal $(, $arg:expr)* $(,)?) => { - $crate::vortex_err!(Other: $fmt, $($arg),*) + ($fmt:literal $($rest:tt)*) => { + ::core::compile_error!(::core::concat!( + "vortex_err! needs a kind before its message, e.g. `vortex_err!(InvalidArgument: ", + ::core::stringify!($fmt), + ")`" + )) }; } @@ -415,6 +349,16 @@ macro_rules! vortex_bail { /// A macro that mirrors `assert!` but instead of panicking on a failed condition, /// it will immediately return an erroneous `VortexResult` to the calling context. +/// +/// Without a message the error is an [`VortexErrorKind::AssertionFailed`] naming the condition. A +/// message needs a leading `Kind:`, as in [`vortex_err!`]: +/// +/// ```compile_fail +/// fn check(len: usize) -> vortex_error::VortexResult<()> { +/// vortex_error::vortex_ensure!(len > 0, "length must be positive"); +/// Ok(()) +/// } +/// ``` #[macro_export] macro_rules! vortex_ensure { ($cond:expr) => { @@ -433,7 +377,7 @@ macro_rules! vortex_ensure { /// Both values must implement [`PartialEq`] and [`Display`], and each is /// evaluated exactly once. Use [`vortex_ensure!`] for values that do not implement `Display`. /// -/// By default this returns an [`AssertionFailed`](VortexError::AssertionFailed) error that +/// By default this returns an [`AssertionFailed`](VortexErrorKind::AssertionFailed) error that /// shows both expressions and their values, so most callers do not need a message: /// /// ``` @@ -447,8 +391,23 @@ macro_rules! vortex_ensure { /// assert!(err.starts_with("Assertion failed error: `len == 2`\n left: 3\n right: 2")); /// ``` /// -/// A custom message, optionally prefixed with an error variant, replaces the expressions. The -/// values are still appended, so the message does not need to repeat them: +/// A check on the caller's input, rather than on an internal invariant, names its kind, either +/// alone or before a message: +/// +/// ``` +/// # use vortex_error::{VortexErrorKind, VortexResult, vortex_ensure_eq}; +/// fn check(len: usize) -> VortexResult<()> { +/// vortex_ensure_eq!(len, 2, InvalidArgument); +/// Ok(()) +/// } +/// +/// let err = check(3).unwrap_err(); +/// assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); +/// assert!(err.to_string().starts_with("Invalid argument error: `len == 2`\n left: 3\n right: 2")); +/// ``` +/// +/// A message replaces the expressions. The values are still appended, so the message does not +/// need to repeat them: /// /// ``` /// # use vortex_error::{VortexResult, vortex_ensure_eq}; @@ -462,16 +421,27 @@ macro_rules! vortex_ensure { /// "Invalid argument error: map entries must have 2 fields\n left: 3\n right: 2" /// )); /// ``` +/// +/// Like [`vortex_err!`], a message without a kind does not compile: +/// +/// ```compile_fail +/// fn check(len: usize) -> vortex_error::VortexResult<()> { +/// vortex_error::vortex_ensure_eq!(len, 2, "map entries must have 2 fields"); +/// Ok(()) +/// } +/// ``` #[macro_export] macro_rules! vortex_ensure_eq { ($left:expr, $right:expr $(,)?) => { + $crate::vortex_ensure_eq!($left, $right, AssertionFailed) + }; + ($left:expr, $right:expr, $kind:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { match (&$left, &$right) { (left_val, right_val) => { if *left_val != *right_val { $crate::vortex_bail!( - AssertionFailed: "`{} == {}`\n left: {}\n right: {}", - stringify!($left), - stringify!($right), + $kind: "{}\n left: {}\n right: {}", + format_args!($fmt $(, $arg)*), left_val, right_val ); @@ -479,13 +449,14 @@ macro_rules! vortex_ensure_eq { } } }; - ($left:expr, $right:expr, $variant:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { + ($left:expr, $right:expr, $kind:ident $(,)?) => { match (&$left, &$right) { (left_val, right_val) => { if *left_val != *right_val { $crate::vortex_bail!( - $variant: "{}\n left: {}\n right: {}", - format_args!($fmt $(, $arg)*), + $kind: "`{} == {}`\n left: {}\n right: {}", + stringify!($left), + stringify!($right), left_val, right_val ); @@ -493,73 +464,110 @@ macro_rules! vortex_ensure_eq { } } }; - ($left:expr, $right:expr, $fmt:literal $(, $arg:expr)* $(,)?) => { - $crate::vortex_ensure_eq!($left, $right, Other: $fmt $(, $arg)*) + ($left:expr, $right:expr, $fmt:literal $($rest:tt)*) => { + ::core::compile_error!(::core::concat!( + "vortex_ensure_eq! needs a kind before its message, e.g. `vortex_ensure_eq!(a, b, ", + "InvalidArgument: ", + ::core::stringify!($fmt), + ")`" + )) }; } /// A convenient macro for panicking with a VortexError in the presence of a programmer error /// (e.g., an invariant has been violated). +/// +/// Like [`vortex_err!`], a message needs a leading `Kind:`; an existing error can be passed as is. +/// +/// ```compile_fail +/// vortex_error::vortex_panic!("unreachable state {}", 3); +/// ``` #[macro_export] macro_rules! vortex_panic { - (OutOfBounds: $idx:expr, $start:expr, $stop:expr) => {{ - $crate::vortex_panic!($crate::vortex_err!(OutOfBounds: $idx, $start, $stop)) - }}; - (NotImplemented: $func:expr, $for_whom:expr) => {{ - $crate::vortex_panic!($crate::vortex_err!(NotImplemented: $func, $for_whom)) - }}; - (MismatchedTypes: $expected:literal, $actual:expr) => {{ - $crate::vortex_panic!($crate::vortex_err!(MismatchedTypes: $expected, $actual)) - }}; - (MismatchedTypes: $expected:expr, $actual:expr) => {{ - $crate::vortex_panic!($crate::vortex_err!(MismatchedTypes: $expected, $actual)) - }}; (Context: $msg:literal, $err:expr) => {{ $crate::vortex_panic!($crate::vortex_err!(Context: $msg, $err)) }}; - ($variant:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { - $crate::vortex_panic!($crate::vortex_err!($variant: $fmt, $($arg),*)) + ($kind:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { + $crate::vortex_panic!($crate::vortex_err!($kind: $fmt, $($arg),*)) + }; + // Before the `$err:expr` arms, which a bare message would otherwise match. + ($fmt:literal $($rest:tt)*) => { + ::core::compile_error!(::core::concat!( + "vortex_panic! needs a kind before its message, e.g. `vortex_panic!(AssertionFailed: ", + ::core::stringify!($fmt), + ")`" + )) }; ($err:expr, $fmt:literal $(, $arg:expr)* $(,)?) => { $crate::__private::panic_err_ctx($err, &format_args!($fmt $(, $arg)*)) }; - ($fmt:literal $(, $arg:expr)* $(,)?) => { - $crate::__private::panic_fmt(&format_args!($fmt $(, $arg)*)) - }; ($err:expr) => { $crate::__private::panic_err($err) }; } +impl From for VortexError { + fn from(_: Infallible) -> Self { + unreachable!() + } +} + impl From for VortexError { fn from(value: arrow_schema::ArrowError) -> Self { - VortexError::Arrow(value, Box::new(Backtrace::capture())) + use arrow_schema::ArrowError::*; + let kind = match &value { + NotYetImplemented(_) => VortexErrorKind::NotImplemented, + // A cast or parse Arrow rejects is a value it cannot represent, not a type it + // cannot handle, which is why `int("x")` is a ValueError. + CastError(_) | ParseError(_) | DivideByZero | InvalidArgumentError(_) => { + VortexErrorKind::InvalidArgument + } + SchemaError(_) => VortexErrorKind::MismatchedTypes, + ArithmeticOverflow(_) + | DictionaryKeyOverflowError + | RunEndIndexOverflowError + | OffsetOverflowError(_) => VortexErrorKind::Overflow, + CsvError(_) | JsonError(_) | IpcError(_) | ParquetError(_) | CDataInterface(_) => { + VortexErrorKind::Serde + } + IoError(..) => VortexErrorKind::Io, + AvroError(_) => VortexErrorKind::Serde, + ExternalError(_) | MemoryError(_) | ComputeError(_) => VortexErrorKind::Other, + }; + VortexError::wrap(kind, value) } } #[cfg(feature = "flatbuffers")] impl From for VortexError { fn from(value: flatbuffers::InvalidFlatbuffer) -> Self { - VortexError::FlatBuffers(value, Box::new(Backtrace::capture())) + VortexError::wrap(VortexErrorKind::Serde, value) } } impl From for VortexError { fn from(value: io::Error) -> Self { - VortexError::Io(value, Box::new(Backtrace::capture())) + VortexError::wrap(VortexErrorKind::Io, value) } } #[cfg(feature = "object_store")] impl From for VortexError { fn from(value: object_store::Error) -> Self { - VortexError::ObjectStore(value, Box::new(Backtrace::capture())) + VortexError::wrap(VortexErrorKind::Io, value) } } impl From for VortexError { fn from(value: jiff::Error) -> Self { - VortexError::Jiff(value, Box::new(Backtrace::capture())) + // A date that does not exist and a unit that makes no sense for the call are both what + // Python's datetime raises ValueError for; jiff reports anything else only as text. + let kind = if value.is_range() || value.is_invalid_parameter() { + VortexErrorKind::InvalidArgument + } else { + VortexErrorKind::Other + }; + VortexError::wrap(kind, value) } } @@ -569,32 +577,32 @@ impl From for VortexError { if value.is_panic() { std::panic::resume_unwind(value.into_panic()) } else { - VortexError::Join(value, Box::new(Backtrace::capture())) + VortexError::external(value) } } } impl From for VortexError { fn from(value: TryFromIntError) -> Self { - VortexError::TryFromInt(value, Box::new(Backtrace::capture())) + VortexError::wrap(VortexErrorKind::Overflow, value) } } impl From for VortexError { fn from(value: prost::EncodeError) -> Self { - Self::Prost(Box::new(value), Box::new(Backtrace::capture())) + VortexError::wrap(VortexErrorKind::Serde, value) } } impl From for VortexError { fn from(value: prost::DecodeError) -> Self { - Self::Prost(Box::new(value), Box::new(Backtrace::capture())) + VortexError::wrap(VortexErrorKind::Serde, value) } } impl From for VortexError { fn from(value: prost::UnknownEnumValue) -> Self { - Self::Prost(Box::new(value), Box::new(Backtrace::capture())) + VortexError::wrap(VortexErrorKind::Serde, value) } } @@ -610,13 +618,12 @@ impl From for VortexError { reason = "cold handlers for vortex_panic!/vortex_expect intentionally panic" )] pub mod __private { - use std::backtrace::Backtrace; + use std::error::Error; - use std::fmt; use std::fmt::Arguments; - use crate::ErrString; use crate::VortexError; + use crate::VortexErrorKind; #[doc(hidden)] #[inline] @@ -630,43 +637,8 @@ pub mod __private { #[cold] #[inline(never)] #[must_use] - pub fn fmt_err( - variant: fn(ErrString, Box) -> VortexError, - args: &Arguments<'_>, - ) -> VortexError { - variant(args.to_string().into(), Box::new(Backtrace::capture())) - } - - #[doc(hidden)] - #[cold] - #[inline(never)] - #[must_use] - pub fn out_of_bounds(idx: usize, start: usize, stop: usize) -> VortexError { - VortexError::OutOfBounds(idx, start, stop, Box::new(Backtrace::capture())) - } - - #[doc(hidden)] - #[cold] - #[inline(never)] - #[must_use] - pub fn not_implemented(func: impl Into, by_whom: &Arguments<'_>) -> VortexError { - VortexError::NotImplemented( - func.into(), - by_whom.to_string().into(), - Box::new(Backtrace::capture()), - ) - } - - #[doc(hidden)] - #[cold] - #[inline(never)] - #[must_use] - pub fn mismatched_types(expected: &dyn fmt::Display, actual: &dyn fmt::Display) -> VortexError { - VortexError::MismatchedTypes( - expected.to_string().into(), - actual.to_string().into(), - Box::new(Backtrace::capture()), - ) + pub fn fmt_err(kind: VortexErrorKind, args: &Arguments<'_>) -> VortexError { + VortexError::new(kind, args.to_string()) } #[doc(hidden)] @@ -674,7 +646,7 @@ pub mod __private { #[inline(never)] #[must_use] pub fn context(msg: &'static str, err: VortexError) -> VortexError { - VortexError::Context(msg.into(), Box::new(err)) + err.with_context(msg) } #[doc(hidden)] @@ -682,7 +654,7 @@ pub mod __private { #[inline(never)] #[must_use] pub fn external(err: impl Into>) -> VortexError { - VortexError::External(err.into(), Box::new(Backtrace::capture())) + VortexError::external(err) } #[doc(hidden)] @@ -692,16 +664,6 @@ pub mod __private { panic!("{err}") } - #[doc(hidden)] - #[cold] - #[inline(never)] - pub fn panic_fmt(args: &Arguments<'_>) -> ! { - panic!( - "{}", - VortexError::Other(args.to_string().into(), Box::new(Backtrace::capture())) - ) - } - #[doc(hidden)] #[cold] #[inline(never)] @@ -722,7 +684,7 @@ pub mod __private { pub fn option_expect_failed(msg: &'static str) -> ! { panic!( "{}", - VortexError::AssertionFailed(msg.into(), Box::new(Backtrace::capture())) + VortexError::new(VortexErrorKind::AssertionFailed, msg) ) } } diff --git a/vortex-error/tests/ensure.rs b/vortex-error/tests/ensure.rs index ac13077be49..3fd9369b07c 100644 --- a/vortex-error/tests/ensure.rs +++ b/vortex-error/tests/ensure.rs @@ -8,8 +8,22 @@ mod tests { use std::cell::Cell; use vortex_error::VortexError; + use vortex_error::VortexErrorKind; use vortex_error::VortexResult; + /// Asserts the error's kind and the message shown after its kind prefix. + fn assert_error(error: &VortexError, kind: VortexErrorKind, message: &str) { + assert_eq!(error.kind(), kind, "{error}"); + let shown = error.to_string(); + let body = shown + .split_once(": ") + .map_or(shown.as_str(), |(_, body)| body); + assert!( + body == message || body.starts_with(&format!("{message}\nBacktrace:")), + "{shown:?}" + ); + } + fn check_default(left: &Cell, right: &Cell) -> VortexResult<()> { vortex_error::vortex_ensure_eq!( left.replace(left.get() + 1), @@ -39,12 +53,10 @@ mod tests { assert_eq!(left.get(), 2); assert_eq!(right.get(), 3); - let VortexError::AssertionFailed(message, _) = error else { - panic!("expected AssertionFailed, got {error}"); - }; - assert_eq!( - message.as_ref(), - "`left.replace(left.get() + 1) == right.replace(right.get() + 1)`\n left: 1\n right: 2" + assert_error( + &error, + VortexErrorKind::AssertionFailed, + "`left.replace(left.get() + 1) == right.replace(right.get() + 1)`\n left: 1\n right: 2", ); } @@ -58,7 +70,7 @@ mod tests { vortex_error::vortex_ensure_eq!( &left, right, - "{context} mismatch {}", + InvalidArgument: "{context} mismatch {}", message_calls.replace(message_calls.get() + 1), ); Ok(()) @@ -70,12 +82,10 @@ mod tests { let error = check(&right).unwrap_err(); assert_eq!(message_calls.get(), 1); - let VortexError::Other(message, _) = error else { - panic!("expected Other, got {error}"); - }; - assert_eq!( - message.as_ref(), - "field mismatch 0\n left: left\n right: right" + assert_error( + &error, + VortexErrorKind::InvalidArgument, + "field mismatch 0\n left: left\n right: right", ); assert_eq!(left, "left"); assert_eq!(right, "right"); @@ -91,10 +101,27 @@ mod tests { let error = check().unwrap_err(); - let VortexError::InvalidArgument(message, _) = error else { - panic!("expected InvalidArgument, got {error}"); + assert_error( + &error, + VortexErrorKind::InvalidArgument, + "expected 2 fields\n left: 1\n right: 2", + ); + } + + #[test] + fn kind_without_message_reports_the_values_compared() { + let check = || -> VortexResult<()> { + vortex_error::vortex_ensure_eq!(1 + 1, 3, OutOfBounds); + Ok(()) }; - assert_eq!(message.as_ref(), "expected 2 fields\n left: 1\n right: 2"); + + let error = check().unwrap_err(); + + assert_error( + &error, + VortexErrorKind::OutOfBounds, + "`1 + 1 == 3`\n left: 2\n right: 3", + ); } #[test] @@ -106,9 +133,6 @@ mod tests { let error = check().unwrap_err(); - let VortexError::AssertionFailed(message, _) = error else { - panic!("expected AssertionFailed, got {error}"); - }; - assert_eq!(message.as_ref(), "false"); + assert_error(&error, VortexErrorKind::AssertionFailed, "false"); } } diff --git a/vortex-error/tests/fmt.rs b/vortex-error/tests/fmt.rs index 8aba428a3ff..993ad964bc9 100644 --- a/vortex-error/tests/fmt.rs +++ b/vortex-error/tests/fmt.rs @@ -13,7 +13,7 @@ use vortex_error::vortex_err; #[inline(never)] fn test_basic_display() { temp_env::with_var("RUST_BACKTRACE", Some("1"), || { - let err = vortex_err!("this is bad"); + let err = vortex_err!(Other: "this is bad"); let display = err.to_string(); assert!( @@ -45,8 +45,9 @@ fn test_from_arrow_with_backtrace() { let display = vx_error.to_string(); assert!( - display - .contains("Arrow error: Not yet implemented: This feature isn't implemented yet"), + display.contains( + "Not implemented error: Not yet implemented: This feature isn't implemented yet" + ), "should contain arrow error message" ); assert!( @@ -72,7 +73,7 @@ fn test_from_arrow_no_backtrace() { assert!( display.contains( - "Arrow error: Not yet implemented: This feature isn't implemented yet" + "Not implemented error: Not yet implemented: This feature isn't implemented yet" ), "should contain arrow error message" ); diff --git a/vortex-error/tests/kind.rs b/vortex-error/tests/kind.rs new file mode 100644 index 00000000000..e50a8833b13 --- /dev/null +++ b/vortex-error/tests/kind.rs @@ -0,0 +1,189 @@ +// SPDX-License-Identifier: Apache-2.0 +// SPDX-FileCopyrightText: Copyright the Vortex contributors + +// This seems to be a bug in the lint - https://github.com/rust-lang/rust-clippy/issues/11024 +#![expect(clippy::tests_outside_test_module)] + +use std::error::Error; +use std::io; +use std::sync::Arc; + +use vortex_error::VortexError; +use vortex_error::VortexErrorKind; +use vortex_error::vortex_err; + +#[test] +fn test_other_err_is_other() { + assert_eq!(vortex_err!(Other: "boom").kind(), VortexErrorKind::Other); +} + +#[test] +fn test_tagged_err_carries_kind() { + // Every kind takes the same `Kind: "format", args..` shape. + let cases: [(VortexError, VortexErrorKind); 8] = [ + ( + vortex_err!(InvalidArgument: "bad {}", 1), + VortexErrorKind::InvalidArgument, + ), + ( + vortex_err!(OutOfBounds: "index {} past {}", 5, 3), + VortexErrorKind::OutOfBounds, + ), + ( + vortex_err!(MismatchedTypes: "want i32, got {}", "u8"), + VortexErrorKind::MismatchedTypes, + ), + ( + vortex_err!(NotImplemented: "take on {}", "Sparse"), + VortexErrorKind::NotImplemented, + ), + ( + vortex_err!(NotFound: "no field {}", "a"), + VortexErrorKind::NotFound, + ), + ( + vortex_err!(Overflow: "{} exceeds u32", 1u64 << 40), + VortexErrorKind::Overflow, + ), + (vortex_err!(Serde: "corrupt footer"), VortexErrorKind::Serde), + ( + vortex_err!(AssertionFailed: "invariant broken"), + VortexErrorKind::AssertionFailed, + ), + ]; + for (err, kind) in cases { + assert_eq!(err.kind(), kind, "{err}"); + } +} + +#[test] +fn test_kind_prefixes_the_display() { + assert!( + vortex_err!(NotFound: "no field a") + .to_string() + .starts_with("Not found error: no field a") + ); + assert!( + vortex_err!(Overflow: "too big") + .to_string() + .starts_with("Overflow error: too big") + ); +} + +#[test] +fn test_int_conversion_is_overflow() { + // `?` on a fallible integer cast must land in Overflow, not Other. + let err = VortexError::from(u8::try_from(300u32).unwrap_err()); + assert_eq!(err.kind(), VortexErrorKind::Overflow); +} + +#[test] +fn test_with_context_preserves_kind_and_source() { + let err = VortexError::from(io::Error::other("disk on fire")).with_context("while reading"); + + assert_eq!(err.kind(), VortexErrorKind::Io); + assert!( + err.source() + .and_then(|source| source.downcast_ref::()) + .is_some(), + "context must not hide the underlying error" + ); + + let display = err.to_string(); + assert!( + display.starts_with("IO error: while reading:\n disk on fire"), + "{display}" + ); +} + +#[test] +fn test_nested_context() { + let err = vortex_err!(Serde: "bad footer") + .with_context("reading layout") + .with_context("opening file"); + + assert_eq!(err.kind(), VortexErrorKind::Serde); + let display = err.to_string(); + assert!( + display.starts_with("Serde error: opening file:\n reading layout:\n bad footer"), + "{display}" + ); +} + +#[test] +fn test_external_preserves_concrete_source() { + let err = vortex_err!(External: io::Error::from(io::ErrorKind::NotFound)); + + assert_eq!(err.kind(), VortexErrorKind::Other); + assert_eq!( + err.source() + .and_then(|source| source.downcast_ref::()) + .map(io::Error::kind), + Some(io::ErrorKind::NotFound) + ); +} + +#[test] +fn test_clone_and_shared_round_trip() { + let err = vortex_err!(Io: "device disappeared"); + let clone = err.clone(); + + assert_eq!(clone.kind(), err.kind()); + assert_eq!(clone.to_string(), err.to_string()); + + // An `Arc` is unwrapped when uniquely held and cloned otherwise; both keep the classification. + let shared = Arc::new(err); + let borrowed = VortexError::from(&shared); + let owned = VortexError::from(shared); + + assert_eq!(borrowed.kind(), VortexErrorKind::Io); + assert_eq!(owned.kind(), VortexErrorKind::Io); + assert_eq!(borrowed.to_string(), owned.to_string()); +} + +#[test] +fn test_arrow_error_is_classified_by_variant() { + use arrow_schema::ArrowError; + + let cases = [ + ( + ArrowError::NotYetImplemented("x".into()), + VortexErrorKind::NotImplemented, + ), + ( + ArrowError::ArithmeticOverflow("x".into()), + VortexErrorKind::Overflow, + ), + ( + ArrowError::SchemaError("x".into()), + VortexErrorKind::MismatchedTypes, + ), + ( + ArrowError::IoError("x".into(), io::Error::other("x")), + VortexErrorKind::Io, + ), + (ArrowError::IpcError("x".into()), VortexErrorKind::Serde), + ( + ArrowError::InvalidArgumentError("x".into()), + VortexErrorKind::InvalidArgument, + ), + (ArrowError::ComputeError("x".into()), VortexErrorKind::Other), + ]; + for (arrow, kind) in cases { + let err = VortexError::from(arrow); + assert_eq!(err.kind(), kind, "{err}"); + assert!( + err.source().is_some(), + "the Arrow error is kept as the source" + ); + } +} + +#[test] +fn test_jiff_error_is_classified() { + let no_such_date = jiff::civil::Date::new(2025, 2, 29).unwrap_err(); + assert_eq!( + VortexError::from(no_such_date).kind(), + VortexErrorKind::InvalidArgument + ); +} diff --git a/vortex-expr/src/analysis/referenced_field_paths.rs b/vortex-expr/src/analysis/referenced_field_paths.rs index 55cec7afc5e..185f2455ffe 100644 --- a/vortex-expr/src/analysis/referenced_field_paths.rs +++ b/vortex-expr/src/analysis/referenced_field_paths.rs @@ -84,7 +84,7 @@ impl NodeFolderContext for ReferencedFieldPaths { let child_fields = node.children()[0] .dtype() .as_struct_fields_opt() - .ok_or_else(|| vortex_err!("Select child is not a struct"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Select child is not a struct"))?; let included_fields = selection.normalize_to_included_fields(child_fields.names())?; let mut narrowed = Vec::with_capacity(requested.len()); diff --git a/vortex-expr/src/stats/rewrite.rs b/vortex-expr/src/stats/rewrite.rs index 968fbfad9ba..3a770bbc753 100644 --- a/vortex-expr/src/stats/rewrite.rs +++ b/vortex-expr/src/stats/rewrite.rs @@ -91,7 +91,7 @@ fn ensure_predicate(expr: &BoundExpression) -> VortexResult<()> { let dtype = expr.dtype(); vortex_ensure!( matches!(dtype, DType::Bool(_)), - "Stats rewrites require a boolean predicate, got {dtype}", + MismatchedTypes: "Stats rewrites require a boolean predicate, got {dtype}", ); Ok(()) } diff --git a/vortex-expr/src/transform/bound_partition.rs b/vortex-expr/src/transform/bound_partition.rs index 88ef5287062..d6093c43626 100644 --- a/vortex-expr/src/transform/bound_partition.rs +++ b/vortex-expr/src/transform/bound_partition.rs @@ -138,7 +138,11 @@ where /// Replace the partition expressions and update every root dtype in the recombination tree. pub fn replace_partitions(&mut self, partitions: Box<[BoundExpression]>) -> VortexResult<()> { - vortex_ensure_eq!(partitions.len(), self.partition_names.len()); + vortex_ensure_eq!( + partitions.len(), + self.partition_names.len(), + InvalidArgument + ); let root_dtype = partition_root_dtype(&self.partition_names, &partitions); let root = replace_root_dtype(self.root.clone(), root_dtype)?; diff --git a/vortex-ffi/cinclude/vortex.h b/vortex-ffi/cinclude/vortex.h index dca15d82ee2..f233647fdd2 100644 --- a/vortex-ffi/cinclude/vortex.h +++ b/vortex-ffi/cinclude/vortex.h @@ -218,10 +218,6 @@ typedef enum { * Index out of bounds */ VX_ERROR_CODE_OUT_OF_BOUNDS = 1, - /** - * Compute kernel execute error - */ - VX_ERROR_CODE_COMPUTE = 2, /** * An invalid argument was provided. */ @@ -243,13 +239,21 @@ typedef enum { */ VX_ERROR_CODE_ASSERTION_FAILED = 7, /** - * IO error + * An IO operation, or a call into the operating system or a device driver, failed */ VX_ERROR_CODE_IO = 8, /** * Panic inside FFI */ VX_ERROR_CODE_PANIC = 9, + /** + * A name was looked up and nothing was bound to it + */ + VX_ERROR_CODE_NOT_FOUND = 10, + /** + * A numeric value does not fit its target type + */ + VX_ERROR_CODE_OVERFLOW = 11, } vx_error_code; /** diff --git a/vortex-ffi/examples/hello_vortex.rs b/vortex-ffi/examples/hello_vortex.rs index 93ed17772f1..5b44abfbef7 100644 --- a/vortex-ffi/examples/hello_vortex.rs +++ b/vortex-ffi/examples/hello_vortex.rs @@ -79,7 +79,7 @@ pub fn main() -> VortexResult<()> { println!("C compilation failed:"); println!("Stdout: {}", String::from_utf8_lossy(&output.stdout)); println!("Stderr: {}", String::from_utf8_lossy(&output.stderr)); - return Err(vortex_err!("C compilation failed")); + return Err(vortex_err!(Other: "C compilation failed")); } // Use a fixed path in the working directory instead of temp file @@ -129,7 +129,7 @@ pub fn main() -> VortexResult<()> { println!("✅ FFI example ran successfully! (Exit code issues during cleanup are known)"); } else if !output.status.success() { println!("Command failed with exit code: {:?}", output.status.code()); - return Err(vortex_err!("C binary execution failed")); + return Err(vortex_err!(Other: "C binary execution failed")); } else { println!("✅ Success!"); } diff --git a/vortex-ffi/src/array.rs b/vortex-ffi/src/array.rs index e339215c2e0..c29bd27df21 100644 --- a/vortex-ffi/src/array.rs +++ b/vortex-ffi/src/array.rs @@ -119,7 +119,7 @@ impl vx_bool_view { /// `array` must be null or a valid `vx_array` pointer created by this crate, and must stay valid /// for the returned reference. pub unsafe fn vx_array_ref<'a>(array: *const vx_array) -> VortexResult<&'a ArrayRef> { - vortex_ensure!(!array.is_null(), "null vx_array"); + vortex_ensure!(!array.is_null(), InvalidArgument: "null vx_array"); Ok(vx_array::as_ref(array)) } @@ -275,14 +275,14 @@ pub unsafe extern "C-unwind" fn vx_array_get_field( let array = vx_array::as_ref(array); let struct_array = array.as_opt::().ok_or_else(|| { vortex_err!( - "vx_array_get_field requires a canonical Struct array, got {}", + MismatchedTypes: "vx_array_get_field requires a canonical Struct array, got {}", array.encoding_id() ) })?; let field_array = struct_array .unmasked_field_opt(index) - .ok_or_else(|| vortex_err!("Field index out of bounds"))? + .ok_or_else(|| vortex_err!(OutOfBounds: "Field index out of bounds"))? .clone(); Ok(vx_array::new(field_array)) @@ -454,11 +454,11 @@ pub extern "C-unwind" fn vx_array_new_bool( vortex_ensure!(!validity.is_null()); let bits = unsafe { &*view }; let validity = unsafe { &*validity }; - vortex_ensure!(bits.bit_offset < 8, "bit_offset must be in [0; 8)"); + vortex_ensure!(bits.bit_offset < 8, InvalidArgument: "bit_offset must be in [0; 8)"); let byte_len = bits.len(); let slice = if bits.ptr.is_null() { - vortex_ensure_eq!(byte_len, 0, "nonzero length but null pointer for view"); + vortex_ensure_eq!(byte_len, 0, InvalidArgument: "nonzero length but null pointer for view"); &[] } else { unsafe { std::slice::from_raw_parts(bits.ptr, byte_len) } @@ -498,8 +498,8 @@ pub unsafe extern "C-unwind" fn vx_array_from_arrow( error_out: *mut *mut vx_error, ) -> *const vx_array { try_or_default(error_out, || { - vortex_ensure!(!array.is_null(), "null arrow array"); - vortex_ensure!(!schema.is_null(), "null arrow schema"); + vortex_ensure!(!array.is_null(), InvalidArgument: "null arrow array"); + vortex_ensure!(!schema.is_null(), InvalidArgument: "null arrow schema"); let session = vx_session::as_ref(session); let ffi_array = unsafe { ptr::replace(array, FFI_ArrowArray::empty()) }; let ffi_schema = unsafe { ptr::replace(schema, FFI_ArrowSchema::empty()) }; @@ -521,7 +521,7 @@ unsafe fn varbinview_at( ) -> vx_view { try_or(error_out, vx_view::null(), || { let array = unsafe { vx_array_ref(array) }?; - vortex_ensure!(index < array.len(), "index {index} out of bounds"); + vortex_ensure!(index < array.len(), OutOfBounds: "index {index} out of bounds"); let dtype_matches = if want_utf8 { matches!(array.dtype(), DType::Utf8(_)) } else { @@ -529,12 +529,12 @@ unsafe fn varbinview_at( }; vortex_ensure!( dtype_matches, - "expected a {} array, got {}", + MismatchedTypes: "expected a {} array, got {}", if want_utf8 { "Utf8" } else { "Binary" }, array.dtype() ); let Some(views) = array.as_opt::() else { - vortex_bail!("expected a canonical array, got {}", array.encoding_id()); + vortex_bail!(MismatchedTypes: "expected a canonical array, got {}", array.encoding_id()); }; Ok(vx_view::from_bytes(views.bytes_at(index).as_slice())) }) @@ -586,7 +586,7 @@ pub unsafe extern "C-unwind" fn vx_array_get_bool(array: *const vx_array, index: let bits = bool_array.to_bit_buffer(); if index >= bits.len() { vortex_panic!( - "index {index} out of bounds for array of length {}", + OutOfBounds: "index {index} out of bounds for array of length {}", bits.len() ); } @@ -648,14 +648,14 @@ pub unsafe extern "C-unwind" fn vx_array_data_ptr_primitive( let array = vx_array::as_ref(array); let primitive = array.as_opt::().ok_or_else(|| { vortex_err!( - "vx_array_data_ptr_primitive requires a canonical Primitive array, got {}", + InvalidArgument: "vx_array_data_ptr_primitive requires a canonical Primitive array, got {}", array.encoding_id() ) })?; let bytes = primitive .buffer_handle() .as_host_opt() - .ok_or_else(|| vortex_err!("array buffer is not in host memory"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "array buffer is not in host memory"))?; Ok(bytes.as_ptr().cast()) }) } @@ -686,7 +686,7 @@ pub unsafe extern "C-unwind" fn vx_array_data_ptr_bool( let array = unsafe { vx_array_ref(array) }?; let array = array.as_opt::().ok_or_else(|| { let id = array.encoding_id(); - vortex_err!("vx_array_data_ptr_bool requires a canonical Bool array, got {id}") + vortex_err!(InvalidArgument: "vx_array_data_ptr_bool requires a canonical Bool array, got {id}") })?; let bits = array.to_bit_buffer(); let ptr = bits.inner().as_ptr().cast(); diff --git a/vortex-ffi/src/data_source.rs b/vortex-ffi/src/data_source.rs index a881b3ac085..cc66df2470e 100644 --- a/vortex-ffi/src/data_source.rs +++ b/vortex-ffi/src/data_source.rs @@ -110,7 +110,7 @@ unsafe fn data_source_new( let opts = unsafe { &*opts }; vortex_ensure!(!opts.paths.is_null()); - vortex_ensure!(opts.paths_len > 0, "empty paths"); + vortex_ensure!(opts.paths_len > 0, InvalidArgument: "empty paths"); let paths = unsafe { slice::from_raw_parts(opts.paths, opts.paths_len) }; let mut data_source = MultiFileDataSource::new(session.clone()); diff --git a/vortex-ffi/src/dtype.rs b/vortex-ffi/src/dtype.rs index e0dc2467914..4875a0e7bf8 100644 --- a/vortex-ffi/src/dtype.rs +++ b/vortex-ffi/src/dtype.rs @@ -74,9 +74,11 @@ impl From<&DType> for vx_dtype_variant { DType::List(..) => vx_dtype_variant::DTYPE_LIST, DType::FixedSizeList(..) => vx_dtype_variant::DTYPE_FIXED_SIZE_LIST, DType::Struct(..) => vx_dtype_variant::DTYPE_STRUCT, - DType::Map(..) => vortex_panic!("Map is not supported in FFI yet"), - DType::Union(..) => vortex_panic!("Union is not supported in FFI yet"), - DType::Variant(_) => vortex_panic!("Variant is not supported in FFI yet"), + DType::Map(..) => vortex_panic!(NotImplemented: "Map is not supported in FFI yet"), + DType::Union(..) => vortex_panic!(NotImplemented: "Union is not supported in FFI yet"), + DType::Variant(_) => { + vortex_panic!(NotImplemented: "Variant is not supported in FFI yet") + } DType::Extension(_) => vx_dtype_variant::DTYPE_EXTENSION, } } @@ -253,7 +255,7 @@ pub unsafe extern "C-unwind" fn vx_dtype_fixed_size_list_size(dtype: *const vx_d let dtype_ref = vx_dtype::as_ref(dtype); match dtype_ref { DType::FixedSizeList(_, size, _) => *size, - _ => vortex_panic!("not a fixed-size list dtype"), + _ => vortex_panic!(MismatchedTypes: "not a fixed-size list dtype"), } } @@ -294,7 +296,7 @@ pub unsafe extern "C-unwind" fn vx_dtype_from_arrow_schema( err: *mut *mut vx_error, ) -> *const vx_dtype { try_or_default(err, || { - vortex_ensure!(!schema.is_null(), "null arrow schema"); + vortex_ensure!(!schema.is_null(), InvalidArgument: "null arrow schema"); let session = vx_session::as_ref(session); let ffi_schema = unsafe { ptr::replace(schema, FFI_ArrowSchema::empty()) }; let arrow_schema = Schema::try_from(&ffi_schema)?; diff --git a/vortex-ffi/src/error.rs b/vortex-ffi/src/error.rs index 8f13a699e59..f63a73bf932 100644 --- a/vortex-ffi/src/error.rs +++ b/vortex-ffi/src/error.rs @@ -8,6 +8,7 @@ use std::ptr; use std::sync::Arc; use vortex::error::VortexError; +use vortex::error::VortexErrorKind; use vortex::error::VortexResult; use crate::box_wrapper; @@ -21,8 +22,8 @@ pub enum vx_error_code { VX_ERROR_CODE_OTHER = 0, /// Index out of bounds VX_ERROR_CODE_OUT_OF_BOUNDS = 1, - /// Compute kernel execute error - VX_ERROR_CODE_COMPUTE = 2, + // 2 is retired. It was VX_ERROR_CODE_COMPUTE, which classified an error by the code it came + // from rather than by what went wrong. Leaving the value unused keeps every code below stable. /// An invalid argument was provided. VX_ERROR_CODE_INVALID_ARGUMENT = 3, /// Serialization/deserialization error @@ -33,24 +34,27 @@ pub enum vx_error_code { VX_ERROR_CODE_MISMATCHED_TYPES = 6, /// Assertion failed VX_ERROR_CODE_ASSERTION_FAILED = 7, - /// IO error + /// An IO operation, or a call into the operating system or a device driver, failed VX_ERROR_CODE_IO = 8, /// Panic inside FFI VX_ERROR_CODE_PANIC = 9, + /// A name was looked up and nothing was bound to it + VX_ERROR_CODE_NOT_FOUND = 10, + /// A numeric value does not fit its target type + VX_ERROR_CODE_OVERFLOW = 11, } fn error_code(error: &VortexError) -> vx_error_code { - match error { - VortexError::OutOfBounds(..) => vx_error_code::VX_ERROR_CODE_OUT_OF_BOUNDS, - VortexError::Compute(..) => vx_error_code::VX_ERROR_CODE_COMPUTE, - VortexError::InvalidArgument(..) => vx_error_code::VX_ERROR_CODE_INVALID_ARGUMENT, - VortexError::Serde(..) => vx_error_code::VX_ERROR_CODE_SERIALIZATION, - VortexError::NotImplemented(..) => vx_error_code::VX_ERROR_CODE_NOT_IMPLEMENTED, - VortexError::MismatchedTypes(..) => vx_error_code::VX_ERROR_CODE_MISMATCHED_TYPES, - VortexError::AssertionFailed(..) => vx_error_code::VX_ERROR_CODE_ASSERTION_FAILED, - VortexError::Io(..) => vx_error_code::VX_ERROR_CODE_IO, - VortexError::Context(_, inner) => error_code(inner), - VortexError::Shared(inner) => error_code(inner), + match error.kind() { + VortexErrorKind::OutOfBounds => vx_error_code::VX_ERROR_CODE_OUT_OF_BOUNDS, + VortexErrorKind::NotFound => vx_error_code::VX_ERROR_CODE_NOT_FOUND, + VortexErrorKind::Overflow => vx_error_code::VX_ERROR_CODE_OVERFLOW, + VortexErrorKind::InvalidArgument => vx_error_code::VX_ERROR_CODE_INVALID_ARGUMENT, + VortexErrorKind::Serde => vx_error_code::VX_ERROR_CODE_SERIALIZATION, + VortexErrorKind::NotImplemented => vx_error_code::VX_ERROR_CODE_NOT_IMPLEMENTED, + VortexErrorKind::MismatchedTypes => vx_error_code::VX_ERROR_CODE_MISMATCHED_TYPES, + VortexErrorKind::AssertionFailed => vx_error_code::VX_ERROR_CODE_ASSERTION_FAILED, + VortexErrorKind::Io => vx_error_code::VX_ERROR_CODE_IO, _ => vx_error_code::VX_ERROR_CODE_OTHER, } } @@ -188,14 +192,17 @@ mod tests { fn test_try_or_null_error_out() { // A null error_out must be tolerated on both the success and failure paths. assert_eq!(try_or(ptr::null_mut(), -1, || Ok(42)), 42); - assert_eq!(try_or(ptr::null_mut(), -1, || Err(vortex_err!("boom"))), -1); + assert_eq!( + try_or(ptr::null_mut(), -1, || Err(vortex_err!(Other: "boom"))), + -1 + ); } #[test] fn test_try_or_default_null_error_out() { assert_eq!(try_or_default(ptr::null_mut(), || Ok(42)), 42); assert_eq!( - try_or_default::(ptr::null_mut(), || Err(vortex_err!("boom"))), + try_or_default::(ptr::null_mut(), || Err(vortex_err!(Other: "boom"))), 0 ); } @@ -204,7 +211,10 @@ mod tests { fn test_try_or_writes_and_clears_error_out() { let mut error: *mut vx_error = ptr::null_mut(); - assert_eq!(try_or(&raw mut error, -1, || Err(vortex_err!("boom"))), -1); + assert_eq!( + try_or(&raw mut error, -1, || Err(vortex_err!(Other: "boom"))), + -1 + ); assert!(!error.is_null()); unsafe { vx_error_free(error) }; @@ -232,8 +242,7 @@ mod tests { assert_eq!( try_or(&raw mut error, -1, || Err::(vortex_err!( - OutOfBounds: 5, 0, 3 - ))), + OutOfBounds: "index {} out of bounds from {} to {}", 5, 0, 3))), -1 ); assert_eq!( diff --git a/vortex-ffi/src/lib.rs b/vortex-ffi/src/lib.rs index b0168851911..bc9cf136cd4 100644 --- a/vortex-ffi/src/lib.rs +++ b/vortex-ffi/src/lib.rs @@ -108,7 +108,7 @@ macro_rules! box_wrapper { /// Extract an owned reference. pub(crate) fn into_box(ptr: *mut $ffi_ident) -> Box<$T>{ if ptr.is_null() { - vortex::error::vortex_panic!("null pointer"); + vortex::error::vortex_panic!(InvalidArgument: "null pointer"); } unsafe { Box::from_raw(ptr.cast::<$T>()) } } @@ -173,7 +173,7 @@ pub(crate) unsafe fn to_field_names( names: *const vx_view, len: usize, ) -> VortexResult> { - vortex_ensure!(!names.is_null() || len == 0, "null names pointer"); + vortex_ensure!(!names.is_null() || len == 0, InvalidArgument: "null names pointer"); (0..len) .map(|i| unsafe { to_field_name(*names.add(i)) }) .collect() diff --git a/vortex-ffi/src/scalar.rs b/vortex-ffi/src/scalar.rs index d9c22083667..d5ae5833a85 100644 --- a/vortex-ffi/src/scalar.rs +++ b/vortex-ffi/src/scalar.rs @@ -245,13 +245,13 @@ pub unsafe extern "C-unwind" fn vx_scalar_new_extension( let storage = vx_scalar::as_ref(storage); let DType::Extension(ext) = dtype else { vortex_bail!( - "vx_scalar_new_extension: dtype {} is not an extension type", + MismatchedTypes: "vx_scalar_new_extension: dtype {} is not an extension type", dtype ); }; vortex_ensure!( storage.dtype().eq_ignore_nullability(ext.storage_dtype()), - "vx_scalar_new_extension: storage scalar dtype {} does not match extension storage dtype {}", + MismatchedTypes: "vx_scalar_new_extension: storage scalar dtype {} does not match extension storage dtype {}", storage.dtype(), ext.storage_dtype() ); @@ -422,7 +422,7 @@ pub unsafe extern "C-unwind" fn vx_scalar_new_struct( err: *mut *mut vx_error, ) -> *mut vx_scalar { try_or(err, ptr::null_mut(), || { - vortex_ensure!(!struct_dtype.is_null(), "struct dtype is null"); + vortex_ensure!(!struct_dtype.is_null(), InvalidArgument: "struct dtype is null"); let values = scalar_values_from_raw(fields, len)?; Ok(vx_scalar::new(Scalar::try_new( vx_dtype::as_ref(struct_dtype).clone(), @@ -451,14 +451,14 @@ fn scalar_values_from_raw( if len == 0 { return Ok(Vec::new()); } - vortex_ensure!(!values.is_null(), "scalar pointer array is null"); + vortex_ensure!(!values.is_null(), InvalidArgument: "scalar pointer array is null"); unsafe { slice::from_raw_parts(values, len) } .iter() .enumerate() .map(|(idx, value)| { if value.is_null() { - vortex_bail!("scalar pointer at index {idx} is null"); + vortex_bail!(InvalidArgument: "scalar pointer at index {idx} is null"); } Ok(vx_scalar::as_ref(*value).clone().into_value()) }) @@ -469,12 +469,12 @@ fn bytes_from_raw<'a>(ptr: *const u8, len: usize, label: &str) -> VortexResult<& if len == 0 { return Ok(&[]); } - vortex_ensure!(!ptr.is_null(), "{label} data pointer is null"); + vortex_ensure!(!ptr.is_null(), InvalidArgument: "{label} data pointer is null"); Ok(unsafe { slice::from_raw_parts(ptr, len) }) } fn fixed_bytes_from_raw(ptr: *const u8, label: &str) -> VortexResult<[u8; N]> { - vortex_ensure!(!ptr.is_null(), "{label} data pointer is null"); + vortex_ensure!(!ptr.is_null(), InvalidArgument: "{label} data pointer is null"); let mut bytes = [0u8; N]; bytes.copy_from_slice(unsafe { slice::from_raw_parts(ptr, N) }); Ok(bytes) diff --git a/vortex-ffi/src/scan.rs b/vortex-ffi/src/scan.rs index b58caddfb69..80b6e5bc842 100644 --- a/vortex-ffi/src/scan.rs +++ b/vortex-ffi/src/scan.rs @@ -79,10 +79,10 @@ box_wrapper!( pub unsafe fn vx_partition_into_array_stream( partition: *mut vx_partition, ) -> VortexResult { - vortex_ensure!(!partition.is_null(), "null vx_partition"); + vortex_ensure!(!partition.is_null(), InvalidArgument: "null vx_partition"); match *vx_partition::into_box(partition) { VxPartitionScan::Pending(partition) => partition.execute(), - _ => vortex_bail!("partition already being consumed"), + _ => vortex_bail!(InvalidArgument: "partition already being consumed"), } } @@ -269,7 +269,7 @@ pub unsafe extern "C-unwind" fn vx_scan_dtype( try_or(err, ptr::null(), || { let scan = vx_scan::as_ref(scan); let VxScan::Pending(scan) = scan else { - vortex_bail!("dtype unavailable: scan already started"); + vortex_bail!(InvalidArgument: "dtype unavailable: scan already started"); }; Ok(vx_dtype::new(scan.dtype().clone())) }) @@ -335,7 +335,7 @@ pub unsafe extern "C-unwind" fn vx_partition_row_count( try_or(err, 1, || { let partition = vx_partition::as_ref(partition); let VxPartitionScan::Pending(partition) = partition else { - vortex_bail!("row count unavailable: partition already started"); + vortex_bail!(InvalidArgument: "row count unavailable: partition already started"); }; write_estimate(partition.row_count(), unsafe { &mut *count }); Ok(0) @@ -362,7 +362,7 @@ pub unsafe extern "C-unwind" fn vx_partition_scan_arrow( let partition = match *vx_partition::into_box(partition) { VxPartitionScan::Pending(partition) => partition, _ => vortex_bail!( - "Can't consume partition into ArrowArrayStream: partition already being consumed" + InvalidArgument: "Can't consume partition into ArrowArrayStream: partition already being consumed" ), }; let array_stream = partition.execute()?; diff --git a/vortex-ffi/src/session.rs b/vortex-ffi/src/session.rs index f0679a7c4c9..cc66474bf63 100644 --- a/vortex-ffi/src/session.rs +++ b/vortex-ffi/src/session.rs @@ -50,7 +50,7 @@ pub unsafe extern "C-unwind" fn vx_session_clone(session: *const vx_session) -> /// `session` must be null or a valid `vx_session` pointer created by this crate, and must stay /// valid for the returned reference. pub unsafe fn vx_session_ref<'a>(session: *const vx_session) -> VortexResult<&'a VortexSession> { - vortex_ensure!(!session.is_null(), "null vx_session"); + vortex_ensure!(!session.is_null(), InvalidArgument: "null vx_session"); Ok(vx_session::as_ref(session)) } diff --git a/vortex-ffi/src/sink.rs b/vortex-ffi/src/sink.rs index f7cd88d7de9..7c9168253fd 100644 --- a/vortex-ffi/src/sink.rs +++ b/vortex-ffi/src/sink.rs @@ -69,7 +69,7 @@ pub unsafe fn vx_array_sink_open_file_with_strategy( let session = vx_session::as_ref(session).clone(); if path.ptr.is_null() { - vortex_bail!("null path"); + vortex_bail!(InvalidArgument: "null path"); } let path = unsafe { path.as_str() }?.to_string(); @@ -129,10 +129,10 @@ pub unsafe extern "C-unwind" fn vx_array_sink_push( let array = vx_array::as_ref(array); let sink = unsafe { &mut *sink }; - vortex_ensure_eq!(*array.dtype(), sink.dtype); + vortex_ensure_eq!(*array.dtype(), sink.dtype, MismatchedTypes); RUNTIME .block_on(sink.sink.send(Ok(array.clone()))) - .map_err(|e| vortex_err!("Send error: {e}")) + .map_err(|e| vortex_err!(Io: "Send error: {e}")) }) } diff --git a/vortex-ffi/src/string.rs b/vortex-ffi/src/string.rs index 5585e7f0a5c..96e4904f056 100644 --- a/vortex-ffi/src/string.rs +++ b/vortex-ffi/src/string.rs @@ -51,7 +51,7 @@ impl vx_view { /// "ptr" must be valid for "len" reads or NULL with "len == 0". pub(crate) unsafe fn as_bytes<'a>(&self) -> VortexResult<&'a [u8]> { if self.ptr.is_null() { - vortex_ensure_eq!(self.len, 0, "null vx_view pointer with non-zero length"); + vortex_ensure_eq!(self.len, 0, InvalidArgument: "null vx_view pointer with non-zero length"); return Ok(&[]); } Ok(unsafe { slice::from_raw_parts(self.ptr.cast(), self.len) }) @@ -63,7 +63,8 @@ impl vx_view { /// /// `self.ptr` must be valid for `self.len` reads, or null when `self.len` is zero. pub unsafe fn as_str<'a>(&self) -> VortexResult<&'a str> { - str::from_utf8(unsafe { self.as_bytes() }?).map_err(|e| vortex_err!("invalid utf-8: {e}")) + str::from_utf8(unsafe { self.as_bytes() }?) + .map_err(|e| vortex_err!(InvalidArgument: "invalid utf-8: {e}")) } } diff --git a/vortex-ffi/src/struct_array.rs b/vortex-ffi/src/struct_array.rs index e1c00877866..f0c382dfe92 100644 --- a/vortex-ffi/src/struct_array.rs +++ b/vortex-ffi/src/struct_array.rs @@ -73,7 +73,7 @@ pub unsafe extern "C" fn vx_struct_column_builder_add_field( if !builder.fields.is_empty() && field.len() != builder.fields[0].len() { vortex_bail!( - "Field length mismatch: expected {}, got {}", + MismatchedTypes: "Field length mismatch: expected {}, got {}", builder.fields[0].len(), field.len() ); diff --git a/vortex-file/src/footer/deserializer.rs b/vortex-file/src/footer/deserializer.rs index 77320ef2204..3eee70d5c74 100644 --- a/vortex-file/src/footer/deserializer.rs +++ b/vortex-file/src/footer/deserializer.rs @@ -119,7 +119,7 @@ impl FooterDeserializer { .then(|| { postscript.dtype.as_ref().ok_or_else(|| { vortex_err!( - "Vortex file doesn't embed a DType and none provided to VortexOpenOptions" + Serde: "Vortex file doesn't embed a DType and none provided to VortexOpenOptions" ) }) }) @@ -136,7 +136,7 @@ impl FooterDeserializer { .checked_sub(self.buffer.len() as u64) .ok_or_else(|| { vortex_err!( - "Footer buffer length {} exceeds declared file size {file_size}", + Serde: "Footer buffer length {} exceeds declared file size {file_size}", self.buffer.len() ) })?; @@ -193,11 +193,11 @@ impl FooterDeserializer { .offset .checked_add(u64::from(segment.length)) .ok_or_else(|| { - vortex_err!("Metadata segment {} range overflowed u64", metadata.key) + vortex_err!(Overflow: "Metadata segment {} range overflowed u64", metadata.key) })?; if end > file_size { vortex_bail!( - "Metadata segment {} range {}..{} exceeds file size {}", + Serde: "Metadata segment {} range {}..{} exceeds file size {}", metadata.key, segment.offset, end, @@ -207,7 +207,7 @@ impl FooterDeserializer { let offset = usize::try_from(segment.offset)?; if !segment.alignment.is_offset_aligned(offset) { vortex_bail!( - "Metadata segment {} offset {} is not aligned to {}", + Serde: "Metadata segment {} offset {} is not aligned to {}", metadata.key, segment.offset, segment.alignment @@ -236,7 +236,7 @@ impl FooterDeserializer { fn parse_postscript(&self, initial_read: &[u8]) -> VortexResult { if initial_read.len() < EOF_SIZE { vortex_bail!( - "Initial read must be at least EOF_SIZE ({}) bytes", + InvalidArgument: "Initial read must be at least EOF_SIZE ({}) bytes", EOF_SIZE ); } @@ -245,27 +245,27 @@ impl FooterDeserializer { let magic_number = &initial_read[magic_bytes_loc..]; if magic_number != MAGIC_BYTES { - vortex_bail!("Malformed file, invalid magic bytes, got {magic_number:?}") + vortex_bail!(Serde: "Malformed file, invalid magic bytes, got {magic_number:?}") } let version = u16::from_le_bytes( initial_read[eof_loc..eof_loc + 2] .try_into() - .map_err(|e| vortex_err!("Version was not a u16 {e}"))?, + .map_err(|e| vortex_err!(Serde: "Version was not a u16 {e}"))?, ); if version != VERSION { - vortex_bail!("Malformed file, unsupported version {version}") + vortex_bail!(Serde: "Malformed file, unsupported version {version}") } let ps_size = u16::from_le_bytes( initial_read[eof_loc + 2..eof_loc + 4] .try_into() - .map_err(|e| vortex_err!("Postscript size was not a u16 {e}"))?, + .map_err(|e| vortex_err!(Serde: "Postscript size was not a u16 {e}"))?, ) as usize; if initial_read.len() < ps_size + EOF_SIZE { vortex_bail!( - "Initial read must be at least {} bytes to include the Postscript", + InvalidArgument: "Initial read must be at least {} bytes to include the Postscript", ps_size + EOF_SIZE ); } @@ -341,7 +341,7 @@ fn checked_segment_slice<'a>( ) -> VortexResult<&'a [u8]> { let offset = usize::try_from(segment.offset.checked_sub(read_offset).ok_or_else(|| { vortex_err!( - "Segment offset {} is smaller than file read offset {read_offset}", + Serde: "Segment offset {} is smaller than file read offset {read_offset}", segment.offset ) })?)?; @@ -350,7 +350,7 @@ fn checked_segment_slice<'a>( .and_then(|end| read.get(offset..end)) .ok_or_else(|| { vortex_err!( - "Segment length {} (at offset {}) out of bounds of slice of length {}", + OutOfBounds: "Segment length {} (at offset {}) out of bounds of slice of length {}", segment.length, offset, read.len() diff --git a/vortex-file/src/footer/field_sizes.rs b/vortex-file/src/footer/field_sizes.rs index afd47353d5b..481f3132a3c 100644 --- a/vortex-file/src/footer/field_sizes.rs +++ b/vortex-file/src/footer/field_sizes.rs @@ -72,7 +72,7 @@ impl CompressedFieldSizes { for (segment_id, path) in attribution { let segment = segments.get(*segment_id as usize).ok_or_else(|| { vortex_err!( - "layout references missing segment {} (segment count: {})", + NotFound: "layout references missing segment {} (segment count: {})", *segment_id, segments.len() ) diff --git a/vortex-file/src/footer/mod.rs b/vortex-file/src/footer/mod.rs index 57be23ec74e..c11ddb25e5e 100644 --- a/vortex-file/src/footer/mod.rs +++ b/vortex-file/src/footer/mod.rs @@ -147,14 +147,14 @@ impl Footer { let segments: Arc<[SegmentSpec]> = fb_footer .segment_specs() - .ok_or_else(|| vortex_err!("FileLayout missing segment specs"))? + .ok_or_else(|| vortex_err!(NotFound: "FileLayout missing segment specs"))? .iter() .map(SegmentSpec::try_from) .try_collect()?; // Note this assertion is `<=` since we allow zero-length segments if !segments.is_sorted_by_key(|segment| segment.offset) { - vortex_bail!("Segment offsets are not ordered"); + vortex_bail!(Serde: "Segment offsets are not ordered"); } let segments_with_metadata = segments_with_metadata(&segments, &metadata); @@ -288,7 +288,7 @@ fn validate_segments_within_file(segments: &[SegmentSpec], file_size: u64) -> Vo .is_some_and(|end| end <= file_size); if !within_file { vortex_bail!( - "Segment at offset {} with length {} extends past the end of the \ + OutOfBounds: "Segment at offset {} with length {} extends past the end of the \ {file_size}-byte file", segment.offset, segment.length, diff --git a/vortex-file/src/footer/postscript.rs b/vortex-file/src/footer/postscript.rs index 863b7da303e..ae195220800 100644 --- a/vortex-file/src/footer/postscript.rs +++ b/vortex-file/src/footer/postscript.rs @@ -116,7 +116,7 @@ impl ReadFlatBuffer for Postscript { .transpose()?, layout: PostscriptSegment::read_flatbuffer( &fb.layout() - .ok_or_else(|| vortex_err!("Postscript missing layout segment"))?, + .ok_or_else(|| vortex_err!(NotFound: "Postscript missing layout segment"))?, )?, statistics: fb .statistics() @@ -124,7 +124,7 @@ impl ReadFlatBuffer for Postscript { .transpose()?, footer: PostscriptSegment::read_flatbuffer( &fb.footer() - .ok_or_else(|| vortex_err!("Postscript missing footer segment"))?, + .ok_or_else(|| vortex_err!(Serde: "Postscript missing footer segment"))?, )?, metadata, }) @@ -149,7 +149,7 @@ fn validate_metadata_entries(metadata: &[PostscriptMetadata]) -> VortexResult<() fn metadata_count_error(metadata_len: usize) -> VortexError { vortex_err!( - "Postscript contains {} metadata segments, but Vortex supports at most {} metadata segments; metadata keys must be non-empty and at most {} bytes", + InvalidArgument: "Postscript contains {} metadata segments, but Vortex supports at most {} metadata segments; metadata keys must be non-empty and at most {} bytes", metadata_len, MAX_METADATA_SEGMENTS, MAX_METADATA_KEY_BYTES @@ -158,7 +158,7 @@ fn metadata_count_error(metadata_len: usize) -> VortexError { fn duplicate_metadata_key_error(key: &str) -> VortexError { vortex_err!( - "Postscript contains duplicate metadata key {key}; metadata keys must be unique, non-empty, and at most {} bytes, and files may contain at most {} metadata segments", + InvalidArgument: "Postscript contains duplicate metadata key {key}; metadata keys must be unique, non-empty, and at most {} bytes, and files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS ) @@ -167,7 +167,7 @@ fn duplicate_metadata_key_error(key: &str) -> VortexError { fn validate_metadata_key(key: &str) -> VortexResult<()> { if key.is_empty() { return Err(vortex_err!( - "Postscript metadata key must not be empty; metadata keys must be at most {} bytes and files may contain at most {} metadata segments", + InvalidArgument: "Postscript metadata key must not be empty; metadata keys must be at most {} bytes and files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS )); @@ -176,7 +176,7 @@ fn validate_metadata_key(key: &str) -> VortexResult<()> { let key_bytes = key.len(); if key_bytes > MAX_METADATA_KEY_BYTES { return Err(vortex_err!( - "Postscript metadata key {key:?} is {key_bytes} bytes, but metadata keys must be at most {} bytes and files may contain at most {} metadata segments", + InvalidArgument: "Postscript metadata key {key:?} is {key_bytes} bytes, but metadata keys must be at most {} bytes and files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS )); diff --git a/vortex-file/src/footer/serializer.rs b/vortex-file/src/footer/serializer.rs index 6997c1d30b0..06ce54669a0 100644 --- a/vortex-file/src/footer/serializer.rs +++ b/vortex-file/src/footer/serializer.rs @@ -176,7 +176,7 @@ impl FooterSerializer { let postscript_buffer = postscript.write_flatbuffer_bytes()?; if postscript_buffer.len() > MAX_POSTSCRIPT_SIZE as usize { Err(vortex_err!( - "Postscript is too large ({} bytes); max postscript size is {}", + Overflow: "Postscript is too large ({} bytes); max postscript size is {}", postscript_buffer.len(), MAX_POSTSCRIPT_SIZE ))?; @@ -225,7 +225,7 @@ fn write_flatbuffer( ) -> VortexResult<(ByteBuffer, PostscriptSegment)> { let buffer = flatbuffer.write_flatbuffer_bytes()?; let length = u32::try_from(buffer.len()) - .map_err(|_| vortex_err!("flatbuffer length exceeds maximum u32"))?; + .map_err(|_| vortex_err!(Serde: "flatbuffer length exceeds maximum u32"))?; let segment = PostscriptSegment { offset: *offset, @@ -243,7 +243,7 @@ fn write_buffer( buffer: ByteBuffer, ) -> VortexResult<(Vec, PostscriptSegment)> { let length = u32::try_from(buffer.len()) - .map_err(|_| vortex_err!("metadata segment length exceeds maximum u32"))?; + .map_err(|_| vortex_err!(Overflow: "metadata segment length exceeds maximum u32"))?; let alignment = buffer.alignment(); let padding = offset.next_multiple_of(alignment.as_usize() as u64) - *offset; diff --git a/vortex-file/src/lib.rs b/vortex-file/src/lib.rs index 1c309112078..b46c766403c 100644 --- a/vortex-file/src/lib.rs +++ b/vortex-file/src/lib.rs @@ -205,7 +205,6 @@ pub(crate) fn enable_all_registered_array_encodings(session: &VortexSession) { use vortex_edition::EditionInclusion; use vortex_edition::EditionSessionExt; use vortex_error::VortexExpect; - use vortex_error::vortex_err; use vortex_layout::session::LayoutSessionExt; const TEST_EDITION: EditionId = EditionId::new("test", 2026, 7, 0); @@ -216,7 +215,6 @@ pub(crate) fn enable_all_registered_array_encodings(session: &VortexSession) { id: TEST_EDITION, min_library_version: None, }) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("test edition is valid"); let component_ids = [ ( @@ -245,7 +243,6 @@ pub(crate) fn enable_all_registered_array_encodings(session: &VortexSession) { for id in ids { editions .declare_inclusion(EditionInclusion::new(kind, &id, TEST_EDITION)) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("registered component has one test-edition inclusion"); } } @@ -263,12 +260,10 @@ pub(crate) fn enable_all_registered_array_encodings(session: &VortexSession) { id, TEST_EDITION, )) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("default aggregate has one test-edition inclusion"); } session .enable_edition(TEST_EDITION) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("test edition is registered"); } diff --git a/vortex-file/src/multi/mod.rs b/vortex-file/src/multi/mod.rs index 03a80171ec5..2cf222f5d75 100644 --- a/vortex-file/src/multi/mod.rs +++ b/vortex-file/src/multi/mod.rs @@ -123,7 +123,7 @@ impl MultiFileDataSource { /// and creates lazy factories for the remaining files. pub async fn build(self) -> VortexResult { if self.glob_sources.is_empty() { - vortex_bail!("MultiFileDataSource requires at least one glob pattern"); + vortex_bail!(InvalidArgument: "MultiFileDataSource requires at least one glob pattern"); } // Create local filesystem lazily if needed (only if any glob lacks a filesystem). @@ -163,7 +163,7 @@ impl MultiFileDataSource { let all_files: Vec<(FileListing, FileSystemRef)> = resolved.into_iter().flatten().collect(); if all_files.is_empty() { - vortex_bail!("No files matched the glob pattern(s): {:?}", globs); + vortex_bail!(NotFound: "No files matched the glob pattern(s): {:?}", globs); } let file_count = all_files.len(); @@ -219,7 +219,7 @@ fn create_local_filesystem(session: &VortexSession) -> VortexResult VortexResult { vortex_bail!( - "The 'object_store' feature is required for automatic local filesystem creation. \ + NotImplemented: "The 'object_store' feature is required for automatic local filesystem creation. \ Either enable the feature or provide a filesystem via .with_filesystem()." ); } @@ -255,7 +255,7 @@ pub async fn open_cached( key = uri.as_deref(); } let Some(key) = key else { - vortex_bail!("Missing cache key"); + vortex_bail!(NotFound: "Missing cache key"); }; let mut options = open_options_fn(session.open_options()); diff --git a/vortex-file/src/multi/uri.rs b/vortex-file/src/multi/uri.rs index 21b84c43110..704bc3c0494 100644 --- a/vortex-file/src/multi/uri.rs +++ b/vortex-file/src/multi/uri.rs @@ -71,10 +71,10 @@ pub fn parse_uri_or_path(uri_or_path: &str) -> VortexResult { target_os = "hermit" ))] fn file_path_to_url(path: &str) -> VortexResult { - let abs = - absolute(Path::new(path)).map_err(|e| vortex_err!("failed to absolutize {path}: {e}"))?; + let abs = absolute(Path::new(path)) + .map_err(|e| vortex_err!(Io: "failed to absolutize {path}: {e}"))?; Url::from_file_path(normalize_path(abs)) - .map_err(|_| vortex_err!("neither URL nor path: {path}")) + .map_err(|_| vortex_err!(InvalidArgument: "neither URL nor path: {path}")) } /// `Url::from_file_path` does not exist on targets without a filesystem, such as @@ -88,7 +88,7 @@ fn file_path_to_url(path: &str) -> VortexResult { )))] fn file_path_to_url(path: &str) -> VortexResult { Err(vortex_err!( - "bare file paths are not supported on this platform: {path}" + InvalidArgument: "bare file paths are not supported on this platform: {path}" )) } diff --git a/vortex-file/src/open.rs b/vortex-file/src/open.rs index 3e06dbcfbf5..6d3878af416 100644 --- a/vortex-file/src/open.rs +++ b/vortex-file/src/open.rs @@ -441,7 +441,7 @@ impl VortexOpenOptions { .filter(|end| *end <= initial_read.len()) .ok_or_else(|| { vortex_err!( - "Segment at offset {} with length {} is out of bounds of the \ + OutOfBounds: "Segment at offset {} with length {} is out of bounds of the \ {}-byte initial read", segment.offset, segment.length, @@ -853,7 +853,7 @@ mod tests { let initial_read = ByteBuffer::zeroed(16); let Err(err) = VortexOpenOptions::collect_initial_segments(0, &initial_read, &bad_footer) else { - vortex_bail!("collecting an out-of-bounds segment must return an error"); + vortex_bail!(AssertionFailed: "collecting an out-of-bounds segment must return an error"); }; assert!( err.to_string().contains("out of bounds"), @@ -900,7 +900,7 @@ mod tests { let mut deserializer = Footer::deserializer(footer_bytes.freeze(), session.clone()) .with_size(serialized_footer_size as u64); let DeserializeStep::Done(cached_footer) = deserializer.deserialize()? else { - vortex_bail!("standalone footer bytes must be sufficient for deserialization"); + vortex_bail!(Serde: "standalone footer bytes must be sufficient for deserialization"); }; session diff --git a/vortex-file/src/read/driver.rs b/vortex-file/src/read/driver.rs index ad9c6570202..43b5a59138b 100644 --- a/vortex-file/src/read/driver.rs +++ b/vortex-file/src/read/driver.rs @@ -481,7 +481,7 @@ mod tests { let waker = futures::task::noop_waker(); let mut context = Context::from_waker(&waker); let Poll::Ready(Some(batch)) = batches.as_mut().poll_next(&mut context) else { - vortex_panic!("partial batch was not emitted by the current poll"); + vortex_panic!(AssertionFailed: "partial batch was not emitted by the current poll"); }; assert_eq!(batch.len(), 1); assert_eq!(batch[0].offset(), 0); diff --git a/vortex-file/src/read/request.rs b/vortex-file/src/read/request.rs index 1ef5beb3757..939de6f9c06 100644 --- a/vortex-file/src/read/request.rs +++ b/vortex-file/src/read/request.rs @@ -146,14 +146,14 @@ impl CoalescedRequest { ) -> VortexResult { vortex_ensure!( range.start <= range.end, - "CoalescedRequest: range.start, {}, must be less than or equal to range.end, {}.", + InvalidArgument: "CoalescedRequest: range.start, {}, must be less than or equal to range.end, {}.", range.start, range.end, ); for req in requests.iter() { vortex_ensure!( req.offset >= range.start, - "CoalescedRequest: sub-request for length {} at file offset {} precedes coalesced range: {}..{}. {:?}", + InvalidArgument: "CoalescedRequest: sub-request for length {} at file offset {} precedes coalesced range: {}..{}. {:?}", req.length, req.offset, range.start, @@ -162,7 +162,7 @@ impl CoalescedRequest { ); vortex_ensure!( req.offset.saturating_add(req.length as u64) <= range.end, - "CoalescedRequest: sub-request for length {} at file offset {} exceeds the coalesced range: {}..{}. {:?}", + InvalidArgument: "CoalescedRequest: sub-request for length {} at file offset {} exceeds the coalesced range: {}..{}. {:?}", req.length, req.offset, range.start, diff --git a/vortex-file/src/segments/source.rs b/vortex-file/src/segments/source.rs index 704750d346f..a3a7a5c9766 100644 --- a/vortex-file/src/segments/source.rs +++ b/vortex-file/src/segments/source.rs @@ -101,7 +101,7 @@ fn validate_read_result( result.and_then(|buffer| { if request.len() != buffer.len() { return Err(vortex_err!( - "FileSegmentSource: expected buffer of length {} but received {}. {:?}", + MismatchedTypes: "FileSegmentSource: expected buffer of length {} but received {}. {:?}", request.len(), buffer.len(), request @@ -164,7 +164,7 @@ impl Stream for ReadRangeResults { return Poll::Ready(None); }; let error = vortex_err!( - "FileSegmentSource: read_ranges ended before resolving request. {:?}", + Io: "FileSegmentSource: read_ranges ended before resolving request. {:?}", req ); return Poll::Ready(Some((req, Err(error)))); @@ -269,7 +269,7 @@ impl Stream for ReadDriver { } Poll::Ready(None) if this.num_active == 0 => Poll::Pending, Poll::Ready(None) => { - vortex_panic!("read result streams ended with active requests") + vortex_panic!(AssertionFailed: "read result streams ended with active requests") } Poll::Pending => Poll::Pending, } @@ -316,7 +316,7 @@ impl FileSegmentSource { let concurrency = reader.concurrency(); if concurrency == 0 { vortex_panic!( - "VortexReadAt::concurrency returned 0 (uri={:?}); this would stall I/O", + AssertionFailed: "VortexReadAt::concurrency returned 0 (uri={:?}); this would stall I/O", reader.uri() ); } @@ -368,7 +368,8 @@ impl SegmentSource for FileSegmentSource { let spec = *match self.segments.get(*id as usize) { Some(spec) => spec, None => { - return future::ready(Err(vortex_err!("Missing segment: {}", id))).boxed(); + return future::ready(Err(vortex_err!(NotFound: "Missing segment: {}", id))) + .boxed(); } }; @@ -390,7 +391,8 @@ impl SegmentSource for FileSegmentSource { // If we fail to submit the event, we create a future that has failed. if let Err(e) = self.events.unbounded_send(event) { - return future::ready(Err(vortex_err!("Failed to submit read request: {e}"))).boxed(); + return future::ready(Err(vortex_err!(Io: "Failed to submit read request: {e}"))) + .boxed(); } let fut = ReadFuture { @@ -445,7 +447,7 @@ impl Future for ReadFuture { if let Some(panic) = self.driver_panic.lock().take() { std::panic::resume_unwind(panic); } - Poll::Ready(Err(vortex_err!("ReadRequest dropped by runtime: {e}"))) + Poll::Ready(Err(vortex_err!(Io: "ReadRequest dropped by runtime: {e}"))) } Poll::Pending => Poll::Pending, }, @@ -454,7 +456,9 @@ impl Future for ReadFuture { // Notify the I/O stream that this request has been polled. match self.events.unbounded_send(ReadEvent::Polled(self.id)) { Ok(()) => Poll::Pending, - Err(e) => Poll::Ready(Err(vortex_err!("ReadRequest dropped by runtime: {e}"))), + Err(e) => { + Poll::Ready(Err(vortex_err!(Io: "ReadRequest dropped by runtime: {e}"))) + } } } _ => Poll::Pending, @@ -538,7 +542,8 @@ impl SegmentSource for BufferSegmentSource { let spec = match self.segments.get(*id as usize) { Some(spec) => spec, None => { - return future::ready(Err(vortex_err!("Missing segment: {}", id))).boxed(); + return future::ready(Err(vortex_err!(NotFound: "Missing segment: {}", id))) + .boxed(); } }; @@ -546,7 +551,7 @@ impl SegmentSource for BufferSegmentSource { let end = start + spec.length as usize; if end > self.buffer.len() { return future::ready(Err(vortex_err!( - "Segment {} range {}..{} out of bounds for buffer of length {}", + OutOfBounds: "Segment {} range {}..{} out of bounds for buffer of length {}", *id, start, end, @@ -867,7 +872,7 @@ mod tests { let permits = Arc::clone(&self.permits); async move { let Ok(permit) = permits.acquire_owned().await else { - vortex_panic!("test semaphore unexpectedly closed"); + vortex_panic!(AssertionFailed: "test semaphore unexpectedly closed"); }; permit.forget(); active.fetch_sub(1, Ordering::SeqCst); @@ -1037,7 +1042,7 @@ mod tests { for _ in 0..(offset as usize % 5 + 1) { tokio::task::yield_now().await; } - vortex_bail!("slow read done") + vortex_bail!(Io: "slow read done") } .boxed() } diff --git a/vortex-file/src/segments/writer.rs b/vortex-file/src/segments/writer.rs index 1673ce40101..183f1c2c95d 100644 --- a/vortex-file/src/segments/writer.rs +++ b/vortex-file/src/segments/writer.rs @@ -54,7 +54,7 @@ impl SegmentSink for BufferedSegmentSink { let mut specs = self.segment_specs.lock(); let segment_id = SegmentId::from( u32::try_from(specs.len()) - .map_err(|_| vortex_err!("Too mant segments, u32 overflow"))?, + .map_err(|_| vortex_err!(Overflow: "Too mant segments, u32 overflow"))?, ); // The API requires us to write these buffers contiguously. Therefore, we can only @@ -66,7 +66,7 @@ impl SegmentSink for BufferedSegmentSink { .map(|buffer| buffer.alignment()) .unwrap_or_else(Alignment::none); let length = u32::try_from(buffers.iter().map(|buffer| buffer.len()).sum::()) - .map_err(|_| vortex_err!("segment buffer length exceeds maximum u32"))?; + .map_err(|_| vortex_err!(Overflow: "segment buffer length exceeds maximum u32"))?; // Add any padding required to align the segment. let byte_offset = self.byte_offset.load(Ordering::Relaxed); diff --git a/vortex-file/src/writer.rs b/vortex-file/src/writer.rs index a5208014bfd..86b72c5418f 100644 --- a/vortex-file/src/writer.rs +++ b/vortex-file/src/writer.rs @@ -454,7 +454,7 @@ fn validate_dtype_editions(session: &VortexSession, dtype: &DType) -> VortexResu DType::Extension(extension) => { if !allowed.contains(&extension.id()) { vortex_bail!( - "Extension DType {} not permitted by enabled editions", + InvalidArgument: "Extension DType {} not permitted by enabled editions", extension.id() ); } @@ -486,7 +486,7 @@ fn new_layout_context(session: &VortexSession, enforce_editions: bool) -> Layout fn validate_metadata_segments(metadata: &HashMap) -> VortexResult<()> { if metadata.len() > MAX_METADATA_SEGMENTS { vortex_bail!( - "Vortex files may contain at most {} metadata segments; got {} metadata segments. Metadata keys must be non-empty and at most {} bytes", + InvalidArgument: "Vortex files may contain at most {} metadata segments; got {} metadata segments. Metadata keys must be non-empty and at most {} bytes", MAX_METADATA_SEGMENTS, metadata.len(), MAX_METADATA_KEY_BYTES @@ -496,7 +496,7 @@ fn validate_metadata_segments(metadata: &HashMap) -> VortexR for key in metadata.keys() { if key.is_empty() { vortex_bail!( - "Vortex metadata keys must be non-empty and at most {} bytes; files may contain at most {} metadata segments", + InvalidArgument: "Vortex metadata keys must be non-empty and at most {} bytes; files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS ); @@ -505,7 +505,7 @@ fn validate_metadata_segments(metadata: &HashMap) -> VortexR let key_bytes = key.len(); if key_bytes > MAX_METADATA_KEY_BYTES { vortex_bail!( - "Vortex metadata key {key:?} is {key_bytes} bytes, but keys must be at most {} bytes; files may contain at most {} metadata segments", + InvalidArgument: "Vortex metadata key {key:?} is {key_bytes} bytes, but keys must be at most {} bytes; files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS ); @@ -548,7 +548,7 @@ impl Writer<'_> { // finish() is called. Therefore, we can assume the writer has failed. // The writer future has failed, we need to propagate the error. match result { - Ok(_) => vortex_bail!("Internal error: writer future completed early"), + Ok(_) => vortex_bail!(AssertionFailed: "Internal error: writer future completed early"), Err(e) => return Err(e), } } @@ -587,7 +587,7 @@ impl Writer<'_> { // finish() is called. Therefore, we can assume the writer has failed. // The writer future has failed, we need to propagate the error. match result { - Ok(_) => vortex_bail!("Internal error: writer future completed early"), + Ok(_) => vortex_bail!(AssertionFailed: "Internal error: writer future completed early"), Err(e) => return Err(e), } } @@ -620,7 +620,7 @@ impl Writer<'_> { async fn handle_failed_task(&mut self) -> VortexError { match (&mut self.future).await { Ok(_) => vortex_err!( - "Internal error: writer task completed successfully but write future finished early" + AssertionFailed: "Internal error: writer task completed successfully but write future finished early" ), Err(e) => e, } diff --git a/vortex-file/tests/common/mod.rs b/vortex-file/tests/common/mod.rs index 29b8ac0024f..3cffd4f9eeb 100644 --- a/vortex-file/tests/common/mod.rs +++ b/vortex-file/tests/common/mod.rs @@ -9,7 +9,6 @@ use vortex_edition::EditionId; use vortex_edition::EditionInclusion; use vortex_edition::EditionSessionExt; use vortex_error::VortexExpect; -use vortex_error::vortex_err; use vortex_layout::session::LayoutSessionExt; use vortex_session::VortexSession; @@ -23,7 +22,6 @@ pub fn enable_all_registered_array_encodings(session: &VortexSession) { id: TEST_EDITION, min_library_version: None, }) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("test edition is valid"); let component_ids = [ ( @@ -52,7 +50,6 @@ pub fn enable_all_registered_array_encodings(session: &VortexSession) { for id in ids { editions .declare_inclusion(EditionInclusion::new(kind, &id, TEST_EDITION)) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("registered component has one test-edition inclusion"); } } @@ -70,11 +67,9 @@ pub fn enable_all_registered_array_encodings(session: &VortexSession) { id, TEST_EDITION, )) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("default aggregate has one test-edition inclusion"); } session .enable_edition(TEST_EDITION) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("test edition is registered"); } diff --git a/vortex-io/src/filesystem/glob.rs b/vortex-io/src/filesystem/glob.rs index 030bf4f56d1..e1684c280f2 100644 --- a/vortex-io/src/filesystem/glob.rs +++ b/vortex-io/src/filesystem/glob.rs @@ -37,8 +37,9 @@ impl dyn FileSystem + '_ { return Ok(stream); } - let glob_pattern = glob::Pattern::new(pattern) - .map_err(|e| vortex_err!("Invalid glob pattern '{}': {}", pattern, e))?; + let glob_pattern = glob::Pattern::new(pattern).map_err( + |e| vortex_err!(InvalidArgument: "Invalid glob pattern '{}': {}", pattern, e), + )?; let listing_prefix = glob_list_prefix(pattern).trim_end_matches('/'); @@ -77,7 +78,7 @@ fn validate_glob(pattern: &str) -> VortexResult<()> { for escape_pattern in ["\\*", "\\?", "\\["] { if pattern.contains(escape_pattern) { vortex_bail!( - "Escaped glob characters are not allowed in patterns. Found '{}' in: {}", + InvalidArgument: "Escaped glob characters are not allowed in patterns. Found '{}' in: {}", escape_pattern, pattern ); @@ -124,7 +125,7 @@ mod tests { #[async_trait] impl FileSystem for HeadFileSystem { fn list(&self, _prefix: &str) -> BoxStream<'_, VortexResult> { - vortex_panic!("list() must not be called for an exact path; glob should use head()") + vortex_panic!(AssertionFailed: "list() must not be called for an exact path; glob should use head()") } async fn head(&self, path: &str) -> VortexResult> { @@ -136,11 +137,11 @@ mod tests { } async fn open_read(&self, _path: &str) -> VortexResult> { - vortex_panic!("open_read() should not be called") + vortex_panic!(AssertionFailed: "open_read() should not be called") } async fn delete(&self, _path: &str) -> VortexResult<()> { - vortex_panic!("delete() should not be called") + vortex_panic!(AssertionFailed: "delete() should not be called") } } diff --git a/vortex-io/src/object_store/read_at.rs b/vortex-io/src/object_store/read_at.rs index b354ea705e8..050641f07eb 100644 --- a/vortex-io/src/object_store/read_at.rs +++ b/vortex-io/src/object_store/read_at.rs @@ -136,7 +136,7 @@ async fn read_object_store_range( let end = written + bytes.len(); vortex_ensure!( end <= length, - "Object store stream returned too many bytes: {} > expected {} (range: {:?})", + Io: "Object store stream returned too many bytes: {} > expected {} (range: {:?})", end, length, range @@ -148,7 +148,7 @@ async fn read_object_store_range( vortex_ensure_eq!( written, length, - "Object store stream returned too few bytes (range: {:?})", + Io: "Object store stream returned too few bytes (range: {:?})", range ); diff --git a/vortex-io/src/read_at.rs b/vortex-io/src/read_at.rs index c24cd49620e..45c7d44b0c5 100644 --- a/vortex-io/src/read_at.rs +++ b/vortex-io/src/read_at.rs @@ -224,7 +224,7 @@ impl VortexReadAt for ByteBuffer { usize::try_from(offset + length as u64).vortex_expect("end too big for usize"); if end > buffer.len() { vortex_bail!( - "Requested range {}..{} out of bounds for buffer of length {}", + OutOfBounds: "Requested range {}..{} out of bounds for buffer of length {}", start, end, buffer.len() diff --git a/vortex-io/src/request/mod.rs b/vortex-io/src/request/mod.rs index efce222ba0f..030a68cd1a8 100644 --- a/vortex-io/src/request/mod.rs +++ b/vortex-io/src/request/mod.rs @@ -180,7 +180,7 @@ impl IoSlot { /// its result has not been taken, since that is a bug in the owner. pub fn issue(&mut self, target: IoTarget) -> IoBatch { if self.request.is_some() || self.result.is_some() { - vortex_panic!("IoSlot: issue while a request is outstanding"); + vortex_panic!(AssertionFailed: "IoSlot: issue while a request is outstanding"); } let request = IoRequest { intent: IoIntent::Fetch, @@ -201,11 +201,11 @@ impl IoSlot { /// does not match the target, since the driver guarantees both. pub fn deliver(&mut self, id: IoRequestId, result: IoResult) { let Some(request) = self.request.take_if(|request| request.request == id) else { - vortex_panic!("IoSlot: delivery of {id:?}, which is not outstanding"); + vortex_panic!(AssertionFailed: "IoSlot: delivery of {id:?}, which is not outstanding"); }; if !result.matches(&request.target) { vortex_panic!( - "IoSlot: {id:?} for {:?} answered with {}", + AssertionFailed: "IoSlot: {id:?} for {:?} answered with {}", request.target, result.kind() ); diff --git a/vortex-io/src/request/source.rs b/vortex-io/src/request/source.rs index cda9e2ebed3..adabc379a08 100644 --- a/vortex-io/src/request/source.rs +++ b/vortex-io/src/request/source.rs @@ -50,7 +50,7 @@ impl IoSource for ReadAtIoSource { if let IoTarget::Range { offset, len, .. } = &request.target && offset.checked_add(*len as u64).is_none() { - vortex_bail!("ReadAtIoSource: range overflow for {:?}", request.request); + vortex_bail!(Overflow: "ReadAtIoSource: range overflow for {:?}", request.request); } } self.queued.lock().extend( @@ -72,11 +72,9 @@ impl IoSource for ReadAtIoSource { } fn wait(&self) -> VortexResult { - let (work, request) = self - .queued - .lock() - .pop_front() - .ok_or_else(|| vortex_err!("ReadAtIoSource: wait with nothing outstanding"))?; + let (work, request) = self.queued.lock().pop_front().ok_or_else( + || vortex_err!(AssertionFailed: "ReadAtIoSource: wait with nothing outstanding"), + )?; let result = match request.target { IoTarget::Size => self.runtime.block_on(self.read.size()).map(IoResult::Size), IoTarget::Range { diff --git a/vortex-io/src/request/source/tests.rs b/vortex-io/src/request/source/tests.rs index fd6bcfd12a9..cca0458c806 100644 --- a/vortex-io/src/request/source/tests.rs +++ b/vortex-io/src/request/source/tests.rs @@ -79,7 +79,7 @@ fn a_range_is_read_at_its_alignment() -> VortexResult<()> { }], )?; let IoResult::Bytes(bytes) = source.wait()?.result? else { - vortex_bail!("expected bytes"); + vortex_bail!(AssertionFailed: "expected bytes"); }; assert!(bytes.try_into_host_sync()?.is_aligned(alignment)); assert_eq!(read.alignments(), vec![alignment]); diff --git a/vortex-io/src/runtime/blocking_pool.rs b/vortex-io/src/runtime/blocking_pool.rs index fc315844831..767be97ca23 100644 --- a/vortex-io/src/runtime/blocking_pool.rs +++ b/vortex-io/src/runtime/blocking_pool.rs @@ -61,7 +61,7 @@ impl BlockingPool { }) .is_err() { - vortex_panic!("cannot spawn blocking work on a shut down runtime"); + vortex_panic!(InvalidArgument: "cannot spawn blocking work on a shut down runtime"); } state.queued_job_count += 1; if state.queued_job_count > state.idle_thread_count { @@ -83,7 +83,7 @@ impl BlockingPool { .spawn(move || worker_loop(receiver, worker_state)) { state.thread_count -= 1; - vortex_panic!("failed to spawn a blocking I/O worker: {error}"); + vortex_panic!(Io: "failed to spawn a blocking I/O worker: {error}"); } } } @@ -210,7 +210,7 @@ mod tests { assert_eq!( recv.recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!("blocking job did not finish: {error}"))?, + .map_err(|error| vortex_err!(Io: "blocking job did not finish: {error}"))?, 42 ); Ok(()) @@ -227,7 +227,7 @@ mod tests { }))); started_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!("first blocking job did not start: {error}"))?; + .map_err(|error| vortex_err!(Io: "first blocking job did not start: {error}"))?; let (ran_send, ran_recv) = mpsc::sync_channel(1); pool.spawn(Box::new(move || { @@ -242,7 +242,7 @@ mod tests { let _ = release_send.send(()); done_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!("blocking queue did not drain: {error}"))?; + .map_err(|error| vortex_err!(Io: "blocking queue did not drain: {error}"))?; assert!(ran_recv.try_recv().is_err()); Ok(()) } @@ -265,7 +265,7 @@ mod tests { for _ in 0..2 { started_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!("blocking job did not start: {error}"))?; + .map_err(|error| vortex_err!(Io: "blocking job did not start: {error}"))?; } barrier.wait(); Ok(()) @@ -280,12 +280,12 @@ mod tests { }))); let first_thread = first_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!("first blocking job did not finish: {error}"))?; + .map_err(|error| vortex_err!(Io: "first blocking job did not finish: {error}"))?; let deadline = Instant::now() + Duration::from_secs(5); while pool.state.lock().idle_thread_count != 1 { if Instant::now() >= deadline { - return Err(vortex_err!("blocking worker did not become idle")); + return Err(vortex_err!(Io: "blocking worker did not become idle")); } std::thread::yield_now(); } @@ -298,7 +298,7 @@ mod tests { }))); let second_thread = started_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!("second blocking job did not finish: {error}"))?; + .map_err(|error| vortex_err!(Io: "second blocking job did not finish: {error}"))?; assert_eq!(first_thread, second_thread); let state = pool.state.lock(); diff --git a/vortex-io/src/runtime/handle.rs b/vortex-io/src/runtime/handle.rs index c08f3114310..e8e5aad6225 100644 --- a/vortex-io/src/runtime/handle.rs +++ b/vortex-io/src/runtime/handle.rs @@ -38,7 +38,7 @@ impl Handle { fn runtime(&self) -> Arc { self.runtime.upgrade().unwrap_or_else(|| { - vortex_panic!("Attempted to use a Handle after its runtime was dropped") + vortex_panic!(InvalidArgument: "Attempted to use a Handle after its runtime was dropped") }) } diff --git a/vortex-io/src/runtime/single.rs b/vortex-io/src/runtime/single.rs index 9f241d6bf55..62fa475888b 100644 --- a/vortex-io/src/runtime/single.rs +++ b/vortex-io/src/runtime/single.rs @@ -129,7 +129,7 @@ impl Executor for Sender { future, task_callback: send, }) { - vortex_panic!("Executor missing: {}", e); + vortex_panic!(AssertionFailed: "Executor missing: {}", e); } Box::new(LazyAbortHandle { task: Mutex::new(recv), @@ -142,7 +142,7 @@ impl Executor for Sender { sync: cpu, task_callback: send, }) { - vortex_panic!("Executor missing: {}", e); + vortex_panic!(AssertionFailed: "Executor missing: {}", e); } Box::new(LazyAbortHandle { task: Mutex::new(recv), @@ -155,7 +155,7 @@ impl Executor for Sender { sync: work, task_callback: send, }) { - vortex_panic!("Executor missing: {}", e); + vortex_panic!(AssertionFailed: "Executor missing: {}", e); } Box::new(LazyAbortHandle { task: Mutex::new(recv), diff --git a/vortex-io/src/runtime/tokio.rs b/vortex-io/src/runtime/tokio.rs index a1696e50c20..046ebe98682 100644 --- a/vortex-io/src/runtime/tokio.rs +++ b/vortex-io/src/runtime/tokio.rs @@ -128,7 +128,7 @@ impl BlockingRuntime for TokioRuntime { { // Assert that we're not currently inside the Tokio context. if tokio::runtime::Handle::try_current().is_ok() { - vortex_error::vortex_panic!("block_on cannot be called from within a Tokio runtime"); + vortex_error::vortex_panic!(InvalidArgument: "block_on cannot be called from within a Tokio runtime"); } let handle = Arc::clone(&self.0); tokio::task::block_in_place(move || handle.block_on(fut)) @@ -142,7 +142,7 @@ impl BlockingRuntime for TokioRuntime { // Assert that we're not currently inside the Tokio context. if tokio::runtime::Handle::try_current().is_ok() { vortex_error::vortex_panic!( - "block_on_stream cannot be called from within a Tokio runtime" + InvalidArgument: "block_on_stream cannot be called from within a Tokio runtime" ); } let handle = Arc::clone(&self.0); diff --git a/vortex-ipc/src/iterator.rs b/vortex-ipc/src/iterator.rs index 64f52b4bbf8..2201d051035 100644 --- a/vortex-ipc/src/iterator.rs +++ b/vortex-ipc/src/iterator.rs @@ -41,10 +41,10 @@ impl SyncIPCReader { }) } msg => { - vortex_bail!("Expected DType message, got {:?}", msg); + vortex_bail!(MismatchedTypes: "Expected DType message, got {:?}", msg); } }, - None => vortex_bail!("Expected DType message, got EOF"), + None => vortex_bail!(MismatchedTypes: "Expected DType message, got EOF"), } } } @@ -67,7 +67,7 @@ impl Iterator for SyncIPCReader { .and_then(|array| { if array.dtype() != self.dtype() { Err(vortex_err!( - "Array data type mismatch: expected {:?}, got {:?}", + MismatchedTypes: "Array data type mismatch: expected {:?}, got {:?}", self.dtype(), array.dtype() )) @@ -76,7 +76,7 @@ impl Iterator for SyncIPCReader { } }), ), - msg => Some(Err(vortex_err!("Expected Array message, got {:?}", msg))), + msg => Some(Err(vortex_err!(MismatchedTypes: "Expected Array message, got {:?}", msg))), }, Err(e) => Some(Err(e)), } diff --git a/vortex-ipc/src/messages/decoder.rs b/vortex-ipc/src/messages/decoder.rs index 73cdd235485..ba950f3c360 100644 --- a/vortex-ipc/src/messages/decoder.rs +++ b/vortex-ipc/src/messages/decoder.rs @@ -95,7 +95,7 @@ impl MessageDecoder { let msg_bytes = bytes.copy_to_const_aligned(*msg_length); let msg = root::(msg_bytes.as_ref())?; if msg.version() != MessageVersion::V0 { - vortex_bail!("Unsupported message version {:?}", msg.version()); + vortex_bail!(InvalidArgument: "Unsupported message version {:?}", msg.version()); } self.state = State::Reading(msg_bytes); @@ -106,7 +106,7 @@ impl MessageDecoder { // Now we read the body let body_length = usize::try_from(msg.body_size()).map_err(|_| { - vortex_err!("body size {} is too large for usize", msg.body_size()) + vortex_err!(Overflow: "body size {} is too large for usize", msg.body_size()) })?; if bytes.remaining() < body_length { return Ok(PollRead::NeedMore(body_length)); @@ -157,7 +157,7 @@ impl MessageDecoder { return Ok(PollRead::Some(DecoderMessage::DType(dtype))); } _ => { - vortex_bail!("Unsupported message header {:?}", msg.header_type()); + vortex_bail!(InvalidArgument: "Unsupported message header {:?}", msg.header_type()); } } } @@ -195,7 +195,7 @@ mod test { let mut buffer = BytesMut::from(ipc_bytes.as_ref()); let (array_parts, ctx, row_count) = match decoder.read_next(&mut buffer).unwrap() { PollRead::Some(DecoderMessage::Array(array_parts)) => array_parts, - otherwise => vortex_panic!("Expected an array, got {:?}", otherwise), + otherwise => vortex_panic!(MismatchedTypes: "Expected an array, got {:?}", otherwise), }; // Decode the array parts with the context diff --git a/vortex-ipc/src/messages/encoder.rs b/vortex-ipc/src/messages/encoder.rs index 4b056052b3a..6f2a0c813bf 100644 --- a/vortex-ipc/src/messages/encoder.rs +++ b/vortex-ipc/src/messages/encoder.rs @@ -76,7 +76,7 @@ impl MessageEncoder { &mut fbb, &fb::ArrayMessageArgs { row_count: u32::try_from(array.len()) - .map_err(|_| vortex_err!("Array length must fit into u32"))?, + .map_err(|_| vortex_err!(Overflow: "Array length must fit into u32"))?, encodings: Some(array_encodings), }, ) @@ -127,7 +127,7 @@ impl MessageEncoder { let (fbv, pos) = fbb.collapse(); let fb_buffer = FlatBuffer::copy_from(&fbv[pos..]); let fb_buffer_len = u32::try_from(fb_buffer.len()) - .map_err(|_| vortex_err!("Array flatbuffer length must fit into u32"))?; + .map_err(|_| vortex_err!(Overflow: "Array flatbuffer length must fit into u32"))?; buffers[0] = Bytes::from(fb_buffer_len.to_le_bytes().to_vec()); buffers[1] = fb_buffer.into_inner().into_bytes(); diff --git a/vortex-ipc/src/messages/reader_async.rs b/vortex-ipc/src/messages/reader_async.rs index 9a6cd946690..5284dcff9b7 100644 --- a/vortex-ipc/src/messages/reader_async.rs +++ b/vortex-ipc/src/messages/reader_async.rs @@ -81,7 +81,7 @@ fn poll_fill_buffer( Poll::Ready(if bytes_read == 0 { if *total_bytes_read > 0 { Err(vortex_err!( - "unexpected EOF during partial read: read {total_bytes_read} of {} expected bytes", + InvalidArgument: "unexpected EOF during partial read: read {total_bytes_read} of {} expected bytes", buffer.len() )) } else { diff --git a/vortex-ipc/src/messages/reader_buf.rs b/vortex-ipc/src/messages/reader_buf.rs index faf2694f707..79685f2f4ad 100644 --- a/vortex-ipc/src/messages/reader_buf.rs +++ b/vortex-ipc/src/messages/reader_buf.rs @@ -35,7 +35,7 @@ impl Iterator for BufMessageReader { match self.decoder.read_next(&mut self.buffer) { Ok(PollRead::Some(msg)) => Some(Ok(msg)), Ok(PollRead::NeedMore(_)) => Some(Err(vortex_err!( - "Buffer did not have sufficient bytes for an IPC message" + Serde: "Buffer did not have sufficient bytes for an IPC message" ))), Err(e) => Some(Err(e)), } diff --git a/vortex-ipc/src/messages/reader_sync.rs b/vortex-ipc/src/messages/reader_sync.rs index 7af395eb9ae..f9fbe8b2eeb 100644 --- a/vortex-ipc/src/messages/reader_sync.rs +++ b/vortex-ipc/src/messages/reader_sync.rs @@ -51,7 +51,7 @@ impl Iterator for SyncMessageReader { return None; } return Some(Err(vortex_err!( - "unexpected EOF during partial read: read {total_bytes_read} of {nbytes} expected bytes" + InvalidArgument: "unexpected EOF during partial read: read {total_bytes_read} of {nbytes} expected bytes" ))); } Ok(n) => total_bytes_read += n, @@ -117,7 +117,7 @@ mod tests { let DecoderMessage::Array((parts, ctx, row_count)) = messages.next().vortex_expect("expected a message")? else { - vortex_panic!("expected an array message"); + vortex_panic!(AssertionFailed: "expected an array message"); }; let actual = parts.decode(array.dtype(), row_count, &ctx, &SESSION)?; assert_eq!(actual.len(), array.len()); diff --git a/vortex-ipc/src/stream.rs b/vortex-ipc/src/stream.rs index d8da4935115..8a46692d07c 100644 --- a/vortex-ipc/src/stream.rs +++ b/vortex-ipc/src/stream.rs @@ -46,10 +46,10 @@ impl AsyncIPCReader { Some(msg) => match msg { DecoderMessage::DType(dtype) => dtype, msg => { - vortex_bail!("Expected DType message, got {:?}", msg); + vortex_bail!(MismatchedTypes: "Expected DType message, got {:?}", msg); } }, - None => vortex_bail!("Expected DType message, got EOF"), + None => vortex_bail!(MismatchedTypes: "Expected DType message, got EOF"), }; let dtype = DType::from_flatbuffer(dtype, session)?; @@ -86,7 +86,7 @@ impl Stream for AsyncIPCReader { .and_then(|array| { if array.dtype() != this.dtype { Err(vortex_err!( - "Array data type mismatch: expected {:?}, got {:?}", + MismatchedTypes: "Array data type mismatch: expected {:?}, got {:?}", this.dtype, array.dtype() )) @@ -96,7 +96,7 @@ impl Stream for AsyncIPCReader { }), )), Ok(msg) => Poll::Ready(Some(Err(vortex_err!( - "Expected Array message, got {:?}", + MismatchedTypes: "Expected Array message, got {:?}", msg )))), Err(e) => Poll::Ready(Some(Err(e))), @@ -183,7 +183,9 @@ impl Stream for ArrayStreamIPCBytes { .encoder .encode(EncoderMessage::DType(this.stream.dtype())) else { - return Poll::Ready(Some(Err(vortex_err!("Failed to encode DType message")))); + return Poll::Ready(Some(Err( + vortex_err!(Serde: "Failed to encode DType message"), + ))); }; this.buffers.extend(buffers); this.written_dtype = true; diff --git a/vortex-jni/src/data_source.rs b/vortex-jni/src/data_source.rs index 7e50b0d934b..098facdbe81 100644 --- a/vortex-jni/src/data_source.rs +++ b/vortex-jni/src/data_source.rs @@ -84,7 +84,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_open( } } if glob_strings.is_empty() { - return Err(vortex_err!("no paths provided").into()); + return Err(vortex_err!(InvalidArgument: "no paths provided").into()); } let glob_urls: Vec = glob_strings @@ -129,10 +129,10 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_openFiles( let count = readables.len(env)?; if count == 0 { - throw_runtime!("no readables provided"); + throw_runtime!(InvalidArgument: "no readables provided"); } if paths.len(env)? != count || lengths.len(env)? != count { - throw_runtime!("readables, paths, and lengths must have equal length"); + throw_runtime!(InvalidArgument: "readables, paths, and lengths must have equal length"); } let mut sizes = vec![0 as jlong; count]; @@ -146,14 +146,14 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_openFiles( let path_obj = paths.get_element(env, idx)?; let path: String = env.cast_local::(path_obj)?.try_to_string(env)?; if path.contains(['*', '?', '[']) { - throw_runtime!("path '{path}' contains glob characters, which are unsupported"); + throw_runtime!(InvalidArgument: "path '{path}' contains glob characters, which are unsupported"); } let size = u64::try_from(sizes[idx]) - .map_err(|_| vortex_err!("negative length for path '{path}'"))?; + .map_err(|_| vortex_err!(InvalidArgument: "negative length for path '{path}'"))?; let readable = readables.get_element(env, idx)?; if readable.is_null() { - throw_runtime!("null readable for path '{path}'"); + throw_runtime!(InvalidArgument: "null readable for path '{path}'"); } let readable = Arc::new(env.new_global_ref(&readable)?); @@ -200,7 +200,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_arrowSchema( ) { try_or_throw(&mut env, |_| { if schema_addr == 0 { - throw_runtime!("null arrow schema address"); + throw_runtime!(InvalidArgument: "null arrow schema address"); } let session = unsafe { session_ref(session_ptr) }; let ds = unsafe { NativeDataSource::from_ptr(pointer) }; diff --git a/vortex-jni/src/errors.rs b/vortex-jni/src/errors.rs index 0e903406ae0..7902d8aada7 100644 --- a/vortex-jni/src/errors.rs +++ b/vortex-jni/src/errors.rs @@ -43,7 +43,7 @@ impl From for VortexError { fn from(error: JNIError) -> Self { match error { JNIError::Vortex(error) => error, - JNIError::Custom(error) => vortex_err!("JNI: {error}"), + JNIError::Custom(error) => vortex_err!(Other: "JNI: {error}"), } } } diff --git a/vortex-jni/src/expression.rs b/vortex-jni/src/expression.rs index afcefe990c4..1d3d85e0dbd 100644 --- a/vortex-jni/src/expression.rs +++ b/vortex-jni/src/expression.rs @@ -111,7 +111,7 @@ fn parse_op(op: jbyte) -> Result { 9 => Operator::Sub, 10 => Operator::Mul, 11 => Operator::Div, - other => throw_runtime!("unknown binary operator code: {other}"), + other => throw_runtime!(InvalidArgument: "unknown binary operator code: {other}"), }) } @@ -127,7 +127,7 @@ fn parse_duplicate_handling(tag: jbyte) -> Result { Ok(match tag { 0 => DuplicateHandling::RightMost, 1 => DuplicateHandling::Error, - other => throw_runtime!("unknown duplicate handling code: {other}"), + other => throw_runtime!(InvalidArgument: "unknown duplicate handling code: {other}"), }) } @@ -215,7 +215,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_pack( let name: FieldName = s.try_to_string(env)?.into(); let expr_ptr = *expressions.get(idx).ok_or_else(|| -> JNIError { - vortex_err!("missing pack expression child").into() + vortex_err!(NotFound: "missing pack expression child").into() })?; let expr = unsafe { expr_ref(expr_ptr) }.clone(); @@ -254,7 +254,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_and( let exprs = collect_operands(env, &operands)?; and_collect(exprs) .map(into_raw) - .ok_or_else(|| vortex_err!("empty AND expression").into()) + .ok_or_else(|| vortex_err!(InvalidArgument: "empty AND expression").into()) }) } @@ -268,7 +268,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_or( let exprs = collect_operands(env, &operands)?; or_collect(exprs) .map(into_raw) - .ok_or_else(|| vortex_err!("empty OR expression").into()) + .ok_or_else(|| vortex_err!(InvalidArgument: "empty OR expression").into()) }) } @@ -323,7 +323,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_spatial( 6 => SpatialIntersects.try_new_expr(EmptyOptions, operands), 7 => SpatialLength.try_new_expr(EmptyOptions, operands), 8 => SpatialMakeLine.try_new_expr(EmptyOptions, operands), - other => throw_runtime!("unknown spatial function code: {other}"), + other => throw_runtime!(InvalidArgument: "unknown spatial function code: {other}"), }?; Ok(into_raw(expr)) }) @@ -551,9 +551,9 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalDecimal( ) -> jlong { try_or_throw(&mut env, |env| { let precision = u8::try_from(precision) - .map_err(|_| vortex_err!("decimal precision out of range: {precision}"))?; - let scale = - i8::try_from(scale).map_err(|_| vortex_err!("decimal scale out of range: {scale}"))?; + .map_err(|_| vortex_err!(OutOfBounds: "decimal precision out of range: {precision}"))?; + let scale = i8::try_from(scale) + .map_err(|_| vortex_err!(OutOfBounds: "decimal scale out of range: {scale}"))?; let decimal_dtype = DecimalDType::try_new(precision, scale)?; if is_null_flag { return Ok(into_raw(lit(Scalar::null(DType::Decimal( @@ -562,7 +562,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalDecimal( ))))); } if unscaled_big_endian.len(env)? > 32 { - throw_runtime!("Decimal value must fit with 32 bytes"); + throw_runtime!(Overflow: "Decimal value must fit with 32 bytes"); } let bytes = env.convert_byte_array(&unscaled_big_endian)?; @@ -582,31 +582,31 @@ fn decimal_value_from_be_bytes( dtype: &DecimalDType, ) -> Result { if bytes.is_empty() { - throw_runtime!("decimal unscaled value must have at least one byte"); + throw_runtime!(InvalidArgument: "decimal unscaled value must have at least one byte"); } let value = i256_from_twos_complement_be(bytes); // Pick the narrowest backing integer that fits the dtype's precision. let required_bits = dtype.required_bit_width(); if required_bits <= 8 { - let v = - BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i8"))?; + let v = BigCast::from(value) + .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i8"))?; Ok(DecimalValue::I8(v)) } else if required_bits <= 16 { - let v = - BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i16"))?; + let v = BigCast::from(value) + .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i16"))?; Ok(DecimalValue::I16(v)) } else if required_bits <= 32 { - let v = - BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i32"))?; + let v = BigCast::from(value) + .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i32"))?; Ok(DecimalValue::I32(v)) } else if required_bits <= 64 { - let v = - BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i64"))?; + let v = BigCast::from(value) + .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i64"))?; Ok(DecimalValue::I64(v)) } else if required_bits <= 128 { let v = value .maybe_i128() - .ok_or_else(|| vortex_err!("decimal value does not fit in i128"))?; + .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i128"))?; Ok(DecimalValue::I128(v)) } else { Ok(DecimalValue::I256(value)) @@ -652,12 +652,11 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalDate( return Ok(into_raw(lit(Scalar::null(dtype)))); } let storage_value = match unit { - TimeUnit::Days => ScalarValue::from( - i32::try_from(value) - .map_err(|_| vortex_err!("date value does not fit in i32 days: {value}"))?, - ), + TimeUnit::Days => ScalarValue::from(i32::try_from(value).map_err( + |_| vortex_err!(Overflow: "date value does not fit in i32 days: {value}"), + )?), TimeUnit::Milliseconds => ScalarValue::from(value), - other => throw_runtime!("date does not support time unit {other}"), + other => throw_runtime!(InvalidArgument: "date does not support time unit {other}"), }; Ok(into_raw(lit(Scalar::try_new(dtype, Some(storage_value))?))) }) @@ -722,10 +721,11 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalTime( return Ok(into_raw(lit(Scalar::null(dtype)))); } let storage_value = match unit { - TimeUnit::Seconds | TimeUnit::Milliseconds => ScalarValue::from( - i32::try_from(value) - .map_err(|_| vortex_err!("time value does not fit in i32 {unit}: {value}"))?, - ), + TimeUnit::Seconds | TimeUnit::Milliseconds => { + ScalarValue::from(i32::try_from(value).map_err( + |_| vortex_err!(Overflow: "time value does not fit in i32 {unit}: {value}"), + )?) + } _ => ScalarValue::from(value), }; Ok(into_raw(lit(Scalar::try_new(dtype, Some(storage_value))?))) @@ -746,11 +746,11 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalGeometry( ) -> jlong { try_or_throw(&mut env, |env| { if wkb.is_null() { - throw_runtime!("geometry literal WKB bytes must not be null"); + throw_runtime!(InvalidArgument: "geometry literal WKB bytes must not be null"); } let bytes = env.convert_byte_array(&wkb)?; let scalar = native_geometry_scalar_from_wkb(&bytes, &VortexSession::default())? - .ok_or_else(|| vortex_err!("unsupported WKB geometry type for a geometry literal"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "unsupported WKB geometry type for a geometry literal"))?; Ok(into_raw(lit(scalar))) }) } @@ -764,8 +764,9 @@ const UUID_BYTE_LEN: usize = 16; /// Arrow's canonical UUID type. The metadata records no version constraint, so the dtype is /// compatible with any UUID column regardless of the UUID versions it contains. fn uuid_dtype(nullability: Nullability) -> Result { - let list_size = u32::try_from(UUID_BYTE_LEN) - .map_err(|_| vortex_err!("UUID byte length {UUID_BYTE_LEN} does not fit in u32"))?; + let list_size = u32::try_from(UUID_BYTE_LEN).map_err( + |_| vortex_err!(Overflow: "UUID byte length {UUID_BYTE_LEN} does not fit in u32"), + )?; let storage_dtype = DType::FixedSizeList( Arc::new(DType::Primitive(PType::U8, Nullability::NonNullable)), list_size, @@ -779,7 +780,7 @@ fn uuid_dtype(nullability: Nullability) -> Result { fn uuid_scalar(bytes: &[u8]) -> Result { if bytes.len() != UUID_BYTE_LEN { throw_runtime!( - "UUID literal must be exactly {UUID_BYTE_LEN} bytes, got {}", + InvalidArgument: "UUID literal must be exactly {UUID_BYTE_LEN} bytes, got {}", bytes.len() ); } @@ -818,7 +819,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalUuid( )?)))); } if value.is_null() { - throw_runtime!("UUID literal bytes must not be null"); + throw_runtime!(InvalidArgument: "UUID literal bytes must not be null"); } let bytes = env.convert_byte_array(&value)?; Ok(into_raw(lit(uuid_scalar(&bytes)?))) @@ -830,8 +831,9 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalUuid( /// SAFETY: `ptr` must satisfy the contract of [`expr_ref`]. unsafe fn literal_scalar<'a>(ptr: jlong, role: &str) -> Result<&'a Scalar, JNIError> { let expr = unsafe { expr_ref(ptr) }; - expr.as_opt::() - .ok_or_else(|| vortex_err!("{role} must be a literal expression, got {expr}").into()) + expr.as_opt::().ok_or_else(|| { + vortex_err!(InvalidArgument: "{role} must be a literal expression, got {expr}").into() + }) } /// The dtype of the literal `ptr`, used as a type prototype, with `nullability` applied. @@ -910,8 +912,9 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalFixedSizeList is_null_flag: jboolean, ) -> jlong { try_or_throw(&mut env, |env| { - let size = u32::try_from(size) - .map_err(|_| vortex_err!("fixed-size list size must not be negative: {size}"))?; + let size = u32::try_from(size).map_err( + |_| vortex_err!(InvalidArgument: "fixed-size list size must not be negative: {size}"), + )?; let element_dtype = unsafe { prototype_dtype( element_type, @@ -929,7 +932,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalFixedSizeList let children = cast_literals(env, &elements, "fixed-size list element", &element_dtype)?; if children.len() != size as usize { throw_runtime!( - "fixed-size list literal of size {size} has {} elements", + InvalidArgument: "fixed-size list literal of size {size} has {} elements", children.len() ); } @@ -958,7 +961,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalStruct( let ptrs = unsafe { fields.get_elements(env, ReleaseMode::NoCopyBack) }?; if ptrs.len() != count { throw_runtime!( - "struct literal has {count} field names but {} fields", + InvalidArgument: "struct literal has {count} field names but {} fields", ptrs.len() ); } @@ -1020,7 +1023,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalMap( let values = cast_literals(env, &values, "map value", &value_dtype)?; if keys.len() != values.len() { throw_runtime!( - "map literal has {} keys but {} values", + InvalidArgument: "map literal has {} keys but {} values", keys.len(), values.len() ); @@ -1058,7 +1061,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalNull( 11 => DType::Primitive(PType::U32, Nullability::Nullable), 12 => DType::Primitive(PType::U64, Nullability::Nullable), 13 => DType::Primitive(PType::F16, Nullability::Nullable), - other => throw_runtime!("unknown null dtype tag: {other}"), + other => throw_runtime!(InvalidArgument: "unknown null dtype tag: {other}"), }; Ok(into_raw(lit(Scalar::null(dtype)))) }) diff --git a/vortex-jni/src/file.rs b/vortex-jni/src/file.rs index 552d36675c7..946b0e174e3 100644 --- a/vortex-jni/src/file.rs +++ b/vortex-jni/src/file.rs @@ -76,7 +76,7 @@ pub(crate) fn extract_metadata( let key_str = env.cast_local::(key_obj)?; let key = key_str.try_to_string(env)?; if val_obj.is_null() { - return Err(vortex_err!("null metadata value for key '{key}'").into()); + return Err(vortex_err!(InvalidArgument: "null metadata value for key '{key}'").into()); } let bytes = env.cast_local::(val_obj)?; segments.insert(key, ByteBuffer::from(env.convert_byte_array(&bytes)?)); @@ -183,14 +183,14 @@ pub extern "system" fn Java_dev_vortex_jni_NativeFiles_readMetadataFromReadable( try_or_throw(&mut env, |env| { let session = unsafe { session_ref(session_ptr) }; if readable.is_null() { - throw_runtime!("null readable"); + throw_runtime!(InvalidArgument: "null readable"); } let name: String = name.try_to_string(env)?; if name.is_empty() { - throw_runtime!("readable name must not be empty"); + throw_runtime!(InvalidArgument: "readable name must not be empty"); } - let length = - u64::try_from(length).map_err(|_| vortex_err!("negative readable length: {length}"))?; + let length = u64::try_from(length) + .map_err(|_| vortex_err!(InvalidArgument: "negative readable length: {length}"))?; let vm = env.get_java_vm()?; let readable = Arc::new(env.new_global_ref(&readable)?); diff --git a/vortex-jni/src/io/mod.rs b/vortex-jni/src/io/mod.rs index d1f2c14df44..cf6d286c98d 100644 --- a/vortex-jni/src/io/mod.rs +++ b/vortex-jni/src/io/mod.rs @@ -140,7 +140,7 @@ pub(crate) mod tests { } std::thread::sleep(Duration::from_millis(10)); } - vortex_bail!("JNI global reference leaked: weak reference still has a referent") + vortex_bail!(AssertionFailed: "JNI global reference leaked: weak reference still has a referent") } #[test] diff --git a/vortex-jni/src/io/read_at.rs b/vortex-jni/src/io/read_at.rs index 2c45fc347cd..182e7877c32 100644 --- a/vortex-jni/src/io/read_at.rs +++ b/vortex-jni/src/io/read_at.rs @@ -135,16 +135,16 @@ impl VortexReadAt for JavaReadable { let _permit = permit; let end = offset .checked_add(length as u64) - .ok_or_else(|| vortex_err!("read {offset}+{length} overflows u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "read {offset}+{length} overflows u64"))?; if end > len { - vortex_bail!("read {offset}..{end} out of bounds for file of length {len}"); + vortex_bail!(OutOfBounds: "read {offset}..{end} out of bounds for file of length {len}"); } // `java.nio.Buffer` capacities are Java ints. if i32::try_from(length).is_err() { - vortex_bail!("read length {length} exceeds ByteBuffer limit"); + vortex_bail!(Overflow: "read length {length} exceeds ByteBuffer limit"); } let joffset = i64::try_from(offset) - .map_err(|_| vortex_err!("read offset {offset} exceeds i64"))?; + .map_err(|_| vortex_err!(Overflow: "read offset {offset} exceeds i64"))?; let mut buffer = ByteBufferMut::with_capacity_aligned(length, alignment); with_jvm(&vm, |env| { @@ -176,7 +176,7 @@ impl VortexReadAt for JavaReadable { .i()?; if remaining != 0 { return Err(vortex_err!( - "readFully returned with {remaining} of {length} bytes unfilled" + Io: "readFully returned with {remaining} of {length} bytes unfilled" ) .into()); } @@ -252,7 +252,7 @@ impl JavaFileSystem { ) -> VortexResult<()> { match self.files.entry_ref(&path) { EntryRef::Occupied(_) => { - vortex_bail!("multiple Java readables normalize to path '{path}'"); + vortex_bail!(InvalidArgument: "multiple Java readables normalize to path '{path}'"); } EntryRef::Vacant(v) => v.insert(JavaFileEntry { readable, size }), }; @@ -294,10 +294,9 @@ impl FileSystem for JavaFileSystem { } async fn open_read(&self, path: &str) -> VortexResult> { - let entry = self - .files - .get(path) - .ok_or_else(|| vortex_err!("no Java readable registered for path '{path}'"))?; + let entry = self.files.get(path).ok_or_else( + || vortex_err!(NotFound: "no Java readable registered for path '{path}'"), + )?; Ok(Arc::new(JavaReadable::new( self.vm.clone(), Arc::clone(&entry.readable), @@ -308,6 +307,6 @@ impl FileSystem for JavaFileSystem { } async fn delete(&self, path: &str) -> VortexResult<()> { - vortex_bail!("delete('{path}') is not supported by a Java-readable file system") + vortex_bail!(InvalidArgument: "delete('{path}') is not supported by a Java-readable file system") } } diff --git a/vortex-jni/src/io/write.rs b/vortex-jni/src/io/write.rs index ffadf400e17..fd8fc607f94 100644 --- a/vortex-jni/src/io/write.rs +++ b/vortex-jni/src/io/write.rs @@ -137,12 +137,12 @@ mod tests { // exits, at which point the attachment is torn down automatically. let attached = thread_vm .is_thread_attached() - .map_err(|e| vortex_err!("is_thread_attached failed: {e}"))?; + .map_err(|e| vortex_err!(Other: "is_thread_attached failed: {e}"))?; assert!(attached, "write upcalls should leave the thread attached"); VortexResult::Ok(()) }) .join() - .map_err(|_| vortex_err!("writer thread panicked"))??; + .map_err(|_| vortex_err!(Other: "writer thread panicked"))??; let written = with_jvm(vm, |env| { let array = env diff --git a/vortex-jni/src/object_store.rs b/vortex-jni/src/object_store.rs index 24d9c80ed1f..ce30a64a3e1 100644 --- a/vortex-jni/src/object_store.rs +++ b/vortex-jni/src/object_store.rs @@ -55,8 +55,9 @@ pub(crate) fn make_object_store( // OpenDAL schemes take the services' own property names (e.g. `secret_id`), not environment // names, and mount at the URL authority, which makes the authority-keyed cache sound. if vortex_cloud::opendal::supports_scheme(url.scheme()) { - let path = Path::from_url_path(url.path()) - .map_err(|e| vortex_err!("cannot parse url path as object_store Path: {e}"))?; + let path = Path::from_url_path(url.path()).map_err( + |e| vortex_err!(InvalidArgument: "cannot parse url path as object_store Path: {e}"), + )?; let cache_key = url_cache_key(url, properties); { if let Some(cached) = OPENDAL_STORES.lock().get(&cache_key) { @@ -131,7 +132,7 @@ mod tests { use super::*; fn parse(url: &str) -> VortexResult { - Url::parse(url).map_err(|e| vortex_err!("{e}")) + Url::parse(url).map_err(|e| vortex_err!(InvalidArgument: "{e}")) } #[test] @@ -178,7 +179,7 @@ mod tests { assert_eq!(path.as_ref(), "dir/data file.vortex"); let mut debug_str = String::new(); - write!(&mut debug_str, "{store:?}").map_err(|e| vortex_err!("{e}"))?; + write!(&mut debug_str, "{store:?}").map_err(|e| vortex_err!(AssertionFailed: "{e}"))?; assert!(debug_str.contains("eu-central-9"), "{debug_str}"); assert!(debug_str.contains("localhost:9000"), "{debug_str}"); Ok(()) diff --git a/vortex-jni/src/runtime.rs b/vortex-jni/src/runtime.rs index 06d18de8a07..4822b7ff721 100644 --- a/vortex-jni/src/runtime.rs +++ b/vortex-jni/src/runtime.rs @@ -23,7 +23,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeRuntime_setWorkerThreads( ) { try_or_throw(&mut env, |_| { if n < 0 { - throw_runtime!("worker thread count must be non-negative"); + throw_runtime!(InvalidArgument: "worker thread count must be non-negative"); } POOL.set_workers(n as usize); Ok(()) diff --git a/vortex-jni/src/scan.rs b/vortex-jni/src/scan.rs index 125558256f9..82324ccfaef 100644 --- a/vortex-jni/src/scan.rs +++ b/vortex-jni/src/scan.rs @@ -104,7 +104,7 @@ fn build_scan_request( ))?), 3 => Selection::IncludeRoaring(deserialize_roaring_selection(selection_roaring_bitmap)?), 4 => Selection::ExcludeRoaring(deserialize_roaring_selection(selection_roaring_bitmap)?), - other => vortex_bail!("unknown selection include code: {other}"), + other => vortex_bail!(Serde: "unknown selection include code: {other}"), }; let row_range = (row_range_begin > 0 || row_range_end > 0).then_some(Range { @@ -128,7 +128,7 @@ fn build_scan_request( fn deserialize_roaring_selection(bytes: &[u8]) -> VortexResult { if bytes.is_empty() { - vortex_bail!("serialized roaring row selection must not be empty"); + vortex_bail!(Serde: "serialized roaring row selection must not be empty"); } let cursor = Cursor::new(bytes); Ok(roaring::RoaringTreemap::deserialize_from(cursor)?) @@ -162,7 +162,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeScan_create( let mut out: Vec = Vec::with_capacity(elements.len()); for v in elements.iter() { if *v < 0 { - throw_runtime!("row selection index must be non-negative"); + throw_runtime!(InvalidArgument: "row selection index must be non-negative"); } out.push(*v as u64); } @@ -215,12 +215,12 @@ pub extern "system" fn Java_dev_vortex_jni_NativeScan_arrowSchema( ) { try_or_throw(&mut env, |_| { if schema_addr == 0 { - throw_runtime!("null arrow schema address"); + throw_runtime!(InvalidArgument: "null arrow schema address"); } let session = unsafe { session_ref(session_ptr) }; let scan = unsafe { &*(pointer as *const NativeScan) }; let NativeScan::Pending(scan) = scan else { - throw_runtime!("schema unavailable: scan already started"); + throw_runtime!(InvalidArgument: "schema unavailable: scan already started"); }; let arrow_schema = session.arrow().to_arrow_schema(scan.dtype())?; let ffi_schema = FFI_ArrowSchema::try_from(&arrow_schema)?; @@ -242,7 +242,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeScan_partitionCount( try_or_throw(&mut env, |env| { let scan = unsafe { &*(pointer as *const NativeScan) }; let NativeScan::Pending(scan) = scan else { - throw_runtime!("partition count unavailable: scan already started"); + throw_runtime!(InvalidArgument: "partition count unavailable: scan already started"); }; let (rows, cardinality) = match scan.partition_count() { Precision::Exact(v) => (v as jlong, 2), @@ -312,7 +312,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativePartition_rowCount( try_or_throw(&mut env, |env| { let partition = unsafe { &*(pointer as *const NativePartition) }; let NativePartition::Pending(partition) = partition else { - throw_runtime!("row count unavailable: partition already started"); + throw_runtime!(InvalidArgument: "row count unavailable: partition already started"); }; let (rows, cardinality) = match partition.row_count() { Precision::Exact(v) => (v as jlong, 2), @@ -343,12 +343,12 @@ pub extern "system" fn Java_dev_vortex_jni_NativePartition_scanArrow( try_or_throw(&mut env, |_| { if stream_addr == 0 { - throw_runtime!("null arrow stream address"); + throw_runtime!(InvalidArgument: "null arrow stream address"); } let partition = match partition { NativePartition::Pending(p) => p, - _ => throw_runtime!("partition already consumed"), + _ => throw_runtime!(InvalidArgument: "partition already consumed"), }; let array_stream = partition.execute()?; diff --git a/vortex-jni/src/session.rs b/vortex-jni/src/session.rs index 8132fd8213a..82f3185ffd9 100644 --- a/vortex-jni/src/session.rs +++ b/vortex-jni/src/session.rs @@ -10,7 +10,6 @@ use vortex::VortexSessionDefault; use vortex::editions::CORE_2026_08_3; use vortex::editions::EditionSessionExt; use vortex::error::VortexExpect; -use vortex::error::vortex_err; use vortex::io::runtime::BlockingRuntime; use vortex::io::session::RuntimeSessionExt; use vortex::session::VortexSession; @@ -23,7 +22,6 @@ pub(crate) fn new_session() -> Box { let session = VortexSession::default().with_handle(RUNTIME.handle()); session .enable_edition(CORE_2026_08_3) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("JNI-supported draft core edition is registered"); vortex_parquet_variant::initialize(&session); vortex_spatial::initialize(&session); diff --git a/vortex-jni/src/writer.rs b/vortex-jni/src/writer.rs index 794aa1cc65c..027fd00c006 100644 --- a/vortex-jni/src/writer.rs +++ b/vortex-jni/src/writer.rs @@ -86,7 +86,7 @@ fn resolve_store( if url.scheme() == "file" { let path = url .to_file_path() - .map_err(|_| vortex_err!("invalid file URL: {url_or_path}"))?; + .map_err(|_| vortex_err!(InvalidArgument: "invalid file URL: {url_or_path}"))?; Ok(ResolvedStore::Path(path)) } else { let (store, path) = make_object_store(&url, properties)?; @@ -148,7 +148,7 @@ impl NativeWriter { .from_arrow_record_batch(batch, self.arrow_schema.as_ref())?; if !vortex_batch.dtype().eq(&self.write_schema) { return Err(vortex_err!( - "write schema mismatch: expected {}, got {}", + MismatchedTypes: "write schema mismatch: expected {}, got {}", self.write_schema, vortex_batch.dtype() )); @@ -156,7 +156,7 @@ impl NativeWriter { let mut sender = self.sender.clone(); RUNTIME .block_on(async move { sender.send(Ok(vortex_batch)).await }) - .map_err(|e| vortex_err!("failed to send batch: {e}")) + .map_err(|e| vortex_err!(Io: "failed to send batch: {e}")) } fn bytes_written(&self) -> u64 { @@ -172,13 +172,14 @@ impl NativeWriter { let handle = self .handle .take() - .ok_or_else(|| vortex_err!("writer already closed"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "writer already closed"))?; RUNTIME.block_on(handle) } } fn checked_jlong(value: u64, name: &str) -> VortexResult { - jlong::try_from(value).map_err(|_| vortex_err!("{name} exceeds Java long range: {value}")) + jlong::try_from(value) + .map_err(|_| vortex_err!(Overflow: "{name} exceeds Java long range: {value}")) } fn exact_count_jlong( @@ -254,7 +255,7 @@ fn scalar_to_java<'local>( ScalarValue::Decimal(value) => { let DType::Decimal(decimal_dtype, _) = scalar.dtype() else { return Err(JNIError::Vortex(vortex_err!( - "decimal statistic has non-decimal dtype {}", + MismatchedTypes: "decimal statistic has non-decimal dtype {}", scalar.dtype() ))); }; @@ -272,7 +273,7 @@ fn scalar_to_java<'local>( ScalarValue::Binary(value) => Ok(env.byte_array_from_slice(value.as_slice())?.into()), ScalarValue::Tuple(_) | ScalarValue::Union(_) | ScalarValue::Variant(_) => { Err(JNIError::Vortex(vortex_err!( - "cannot return nested scalar write statistic with dtype {} to Java", + NotImplemented: "cannot return nested scalar write statistic with dtype {} to Java", scalar.dtype() ))) } @@ -287,7 +288,7 @@ fn write_summary_to_java<'local>( let file_stats = summary.footer().statistics(); let columns = env.new_object_array( i32::try_from(column_sizes.len()) - .map_err(|_| vortex_err!("column count exceeds Java array range"))?, + .map_err(|_| vortex_err!(Overflow: "column count exceeds Java array range"))?, jni::jni_str!("dev/vortex/api/VortexColumnStatistics"), JObject::null(), )?; @@ -322,10 +323,9 @@ fn write_summary_to_java<'local>( jni::jni_str!("dev/vortex/api/VortexColumnStatistics"), jni::jni_sig!("(IJJJJLjava/lang/Object;Ljava/lang/Object;)V"), &[ - JValue::Int( - i32::try_from(column_index) - .map_err(|_| vortex_err!("column index exceeds Java int range"))?, - ), + JValue::Int(i32::try_from(column_index).map_err( + |_| vortex_err!(Overflow: "column index exceeds Java int range"), + )?), JValue::Long(checked_jlong(compressed_size, "compressed column size")?), JValue::Long(checked_jlong(summary.row_count(), "row count")?), JValue::Long(null_count), @@ -362,10 +362,10 @@ pub extern "system" fn Java_dev_vortex_jni_NativeWriter_create( ) -> jlong { try_or_throw(&mut env, |env| { if session_ptr == 0 { - throw_runtime!("null session pointer"); + throw_runtime!(InvalidArgument: "null session pointer"); } if arrow_schema_addr == 0 { - throw_runtime!("null arrow schema address"); + throw_runtime!(InvalidArgument: "null arrow schema address"); } let session = unsafe { session_ref(session_ptr) }; @@ -446,13 +446,13 @@ pub extern "system" fn Java_dev_vortex_jni_NativeWriter_createStream( ) -> jlong { try_or_throw(&mut env, |env| { if session_ptr == 0 { - throw_runtime!("null session pointer"); + throw_runtime!(InvalidArgument: "null session pointer"); } if arrow_schema_addr == 0 { - throw_runtime!("null arrow schema address"); + throw_runtime!(InvalidArgument: "null arrow schema address"); } if writable.is_null() { - throw_runtime!("null writable"); + throw_runtime!(InvalidArgument: "null writable"); } let session = unsafe { session_ref(session_ptr) }; @@ -511,8 +511,12 @@ pub extern "system" fn Java_dev_vortex_jni_NativeWriter_writeBatch( unsafe { FFI_ArrowArray::from_raw(arrow_array_addr as *mut FFI_ArrowArray) }; let ffi_schema = unsafe { &*(arrow_schema_addr as *const FFI_ArrowSchema) }; - let array_data = unsafe { arrow_array::ffi::from_ffi(ffi_array, ffi_schema) } - .map_err(|e| JNIError::Vortex(vortex_err!("failed to import Arrow FFI data: {e}")))?; + let array_data = + unsafe { arrow_array::ffi::from_ffi(ffi_array, ffi_schema) }.map_err(|e| { + JNIError::Vortex( + vortex_err!(InvalidArgument: "failed to import Arrow FFI data: {e}"), + ) + })?; let batch = RecordBatch::from(StructArray::from(array_data)); writer.write_record_batch(batch)?; diff --git a/vortex-json/src/dtype.rs b/vortex-json/src/dtype.rs index 2c5b30aeddd..d289ef9f341 100644 --- a/vortex-json/src/dtype.rs +++ b/vortex-json/src/dtype.rs @@ -31,14 +31,14 @@ impl ExtVTable for Json { } fn deserialize_metadata(&self, metadata: &[u8]) -> VortexResult { - vortex_ensure!(metadata.is_empty(), "JSON metadata must be empty"); + vortex_ensure!(metadata.is_empty(), Serde: "JSON metadata must be empty"); Ok(EmptyMetadata) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( ext_dtype.storage_dtype().is_utf8(), - "JSON storage dtype must be utf8, got {}", + MismatchedTypes: "JSON storage dtype must be utf8, got {}", ext_dtype.storage_dtype() ); Ok(()) @@ -49,7 +49,7 @@ impl ExtVTable for Json { storage_value: &'a ScalarValue, ) -> VortexResult> { let ScalarValue::Utf8(value) = storage_value else { - vortex_bail!("JSON storage scalar must be utf8, got {storage_value}"); + vortex_bail!(MismatchedTypes: "JSON storage scalar must be utf8, got {storage_value}"); }; Ok(value.as_str()) } diff --git a/vortex-json/src/json_to_variant.rs b/vortex-json/src/json_to_variant.rs index 32538b7ad3d..2ebd2562a24 100644 --- a/vortex-json/src/json_to_variant.rs +++ b/vortex-json/src/json_to_variant.rs @@ -121,7 +121,7 @@ impl ScalarFnVTable for JsonToVariant { let dtype = field .dtype .as_ref() - .ok_or_else(|| vortex_err!("ShreddingSpecField missing dtype")) + .ok_or_else(|| vortex_err!(NotFound: "ShreddingSpecField missing dtype")) .and_then(|dtype| DType::from_proto(dtype, session))?; Ok((path, dtype)) }) @@ -147,7 +147,7 @@ impl ScalarFnVTable for JsonToVariant { input_dtype .as_extension_opt() .is_some_and(|ext_dtype| ext_dtype.is::()), - "JsonToVariant input must be a Json extension, found {input_dtype}" + MismatchedTypes: "JsonToVariant input must be a Json extension, found {input_dtype}" ); Ok(DType::Variant(input_dtype.nullability())) @@ -169,7 +169,7 @@ impl ScalarFnVTable for JsonToVariant { // looping. let no_kernel = || { vortex_err!( - "json_to_variant requires a registered Variant encoding to build Variant values \ + InvalidArgument: "json_to_variant requires a registered Variant encoding to build Variant values \ from JSON, but none is registered with this session" ) }; @@ -185,7 +185,7 @@ impl ScalarFnVTable for JsonToVariant { input.execute::(ctx)?.into_array() } else { vortex_bail!( - "JsonToVariant input must be a Json extension, found {}", + MismatchedTypes: "JsonToVariant input must be a Json extension, found {}", input.dtype() ); }; @@ -243,7 +243,7 @@ impl ShreddingSpec { path.elements() .iter() .all(|element| matches!(element, VariantPathElement::Field(_))), - "ShreddingSpec paths must only contain object fields, found list index in {path}" + InvalidArgument: "ShreddingSpec paths must only contain object fields, found list index in {path}" ); } Ok(Self(fields)) diff --git a/vortex-json/src/lib.rs b/vortex-json/src/lib.rs index 0cf27f2db2f..15c06c82b9f 100644 --- a/vortex-json/src/lib.rs +++ b/vortex-json/src/lib.rs @@ -26,7 +26,6 @@ use vortex_array::scalar_fn::session::ScalarFnSessionExt; use vortex_arrow::ArrowSessionExt; use vortex_edition::EditionSessionExt; use vortex_error::VortexExpect; -use vortex_error::vortex_err; use vortex_session::VortexSession; /// Register JSON extension support with a session. @@ -42,15 +41,12 @@ pub fn initialize(session: &VortexSession) { session .editions() .declare_family(&editions::FAMILY) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("JSON edition family is valid"); session .register_edition(&editions::DECLARATION) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("JSON edition declaration is valid"); } session .enable_edition(editions::JSON_2026_08) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("JSON edition is registered"); } diff --git a/vortex-layout/examples/reverse_index/main.rs b/vortex-layout/examples/reverse_index/main.rs index a03a16d2d20..6114e5f9f7f 100644 --- a/vortex-layout/examples/reverse_index/main.rs +++ b/vortex-layout/examples/reverse_index/main.rs @@ -214,7 +214,7 @@ impl IndexVTable for ReverseIndex { let mut buffer = Vec::with_capacity(bitmap.serialized_size()); bitmap .serialize_into(&mut buffer) - .map_err(|err| vortex_err!("Failed to serialize postings: {err}"))?; + .map_err(|err| vortex_err!(Serde: "Failed to serialize postings: {err}"))?; lists.push(buffer); } @@ -244,7 +244,7 @@ impl IndexVTable for ReverseIndex { let postings = (0..lists.len()) .map(|idx| { RoaringBitmap::deserialize_from(lists.bytes_at(idx).as_slice()) - .map_err(|err| vortex_err!("Failed to deserialize postings: {err}")) + .map_err(|err| vortex_err!(Serde: "Failed to deserialize postings: {err}")) }) .collect::>()?; Ok(Entries { @@ -391,10 +391,10 @@ fn demo_session() -> VortexResult { .with::(); session .register_edition(&DEMO_EDITION_DECLARATION) - .map_err(|err| vortex_err!("{err}"))?; + .map_err(|err| vortex_err!(Io: "{err}"))?; session .enable_edition(DEMO_EDITION) - .map_err(|err| vortex_err!("{err}"))?; + .map_err(|err| vortex_err!(Io: "{err}"))?; session.indexes().register(ReverseIndex::new_ref()); Ok(session) } diff --git a/vortex-layout/src/arrays/shared/vtable.rs b/vortex-layout/src/arrays/shared/vtable.rs index e97505b0eb3..a1a3df88895 100644 --- a/vortex-layout/src/arrays/shared/vtable.rs +++ b/vortex-layout/src/arrays/shared/vtable.rs @@ -71,8 +71,8 @@ impl VTable for Shared { let source = slots[SharedSlots::SOURCE] .as_ref() .vortex_expect("SharedArray source slot must be present"); - vortex_error::vortex_ensure_eq!(source.dtype(), dtype, "SharedArray dtype mismatch"); - vortex_error::vortex_ensure_eq!(source.len(), len, "SharedArray len mismatch"); + vortex_error::vortex_ensure_eq!(source.dtype(), dtype, MismatchedTypes: "SharedArray dtype mismatch"); + vortex_error::vortex_ensure_eq!(source.len(), len, InvalidArgument: "SharedArray len mismatch"); Ok(()) } @@ -81,7 +81,7 @@ impl VTable for Shared { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!("SharedArray has no buffers") + vortex_panic!(OutOfBounds: "SharedArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -104,7 +104,7 @@ impl VTable for Shared { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_error::vortex_bail!("Shared array is not serializable") + vortex_error::vortex_bail!(Serde: "Shared array is not serializable") } fn deserialize( @@ -117,7 +117,7 @@ impl VTable for Shared { _children: &dyn vortex_array::serde::ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_error::vortex_bail!("Shared array is not serializable") + vortex_error::vortex_bail!(Serde: "Shared array is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-layout/src/children.rs b/vortex-layout/src/children.rs index a1a582f72c2..6079bbc0151 100644 --- a/vortex-layout/src/children.rs +++ b/vortex-layout/src/children.rs @@ -100,11 +100,11 @@ impl LayoutChildren for OwnedLayoutChildren { fn child(&self, idx: usize, dtype: &DType) -> VortexResult { if idx >= self.0.len() { - vortex_bail!("Child index out of bounds: {} of {}", idx, self.0.len()); + vortex_bail!(OutOfBounds: "Child index out of bounds: {} of {}", idx, self.0.len()); } let child = &self.0[idx]; if child.dtype() != dtype { - vortex_bail!("Child dtype mismatch: {} != {}", child.dtype(), dtype); + vortex_bail!(MismatchedTypes: "Child dtype mismatch: {} != {}", child.dtype(), dtype); } Ok(Arc::clone(child)) } @@ -199,7 +199,7 @@ impl ViewedLayoutChildren { let encoding_id = self .layout_read_ctx .resolve(fb_layout.encoding()) - .ok_or_else(|| vortex_err!("Encoding not found: {}", fb_layout.encoding()))?; + .ok_or_else(|| vortex_err!(NotFound: "Encoding not found: {}", fb_layout.encoding()))?; let children = fb_layout .children() @@ -234,7 +234,7 @@ impl LayoutChildren for ViewedLayoutChildren { fn child(&self, idx: usize, dtype: &DType) -> VortexResult { if idx >= self.nchildren() { - vortex_bail!("Child index out of bounds: {} of {}", idx, self.nchildren()); + vortex_bail!(OutOfBounds: "Child index out of bounds: {} of {}", idx, self.nchildren()); } let layout_ref = self.cache[idx].get_or_try_init(|| { @@ -258,13 +258,13 @@ impl LayoutChildren for ViewedLayoutChildren { .layout_read_ctx .resolve(fb_child.encoding()) .ok_or_else(|| { - vortex_err!("Unknown layout encoding index: {}", fb_child.encoding()) + vortex_err!(NotFound: "Unknown layout encoding index: {}", fb_child.encoding()) })?; let Some(encoding) = self.layouts.get(&encoding_id) else { if self.allow_unknown { return viewed_children.foreign_layout_from_fb(fb_child, dtype); } - vortex_bail!("Unknown layout encoding: {encoding_id}"); + vortex_bail!(NotFound: "Unknown layout encoding: {encoding_id}"); }; let build_ctx = LayoutBuildContext { diff --git a/vortex-layout/src/layouts/chunked/mod.rs b/vortex-layout/src/layouts/chunked/mod.rs index 459429046c2..02959600145 100644 --- a/vortex-layout/src/layouts/chunked/mod.rs +++ b/vortex-layout/src/layouts/chunked/mod.rs @@ -65,7 +65,7 @@ impl VTable for Chunked { ) -> VortexResult { let chunk_offsets = chunk_offsets(args.children)?; if chunk_offsets.last().copied() != Some(args.row_count) { - vortex_bail!("Chunked child row counts do not add up to parent row count"); + vortex_bail!(InvalidArgument: "Chunked child row counts do not add up to parent row count"); } Ok(ChunkedData { chunk_offsets }) } @@ -134,7 +134,7 @@ fn chunk_offsets(children: &dyn LayoutChildren) -> VortexResult> { offsets.push( offsets[idx] .checked_add(children.child_row_count(idx)) - .ok_or_else(|| vortex_err!("Chunked child row counts overflow"))?, + .ok_or_else(|| vortex_err!(Overflow: "Chunked child row counts overflow"))?, ); } Ok(offsets) diff --git a/vortex-layout/src/layouts/chunked/reader.rs b/vortex-layout/src/layouts/chunked/reader.rs index c658a83bb46..9e89d991f57 100644 --- a/vortex-layout/src/layouts/chunked/reader.rs +++ b/vortex-layout/src/layouts/chunked/reader.rs @@ -134,7 +134,7 @@ impl ChunkedReader { fn chunk_offset(&self, idx: usize) -> u64 { if idx >= self.layout.chunk_offsets.len() { vortex_panic!( - "Internal error: Chunk offset {idx} out of bounds (num_children: {}, num_offsets: {}). \ + AssertionFailed: "Internal error: Chunk offset {idx} out of bounds (num_children: {}, num_offsets: {}). \ This indicates a bug in ChunkedReader initialization or chunk_range calculation.", self.layout.nchildren(), self.layout.chunk_offsets.len() @@ -415,7 +415,7 @@ impl LayoutReader for ChunkedReader { // Split the mask over each chunk. let chunks: Vec<_> = FuturesOrdered::from_iter(chunk_evals).try_collect().await?; - vortex_ensure!(!chunks.is_empty(), "Empty chunks were checked earlier"); + vortex_ensure!(!chunks.is_empty(), AssertionFailed: "Empty chunks were checked earlier"); // If there is only one chunk, we can return it directly. if chunks.len() == 1 { diff --git a/vortex-layout/src/layouts/dict/mod.rs b/vortex-layout/src/layouts/dict/mod.rs index eee88f916d3..d7442ee3436 100644 --- a/vortex-layout/src/layouts/dict/mod.rs +++ b/vortex-layout/src/layouts/dict/mod.rs @@ -74,7 +74,7 @@ impl VTable for Dict { vortex_ensure_eq!( args.children.nchildren(), 2, - "DictLayout expects exactly 2 children" + InvalidArgument: "DictLayout expects exactly 2 children" ); let codes_nullable = metadata .is_nullable_codes @@ -86,7 +86,7 @@ impl VTable for Dict { vortex_ensure_eq!( codes.row_count(), args.row_count, - "Dictionary codes row count does not match parent" + InvalidArgument: "Dictionary codes row count does not match parent" ); Ok(DictData { codes_dtype, @@ -98,7 +98,7 @@ impl VTable for Dict { match idx { 0 => Ok(layout.dtype().clone()), 1 => Ok(layout.codes_dtype.clone()), - _ => vortex_bail!("Dict child index out of bounds: {idx}"), + _ => vortex_bail!(OutOfBounds: "Dict child index out of bounds: {idx}"), } } @@ -106,7 +106,7 @@ impl VTable for Dict { match idx { 0 => LayoutChildType::Auxiliary("values".into()), 1 => LayoutChildType::Transparent("codes".into()), - _ => vortex_panic!("Dict child index out of bounds: {idx}"), + _ => vortex_panic!(OutOfBounds: "Dict child index out of bounds: {idx}"), } } diff --git a/vortex-layout/src/layouts/dict/writer.rs b/vortex-layout/src/layouts/dict/writer.rs index 7808777a8c2..e0f562bc11e 100644 --- a/vortex-layout/src/layouts/dict/writer.rs +++ b/vortex-layout/src/layouts/dict/writer.rs @@ -423,7 +423,7 @@ impl Stream for DictionaryTransformer { // Receiver dropped, close this group self.active_codes_tx = None; if let Some(values_tx) = self.active_values_tx.take() { - drop(values_tx.send(Err(vortex_err!("values receiver dropped")))); + drop(values_tx.send(Err(vortex_err!(Io: "values receiver dropped")))); } } Poll::Pending => { @@ -467,7 +467,7 @@ impl Stream for DictionaryTransformer { let values_future = async move { values_rx .await - .map_err(|e| vortex_err!("values sender dropped: {}", e)) + .map_err(|e| vortex_err!(Io: "values sender dropped: {}", e)) .flatten() } .boxed(); @@ -501,7 +501,7 @@ impl Stream for DictionaryTransformer { Poll::Ready(None) => { // Handle any incomplete group if let Some(values_tx) = self.active_values_tx.take() { - drop(values_tx.send(Err(vortex_err!("Incomplete dictionary group")))); + drop(values_tx.send(Err(vortex_err!(Io: "Incomplete dictionary group")))); } self.active_codes_tx = None; return Poll::Ready(None); diff --git a/vortex-layout/src/layouts/file_stats.rs b/vortex-layout/src/layouts/file_stats.rs index 97669808eef..dbbba0fd939 100644 --- a/vortex-layout/src/layouts/file_stats.rs +++ b/vortex-layout/src/layouts/file_stats.rs @@ -466,7 +466,7 @@ impl FileStatsAccumulator { if dtype.nullability() == Nullability::Nullable { // top level dtype could be nullable, but we don't support it yet vortex_panic!( - "FileStatsAccumulator temporarily does not support nullable top-level structs, got: {}. Use Validity::NonNullable", + NotImplemented: "FileStatsAccumulator temporarily does not support nullable top-level structs, got: {}. Use Validity::NonNullable", dtype ); } diff --git a/vortex-layout/src/layouts/flat/mod.rs b/vortex-layout/src/layouts/flat/mod.rs index 6913d2fc0c4..b860ee8bf1b 100644 --- a/vortex-layout/src/layouts/flat/mod.rs +++ b/vortex-layout/src/layouts/flat/mod.rs @@ -83,10 +83,10 @@ impl VTable for Flat { metadata: &FlatLayoutMetadata, ) -> VortexResult { if args.segment_ids.len() != 1 { - vortex_bail!("Flat layout must have exactly one segment ID"); + vortex_bail!(InvalidArgument: "Flat layout must have exactly one segment ID"); } if args.children.nchildren() != 0 { - vortex_bail!("Flat layout must not have children"); + vortex_bail!(InvalidArgument: "Flat layout must not have children"); } Ok(FlatData { segment_id: args.segment_ids[0], @@ -99,11 +99,11 @@ impl VTable for Flat { } fn child_dtype(_layout: &Layout, idx: usize) -> VortexResult { - vortex_bail!("Flat layout has no child {idx}") + vortex_bail!(OutOfBounds: "Flat layout has no child {idx}") } fn child_type(_layout: &Layout, idx: usize) -> LayoutChildType { - vortex_panic!("Flat layout has no child {idx}") + vortex_panic!(OutOfBounds: "Flat layout has no child {idx}") } fn new_reader( diff --git a/vortex-layout/src/layouts/flat/writer.rs b/vortex-layout/src/layouts/flat/writer.rs index ac8bd44045a..e6272980cc0 100644 --- a/vortex-layout/src/layouts/flat/writer.rs +++ b/vortex-layout/src/layouts/flat/writer.rs @@ -157,7 +157,7 @@ impl LayoutStrategy for FlatLayoutStrategy { let segment_id = segment_sink.write(sequence_id, buffers).await?; let None = stream.next().await else { - vortex_bail!("flat layout received stream with more than a single chunk"); + vortex_bail!(InvalidArgument: "flat layout received stream with more than a single chunk"); }; Ok(FlatLayout::new_with_metadata( row_count, diff --git a/vortex-layout/src/layouts/foreign/mod.rs b/vortex-layout/src/layouts/foreign/mod.rs index c2e32ffa253..c33126f604d 100644 --- a/vortex-layout/src/layouts/foreign/mod.rs +++ b/vortex-layout/src/layouts/foreign/mod.rs @@ -172,7 +172,7 @@ impl DynLayout for ForeignLayout { _ctx: &crate::LayoutReaderContext, ) -> VortexResult { vortex_bail!( - "Cannot read unknown layout encoding '{}'", + NotFound: "Cannot read unknown layout encoding '{}'", self.encoding.id() ) } diff --git a/vortex-layout/src/layouts/indexed/mod.rs b/vortex-layout/src/layouts/indexed/mod.rs index d668e7b9363..d82a9a32cd7 100644 --- a/vortex-layout/src/layouts/indexed/mod.rs +++ b/vortex-layout/src/layouts/indexed/mod.rs @@ -186,26 +186,26 @@ impl IndexPartitioning { fn validate(&self, id: IndexId, data_row_count: u64, index_row_count: u64) -> VortexResult<()> { vortex_ensure!( self.partition_len > 0, - "Index {id} has a zero partition length" + InvalidArgument: "Index {id} has a zero partition length" ); let expected = data_row_count.div_ceil(self.partition_len); vortex_ensure!( self.index_ends.len() as u64 == expected, - "Index {id} has {} partitions, expected {expected} for {data_row_count} rows at {} rows each", + InvalidArgument: "Index {id} has {} partitions, expected {expected} for {data_row_count} rows at {} rows each", self.index_ends.len(), self.partition_len ); vortex_ensure!( self.index_ends.is_sorted(), - "Index {id} partition ends must be non-decreasing" + InvalidArgument: "Index {id} partition ends must be non-decreasing" ); vortex_ensure!( self.index_ends.last().copied().unwrap_or(0) == index_row_count, - "Index {id} partition ends do not cover its {index_row_count}-row child" + InvalidArgument: "Index {id} partition ends do not cover its {index_row_count}-row child" ); vortex_ensure!( self.declined.max().is_none_or(|p| u64::from(p) < expected), - "Index {id} declines a partition past its last" + InvalidArgument: "Index {id} declines a partition past its last" ); Ok(()) } @@ -288,14 +288,14 @@ impl IndexedLayout { ) -> VortexResult { vortex_ensure!( index_layouts.len() == indexes.len(), - "IndexedLayout got {} index children for {} specs", + InvalidArgument: "IndexedLayout got {} index children for {} specs", index_layouts.len(), indexes.len() ); for (layout, spec) in index_layouts.iter().zip(&indexes) { vortex_ensure!( layout.dtype() == &spec.index_dtype, - "Index child dtype {} does not match spec dtype {} for {}", + MismatchedTypes: "Index child dtype {} does not match spec dtype {} for {}", layout.dtype(), spec.index_dtype, spec.id @@ -375,7 +375,7 @@ impl VTable for Indexed { ) -> VortexResult { vortex_ensure!( args.children.nchildren() == 1 + metadata.indexes.len(), - "IndexedLayout expects {} children (data + {} indexes), got {}", + InvalidArgument: "IndexedLayout expects {} children (data + {} indexes), got {}", 1 + metadata.indexes.len(), metadata.indexes.len(), args.children.nchildren() @@ -392,7 +392,9 @@ impl VTable for Indexed { .as_ref() .map(|dtype| DType::from_proto(dtype, args.session)) .transpose()? - .ok_or_else(|| vortex_err!("Index spec {} is missing its dtype", spec.id))?; + .ok_or_else( + || vortex_err!(Serde: "Index spec {} is missing its dtype", spec.id), + )?; let id = IndexId::from(spec.id.as_str()); let partitioning = spec @@ -440,7 +442,7 @@ impl VTable for Indexed { 0 => Ok(layout.dtype().clone()), _ => { let Some(spec) = layout.indexes.get(slot - 1) else { - vortex_bail!("Invalid child index: {}", slot); + vortex_bail!(OutOfBounds: "Invalid child index: {}", slot); }; Ok(spec.index_dtype.clone()) } @@ -452,7 +454,7 @@ impl VTable for Indexed { 0 => LayoutChildType::Transparent("data".into()), _ => match layout.indexes.get(slot - 1) { Some(spec) => LayoutChildType::Auxiliary(format!("index:{}", spec.id).into()), - None => vortex_panic!("Invalid child index: {}", slot), + None => vortex_panic!(OutOfBounds: "Invalid child index: {}", slot), }, } } @@ -525,16 +527,16 @@ impl DeserializeMetadata for IndexedMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { let Some((&version, proto_bytes)) = metadata.split_first() else { - vortex_bail!("Indexed metadata missing protobuf version"); + vortex_bail!(Serde: "Indexed metadata missing protobuf version"); }; vortex_ensure!( version == INDEXED_METADATA_VERSION, - "Unsupported indexed metadata version: {}", + Serde: "Unsupported indexed metadata version: {}", version ); let proto = IndexedMetadataProto::decode(proto_bytes) - .map_err(|err| vortex_err!("Failed to decode indexed metadata: {err}"))?; + .map_err(|err| vortex_err!(Serde: "Failed to decode indexed metadata: {err}"))?; Ok(Self { indexes: proto.indexes.into(), }) diff --git a/vortex-layout/src/layouts/indexed/test_harness.rs b/vortex-layout/src/layouts/indexed/test_harness.rs index 90a126b83d2..716e4f197cb 100644 --- a/vortex-layout/src/layouts/indexed/test_harness.rs +++ b/vortex-layout/src/layouts/indexed/test_harness.rs @@ -29,17 +29,17 @@ pub fn check_roundtrip( let parsed = vtable.deserialize_options(&blob)?; vortex_ensure!( vtable.serialize_options(&parsed) == blob, - "Index {} options do not re-serialize to the same blob", + AssertionFailed: "Index {} options do not re-serialize to the same blob", vtable.id() ); - let declared = vtable - .index_dtype(data_dtype, options) - .ok_or_else(|| vortex_err!("Index {} cannot index {data_dtype}", vtable.id()))?; + let declared = vtable.index_dtype(data_dtype, options).ok_or_else( + || vortex_err!(AssertionFailed: "Index {} cannot index {data_dtype}", vtable.id()), + )?; let encoded = vtable.encode(chunk, options, ctx)?; vortex_ensure!( encoded.dtype() == &declared, - "Index {} encoded dtype {}, but declared {declared}", + AssertionFailed: "Index {} encoded dtype {}, but declared {declared}", vtable.id(), encoded.dtype() ); diff --git a/vortex-layout/src/layouts/indexed/tests.rs b/vortex-layout/src/layouts/indexed/tests.rs index f2f28b54509..cd0fa567b49 100644 --- a/vortex-layout/src/layouts/indexed/tests.rs +++ b/vortex-layout/src/layouts/indexed/tests.rs @@ -149,7 +149,7 @@ fn partitioned_strategy(configs: Vec) -> IndexedStrategy { fn partitioned(config: IndexConfig, partition_len: u64) -> VortexResult { let partition_len = NonZeroU64::new(partition_len) - .ok_or_else(|| vortex_err!("partition length must be non-zero"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "partition length must be non-zero"))?; Ok(config.with_partition_len(partition_len)) } @@ -336,7 +336,7 @@ async fn layout_carries_one_auxiliary_child_per_index() -> VortexResult<()> { // Index content is an ordinary layout tree, so it inherits chunking and zone maps for free. let index_child = layout .slot(1)? - .ok_or_else(|| vortex_err!("an exact-value index was configured"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "an exact-value index was configured"))?; assert_eq!( index_child .dtype() @@ -512,7 +512,7 @@ async fn writer_rejects_an_index_that_does_not_match_its_declared_dtype() -> Vor .await; let Err(err) = result else { - vortex_bail!("writing an index that does not match its declared dtype should fail"); + vortex_bail!(AssertionFailed: "writing an index that does not match its declared dtype should fail"); }; assert!(err.to_string().contains("declared"), "{err}"); Ok(()) @@ -551,10 +551,10 @@ async fn index_whose_stored_dtype_no_longer_matches_its_kind_is_skipped() -> Vor ); let data = layout .slot(0)? - .ok_or_else(|| vortex_err!("indexed layout has a data child"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "indexed layout has a data child"))?; let index = layout .slot(1)? - .ok_or_else(|| vortex_err!("an index was configured"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "an index was configured"))?; let changed = IndexedLayout::try_new(data, vec![index], vec![changed])?.into_layout(); let reader = text_reader(&session, &changed, segments)?; @@ -578,7 +578,7 @@ fn exact_value_index_roundtrips( let vtable = ExactValueIndex::new_ref(); let kind = vtable .as_opt::() - .ok_or_else(|| vortex_err!("new_ref makes an ExactValueIndex"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "new_ref makes an ExactValueIndex"))?; let mut ctx = new_session().create_execution_ctx(); check_roundtrip( kind, @@ -594,7 +594,7 @@ fn fixed_superset_index_roundtrips() -> VortexResult<()> { let vtable = FixedSupersetIndex::new_ref("test.idx.fixed", RoaringBitmap::new()); let kind = vtable .as_opt::() - .ok_or_else(|| vortex_err!("new_ref makes a FixedSupersetIndex"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "new_ref makes a FixedSupersetIndex"))?; let mut ctx = new_session().create_execution_ctx(); check_roundtrip( kind, @@ -648,7 +648,7 @@ fn partitioning(layout: &LayoutRef) -> VortexResult { layout.as_::().indexes()[0] .partitioning() .cloned() - .ok_or_else(|| vortex_err!("index should be partitioned")) + .ok_or_else(|| vortex_err!(AssertionFailed: "index should be partitioned")) } /// Partitioning changes how the index is built and probed, never what it answers: every value @@ -673,7 +673,7 @@ async fn partitioned_index_answers_like_an_unpartitioned_one( // One data chunk, several index partitions: the two widths really are independent. let data = layout .slot(0)? - .ok_or_else(|| vortex_err!("indexed layout has a data child"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "indexed layout has a data child"))?; assert!(data.as_opt::().is_some()); assert_eq!( partitioning(&layout)?.index_ends().len() as u64, @@ -740,7 +740,7 @@ impl CountingFixture { let index = layout .slot(1)? - .ok_or_else(|| vortex_err!("an index was configured"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "an index was configured"))?; // Each partition is its own index-child chunk, so chunk `p` holds partition `p`. assert_eq!(index.nslots(), 3); let partitions = (0..index.nslots()) @@ -748,7 +748,7 @@ impl CountingFixture { segment_ids( &index .slot(p)? - .ok_or_else(|| vortex_err!("partition {p} has a chunk"))?, + .ok_or_else(|| vortex_err!(AssertionFailed: "partition {p} has a chunk"))?, ) }) .collect::>()?; @@ -857,7 +857,8 @@ async fn probing_loads_only_the_index_chunks_its_filter_cannot_prune() -> Vortex ChunkedLayoutStrategy::new(FlatLayoutStrategy::default()), FlatLayoutStrategy::default(), ZonedLayoutOptions { - block_size: NonZeroUsize::new(2).ok_or_else(|| vortex_err!("non-zero"))?, + block_size: NonZeroUsize::new(2) + .ok_or_else(|| vortex_err!(AssertionFailed: "non-zero"))?, ..Default::default() }, ), @@ -885,10 +886,10 @@ async fn probing_loads_only_the_index_chunks_its_filter_cannot_prune() -> Vortex let index = layout .slot(1)? - .ok_or_else(|| vortex_err!("an index was configured"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "an index was configured"))?; let chunks = index .slot(0)? - .ok_or_else(|| vortex_err!("the zoned index child has data"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "the zoned index child has data"))?; let chunk_count = usize::try_from(INDEX_ROWS)? / 2; assert_eq!(chunks.nslots(), chunk_count); let chunk_segments = (0..chunk_count) @@ -896,7 +897,7 @@ async fn probing_loads_only_the_index_chunks_its_filter_cannot_prune() -> Vortex segment_ids( &chunks .slot(chunk)? - .ok_or_else(|| vortex_err!("chunk {chunk} exists"))?, + .ok_or_else(|| vortex_err!(AssertionFailed: "chunk {chunk} exists"))?, ) }) .collect::>>()?; @@ -971,13 +972,13 @@ async fn probing_skips_partitions_the_selection_rules_out( let (send, recv) = oneshot::channel(); let pending = MaskFuture::new(ROWS.len(), async move { recv.await - .map_err(|_| vortex_err!("selection sender dropped")) + .map_err(|_| vortex_err!(AssertionFailed: "selection sender dropped")) }); let evaluated = reader.filter_evaluation(&all, &filter, pending)?; // Nothing can be skipped before the selection is known, so nothing is probed yet. assert!(fixture.index_requested().is_empty()); send.send(selection.clone()) - .map_err(|_| vortex_err!("filter dropped the selection"))?; + .map_err(|_| vortex_err!(AssertionFailed: "filter dropped the selection"))?; evaluated.await? } }; @@ -1239,7 +1240,7 @@ mod exact_value { let mut buffer = Vec::with_capacity(bitmap.serialized_size()); bitmap .serialize_into(&mut buffer) - .map_err(|err| vortex_err!("Failed to serialize postings: {err}"))?; + .map_err(|err| vortex_err!(Serde: "Failed to serialize postings: {err}"))?; lists.push(buffer); } @@ -1280,8 +1281,9 @@ mod exact_value { .keys .push(String::from_utf8_lossy(keys.bytes_at(idx).as_slice()).into_owned()); decoded.postings.push( - RoaringBitmap::deserialize_from(lists.bytes_at(idx).as_slice()) - .map_err(|err| vortex_err!("Failed to deserialize postings: {err}"))?, + RoaringBitmap::deserialize_from(lists.bytes_at(idx).as_slice()).map_err( + |err| vortex_err!(Serde: "Failed to deserialize postings: {err}"), + )?, ); } Ok(decoded) @@ -1419,7 +1421,7 @@ mod exact_value { _options: &(), _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!("a declining index never builds content to encode") + vortex_bail!(AssertionFailed: "a declining index never builds content to encode") } fn decode( diff --git a/vortex-layout/src/layouts/indexed/writer.rs b/vortex-layout/src/layouts/indexed/writer.rs index 67769334f96..066c1f112f3 100644 --- a/vortex-layout/src/layouts/indexed/writer.rs +++ b/vortex-layout/src/layouts/indexed/writer.rs @@ -182,7 +182,7 @@ impl PartitionBuilder for TypedPartitionBuilder { let array = vtable.encode(chunk, &options, &mut ctx)?; vortex_ensure!( array.dtype() == &index_dtype, - "Index {} encoded a chunk of dtype {}, but the index kind declared {index_dtype}", + MismatchedTypes: "Index {} encoded a chunk of dtype {}, but the index kind declared {index_dtype}", vtable.id(), array.dtype() ); @@ -392,7 +392,7 @@ impl IndexContent { // One spec records one options blob, so partitions may not disagree about it. Some(first) => vortex_ensure!( *first == partition_options, - "Index {id} partition {partition} finished with different options than earlier partitions" + InvalidArgument: "Index {id} partition {partition} finished with different options than earlier partitions" ), } built.push((partition, content)); @@ -460,14 +460,14 @@ impl LayoutStrategy for IndexedStrategy { }; let Some(block_len) = self.data_block_len.filter(|len| *len > 0) else { vortex_bail!( - "Index {} is partitioned every {partition_len} rows, which requires a non-zero \ + InvalidArgument: "Index {} is partitioned every {partition_len} rows, which requires a non-zero \ data block length (IndexedStrategy::with_data_block_len)", config.vtable.id() ); }; vortex_ensure!( partition_len.get() % block_len == 0, - "Index {} partition length {partition_len} must be a multiple of the data block \ + InvalidArgument: "Index {} partition length {partition_len} must be a multiple of the data block \ length {block_len}", config.vtable.id() ); diff --git a/vortex-layout/src/layouts/list/mod.rs b/vortex-layout/src/layouts/list/mod.rs index f5c8c618b15..75b793f5eb8 100644 --- a/vortex-layout/src/layouts/list/mod.rs +++ b/vortex-layout/src/layouts/list/mod.rs @@ -79,17 +79,16 @@ impl VTable for List { metadata: &ListLayoutMetadata, ) -> VortexResult { ListLayout::validate_children(args.dtype, args.children.nchildren())?; - let elements_dtype = args - .dtype - .as_list_element_opt() - .ok_or_else(|| vortex_err!("ListLayout requires a List dtype, got {}", args.dtype))?; + let elements_dtype = args.dtype.as_list_element_opt().ok_or_else( + || vortex_err!(InvalidArgument: "ListLayout requires a List dtype, got {}", args.dtype), + )?; args.children.child(ELEMENTS_CHILD_INDEX, elements_dtype)?; let offsets_dtype = DType::Primitive(metadata.offsets_ptype(), Nullability::NonNullable); let offsets = args.children.child(OFFSETS_CHILD_INDEX, &offsets_dtype)?; vortex_ensure_eq!( offsets.row_count().saturating_sub(1), args.row_count, - "List offsets row count does not match parent" + InvalidArgument: "List offsets row count does not match parent" ); if args.dtype.is_nullable() { let validity = args @@ -98,7 +97,7 @@ impl VTable for List { vortex_ensure_eq!( validity.row_count(), args.row_count, - "List validity row count does not match parent" + InvalidArgument: "List validity row count does not match parent" ); } Ok(ListData { @@ -125,7 +124,7 @@ impl VTable for List { .dtype() .as_list_element_opt() .map(|dtype| dtype.as_ref().clone()) - .ok_or_else(|| vortex_err!("ListLayout requires a List dtype")), + .ok_or_else(|| vortex_err!(InvalidArgument: "ListLayout requires a List dtype")), OFFSETS_CHILD_INDEX => Ok(DType::Primitive( layout.offsets_ptype, Nullability::NonNullable, @@ -133,7 +132,7 @@ impl VTable for List { VALIDITY_CHILD_INDEX if layout.dtype().is_nullable() => { Ok(DType::Bool(Nullability::NonNullable)) } - _ => vortex_bail!("Invalid child index {idx} for ListLayout"), + _ => vortex_bail!(OutOfBounds: "Invalid child index {idx} for ListLayout"), } } @@ -144,7 +143,7 @@ impl VTable for List { VALIDITY_CHILD_INDEX if layout.dtype().is_nullable() => { LayoutChildType::Auxiliary("validity".into()) } - _ => vortex_panic!("Invalid child index {idx} for ListLayout"), + _ => vortex_panic!(OutOfBounds: "Invalid child index {idx} for ListLayout"), } } @@ -192,13 +191,13 @@ impl Layout { /// Returns the elements child. pub fn elements(&self) -> VortexResult { self.slot(ELEMENTS_CHILD_INDEX)? - .ok_or_else(|| vortex_err!("ListLayout elements slot is absent")) + .ok_or_else(|| vortex_err!(AssertionFailed: "ListLayout elements slot is absent")) } /// Returns the offsets child. pub fn offsets(&self) -> VortexResult { self.slot(OFFSETS_CHILD_INDEX)? - .ok_or_else(|| vortex_err!("ListLayout offsets slot is absent")) + .ok_or_else(|| vortex_err!(AssertionFailed: "ListLayout offsets slot is absent")) } /// Returns the optional validity child. diff --git a/vortex-layout/src/layouts/list/writer.rs b/vortex-layout/src/layouts/list/writer.rs index 8e3a25cf407..c5dbab7a3e9 100644 --- a/vortex-layout/src/layouts/list/writer.rs +++ b/vortex-layout/src/layouts/list/writer.rs @@ -267,7 +267,7 @@ async fn transpose_list_column( .is_err() || offsets_tx.send(Ok((sp.advance(), offsets))).await.is_err() { - vortex_bail!("list child writer finished before all chunks were sent"); + vortex_bail!(Io: "list child writer finished before all chunks were sent"); } if let Some(validity_tx) = &validity_tx { let validity = validity @@ -278,7 +278,7 @@ async fn transpose_list_column( .await .is_err() { - vortex_bail!("list validity writer finished before all chunks were sent"); + vortex_bail!(Io: "list validity writer finished before all chunks were sent"); } } } diff --git a/vortex-layout/src/layouts/repartition.rs b/vortex-layout/src/layouts/repartition.rs index b213ddd7749..03865377c53 100644 --- a/vortex-layout/src/layouts/repartition.rs +++ b/vortex-layout/src/layouts/repartition.rs @@ -280,7 +280,7 @@ fn exact_size(chunk: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { return Ok(chunk.nbytes()); } let size = uncompressed_size_in_bytes(chunk, UncompressedSizeOpts::exact(), ctx)?; - u64::try_from(size).map_err(|e| vortex_err!("block size does not fit in u64: {e}")) + u64::try_from(size).map_err(|e| vortex_err!(Overflow: "block size does not fit in u64: {e}")) } #[cfg(test)] diff --git a/vortex-layout/src/layouts/row_idx/expr.rs b/vortex-layout/src/layouts/row_idx/expr.rs index 659eb1f69d7..4b10fbe1387 100644 --- a/vortex-layout/src/layouts/row_idx/expr.rs +++ b/vortex-layout/src/layouts/row_idx/expr.rs @@ -59,7 +59,7 @@ impl ScalarFnVTable for RowIdx { _ctx: &mut vortex_array::ExecutionCtx, ) -> VortexResult { vortex_bail!( - "RowIdxExpr should not be executed directly, use it in the context of a Vortex scan and it will be substituted for a row index array" + AssertionFailed: "RowIdxExpr should not be executed directly, use it in the context of a Vortex scan and it will be substituted for a row index array" ); } diff --git a/vortex-layout/src/layouts/struct_/mod.rs b/vortex-layout/src/layouts/struct_/mod.rs index 4506a0b6e20..a973943e2ba 100644 --- a/vortex-layout/src/layouts/struct_/mod.rs +++ b/vortex-layout/src/layouts/struct_/mod.rs @@ -70,7 +70,7 @@ impl VTable for Struct { vortex_ensure_eq!( child_row_count, args.row_count, - "Struct child {idx} row count does not match parent" + InvalidArgument: "Struct child {idx} row count does not match parent" ); } Ok(()) @@ -164,12 +164,12 @@ impl Layout { continue; }; let Field::Name(field_name) = field else { - vortex_bail!("Expected field name, got {field:?}"); + vortex_bail!(MismatchedTypes: "Expected field name, got {field:?}"); }; let idx = self .struct_fields() .find(field_name) - .ok_or_else(|| vortex_err!("Field not found: {field_name}"))?; + .ok_or_else(|| vortex_err!(NotFound: "Field not found: {field_name}"))?; per_child(path.clone().step_into()?, idx)?; } Ok(()) @@ -178,9 +178,9 @@ impl Layout { fn validate_children(dtype: &DType, nchildren: usize) -> VortexResult<()> { let fields = dtype .as_struct_fields_opt() - .ok_or_else(|| vortex_err!("Expected struct dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected struct dtype"))?; let expected = fields.nfields() + usize::from(dtype.is_nullable()); - vortex_ensure_eq!(nchildren, expected); + vortex_ensure_eq!(nchildren, expected, InvalidArgument); Ok(()) } @@ -193,7 +193,7 @@ impl Layout { dtype .as_struct_fields_opt() .and_then(|fields| fields.field_by_index(slot - 1)) - .ok_or_else(|| vortex_err!("Missing field {}", slot - 1)) + .ok_or_else(|| vortex_err!(NotFound: "Missing field {}", slot - 1)) } } } diff --git a/vortex-layout/src/layouts/struct_/reader.rs b/vortex-layout/src/layouts/struct_/reader.rs index 9d9630473c8..d595bdd5c52 100644 --- a/vortex-layout/src/layouts/struct_/reader.rs +++ b/vortex-layout/src/layouts/struct_/reader.rs @@ -165,9 +165,9 @@ impl StructReader { fn field_reader(&self, item: &Item) -> VortexResult<&LayoutReaderRef> { let name = match item { Item::Validity => { - return self - .validity()? - .ok_or_else(|| vortex_err!("Non-nullable struct layout has no validity")); + return self.validity()?.ok_or_else( + || vortex_err!(AssertionFailed: "Non-nullable struct layout has no validity"), + ); } Item::Field(name) => name, }; @@ -176,7 +176,7 @@ impl StructReader { .as_ref() .and_then(|lookup| lookup.get(name).copied()) .or_else(|| self.struct_fields().find(name)) - .ok_or_else(|| vortex_err!("Field {} not found in struct layout", name))?; + .ok_or_else(|| vortex_err!(NotFound: "Field {} not found in struct layout", name))?; self.field_reader_by_index(idx) } @@ -284,7 +284,7 @@ impl StructReader { let field_index = |name: &FieldName| { fields .find(name) - .ok_or_else(|| vortex_err!("Field {name} not found in struct layout")) + .ok_or_else(|| vortex_err!(NotFound: "Field {name} not found in struct layout")) }; let (names, indices) = if expr.is_root() { @@ -320,7 +320,7 @@ impl StructReader { .map(|idx: usize| -> VortexResult<_> { let dtype = fields .field_by_index(idx) - .ok_or_else(|| vortex_err!("Field index {idx} out of bounds"))?; + .ok_or_else(|| vortex_err!(OutOfBounds: "Field index {idx} out of bounds"))?; Ok((idx, BoundExpression::new_root(dtype))) }) .try_collect()?; @@ -426,7 +426,7 @@ fn expand_struct_root( if let Some(field_name) = scalar_fn.as_opt::() { let idx = fields.find(field_name).ok_or_else(|| { - vortex_err!("Field {field_name} not found while expanding struct root") + vortex_err!(NotFound: "Field {field_name} not found while expanding struct root") })?; let child = packed.children()[idx].clone(); return Ok(Transformed { @@ -650,7 +650,7 @@ impl LayoutReader for StructReader { ), Partitioned::Direct(_) => { vortex_bail!( - "Cannot evaluate struct projection {expr} as a filter over {}", + NotImplemented: "Cannot evaluate struct projection {expr} as a filter over {}", self.name ) } diff --git a/vortex-layout/src/layouts/struct_/writer.rs b/vortex-layout/src/layouts/struct_/writer.rs index 0e9960a7c74..69f9792e826 100644 --- a/vortex-layout/src/layouts/struct_/writer.rs +++ b/vortex-layout/src/layouts/struct_/writer.rs @@ -114,14 +114,14 @@ impl LayoutStrategy for StructStrategy { let dtype = stream.dtype().clone(); let Some(struct_dtype) = dtype.as_struct_fields_opt() else { - vortex_bail!("StructStrategy can only write struct-typed streams, got {dtype}"); + vortex_bail!(MismatchedTypes: "StructStrategy can only write struct-typed streams, got {dtype}"); }; // Check for unique field names at write time. if HashSet::<_, DefaultHashBuilder>::from_iter(struct_dtype.names().iter()).len() != struct_dtype.names().len() { - vortex_bail!("StructLayout must have unique field names"); + vortex_bail!(InvalidArgument: "StructLayout must have unique field names"); } let is_nullable = dtype.is_nullable(); @@ -183,7 +183,7 @@ impl LayoutStrategy for StructStrategy { for (tx, column) in column_streams_tx.iter().zip_eq(columns) { if tx.send(Ok(column)).await.is_err() { vortex_bail!( - "struct column writer finished before all chunks were sent" + Io: "struct column writer finished before all chunks were sent" ); } } diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs index 3401e359103..3a5e6dfbddc 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs @@ -98,7 +98,9 @@ mod tests { .iter() .copied() .collect::>>() - .ok_or_else(|| vortex_err!("non-null test case contains a null"))?, + .ok_or_else( + || vortex_err!(AssertionFailed: "non-null test case contains a null"), + )?, ), Nullability::Nullable => BoolArray::from_iter(values.iter().copied()), }; diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs index cdc900bd339..2a703ac5b5b 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs @@ -43,7 +43,7 @@ pub(super) fn accumulate_canonical( | Canonical::Union(_) | Canonical::Map(_) => { vortex_bail!( - "Unsupported canonical type for bloom filter: {}", + InvalidArgument: "Unsupported canonical type for bloom filter: {}", canonical.dtype() ) } diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs index a13118c5729..8d994ef4f80 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs @@ -99,19 +99,20 @@ impl BloomOptions { vortex_ensure_eq!( bytes.len(), OPTIONS_BYTES_LEN, - "invalid bloom metadata length" + Serde: "invalid bloom metadata length" ); // Both options are u32 let (chunks, remainder) = bytes.as_chunks::<4>(); - vortex_ensure_eq!(remainder.len(), 0, "expected no trailing metadata bytes"); + vortex_ensure_eq!(remainder.len(), 0, Serde: "expected no trailing metadata bytes"); let blocks_count = u32::from_le_bytes(chunks[0]); let hash_fn = HashFn::try_from(u32::from_le_bytes(chunks[1]))?; Ok(Self { - blocks_count: NonZeroU32::new(blocks_count) - .ok_or_else(|| vortex_err!("bloom blocks length must be non-zero"))?, + blocks_count: NonZeroU32::new(blocks_count).ok_or_else( + || vortex_err!(InvalidArgument: "bloom blocks length must be non-zero"), + )?, hash_fn, }) } @@ -320,12 +321,16 @@ impl AggregateFnVTable for BloomFilter { let bytes = scalar .as_binary() .value() - .ok_or_else(|| vortex_err!("non-null bloom partial has no bytes"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "non-null bloom partial has no bytes"))?; let partial = BloomPartial::deserialize(bytes.clone())?; // `deserialize` validates the byte length, but it cannot know the options the filter was // built with, so compare the block count here. - vortex_ensure_eq!(partial.len(), args.options.blocks_count().get() as usize); + vortex_ensure_eq!( + partial.len(), + args.options.blocks_count().get() as usize, + InvalidArgument + ); Ok(partial) } @@ -449,7 +454,7 @@ pub(in crate::layouts::zoned::aggregates::bloom_filter) mod test_utils { let bytes = state .as_binary() .value() - .ok_or_else(|| vortex_err!("bloom state must be non-null"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "bloom state must be non-null"))?; let bloom_filter = BloomPartial::deserialize(bytes.clone())?; diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs index 61457a3a6d8..550712f9f07 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs @@ -37,7 +37,7 @@ impl BloomPartial { vortex_ensure_eq!( self.len(), other.len(), - "bloom partial block count mismatch" + InvalidArgument: "bloom partial block count mismatch" ); // One flat `u32` slice each: the compiler turns the flat OR into wide loads and stores, diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs index db7da6f700e..b4ea657d629 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs @@ -77,7 +77,7 @@ impl TryFrom for HashFn { fn try_from(value: u32) -> Result { match value { 0 => Ok(Self::XxHash3_64), - _ => Err(vortex_err!("unknown bloom hash function ID: {value}")), + _ => Err(vortex_err!(NotFound: "unknown bloom hash function ID: {value}")), } } } diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs index 509a735fc94..b9fe5343091 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs @@ -69,7 +69,7 @@ impl BloomPartial { } other => { return Err(vortex_err!( - "Unsupported scalar type for bloom filter: {other}" + InvalidArgument: "Unsupported scalar type for bloom filter: {other}" )); } }) diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs index 6d7400ccbc3..16fbee72242 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs @@ -30,12 +30,12 @@ impl BloomPartial { pub(in crate::layouts::zoned) fn deserialize(bytes: ByteBuffer) -> VortexResult { vortex_ensure!( !bytes.is_empty() && bytes.len().is_multiple_of(BLOCK_SIZE), - "invalid bloom filter byte length: {}", + Serde: "invalid bloom filter byte length: {}", bytes.len() ); vortex_ensure!( u32::try_from(bytes.len() / BLOCK_SIZE).is_ok(), - "bloom blocks length must be non-zero and lower than u32::MAX", + Serde: "bloom blocks length must be non-zero and lower than u32::MAX", ); let blocks = Buffer::::from_byte_buffer(bytes.aligned(Alignment::of::())); diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs index fc8f91627cb..552fe0ecfb7 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs @@ -88,12 +88,12 @@ impl ScalarFnVTable for BloomContains { fn return_dtype(&self, _options: &Self::Options, args: &[DType]) -> VortexResult { vortex_ensure!( matches!(args[0], DType::Binary(_)), - "bloom filter must be Binary" + MismatchedTypes: "bloom filter must be Binary" ); vortex_ensure!( is_bloom_valid_dtype(&args[1]), - "bloom filter needle value type is unsupported" + MismatchedTypes: "bloom filter needle value type is unsupported" ); Ok(DType::Bool(args[0].nullability() | args[1].nullability())) @@ -114,9 +114,9 @@ impl ScalarFnVTable for BloomContains { // For now, a bloom filter can execute only when the needle is a literal, // so anything other than a constant here is unexpected. let needle_array = args.get(1)?; - let needle = needle_array - .as_constant() - .ok_or_else(|| vortex_err!("bloom filter needle must be a constant"))?; + let needle = needle_array.as_constant().ok_or_else( + || vortex_err!(InvalidArgument: "bloom filter needle must be a constant"), + )?; // The bloom filter doesn't consider nulls as values // whose presence it should detect. During writes, the filter @@ -180,7 +180,8 @@ impl ScalarFnVTable for BloomContains { // Bloom filter length is never larger than a `u32`. This is intentional // and a property of the implementation. u32::try_from(partial.len()).vortex_expect("valid u32 size"), - options.blocks_count().get() + options.blocks_count().get(), + InvalidArgument ); partial.contains_scalar(&needle) }; @@ -360,9 +361,9 @@ mod tests { )?; let dtype = DType::Primitive(PType::I64, Nullability::NonNullable); - let proof = eq(root(dtype), lit(42i64)) - .falsify(&session)? - .ok_or_else(|| vortex_error::vortex_err!("equality should have a bloom falsifier"))?; + let proof = eq(root(dtype), lit(42i64)).falsify(&session)?.ok_or_else( + || vortex_error::vortex_err!(AssertionFailed: "equality should have a bloom falsifier"), + )?; let mut ctx = session.create_execution_ctx(); assert_arrays_eq!( @@ -398,7 +399,7 @@ mod tests { let dtype = DType::Primitive(PType::I64, Nullability::NonNullable); let proof = eq(root(dtype.clone()), lit(42i64)) .falsify(&session)? - .ok_or_else(|| vortex_error::vortex_err!("equality should have a bloom falsifier"))?; + .ok_or_else(|| vortex_error::vortex_err!(AssertionFailed: "equality should have a bloom falsifier"))?; let zone_map = ZoneMap::try_new( dtype, diff --git a/vortex-layout/src/layouts/zoned/builder.rs b/vortex-layout/src/layouts/zoned/builder.rs index 97290ad731d..e94e2107e6c 100644 --- a/vortex-layout/src/layouts/zoned/builder.rs +++ b/vortex-layout/src/layouts/zoned/builder.rs @@ -60,7 +60,7 @@ impl AggregateStatsAccumulator { vortex_ensure_eq!( partials.len(), self.builders.len(), - "aggregate partial count must match zone stats builder count" + AssertionFailed: "aggregate partial count must match zone stats builder count" ); for (builder, value) in self.builders.iter_mut().zip_eq(partials) { diff --git a/vortex-layout/src/layouts/zoned/mod.rs b/vortex-layout/src/layouts/zoned/mod.rs index ff6aaba350b..a8a0eed1653 100644 --- a/vortex-layout/src/layouts/zoned/mod.rs +++ b/vortex-layout/src/layouts/zoned/mod.rs @@ -107,7 +107,7 @@ impl VTable for Zoned { ) } ZoneMapSchema::LegacyStats(_) => { - vortex_panic!("Cannot serialize legacy stats schema as vortex.zoned") + vortex_panic!(NotImplemented: "Cannot serialize legacy stats schema as vortex.zoned") } }, } @@ -121,7 +121,7 @@ impl VTable for Zoned { vortex_ensure_eq!( args.children.nchildren(), 2, - "ZonedLayout expects exactly 2 children (data, zones)" + InvalidArgument: "ZonedLayout expects exactly 2 children (data, zones)" ); vortex_ensure_eq!(args.children.child_row_count(0), args.row_count); let Some(aggregate_fns) = @@ -149,7 +149,7 @@ impl VTable for Zoned { match idx { 0 => Ok(layout.dtype().clone()), 1 => Ok(layout.stats_table_dtype.clone()), - _ => vortex_bail!("Invalid child index: {idx}"), + _ => vortex_bail!(OutOfBounds: "Invalid child index: {idx}"), } } @@ -157,7 +157,7 @@ impl VTable for Zoned { match idx { 0 => LayoutChildType::Transparent("data".into()), 1 => LayoutChildType::Auxiliary("zones".into()), - _ => vortex_panic!("Invalid child index: {}", idx), + _ => vortex_panic!(OutOfBounds: "Invalid child index: {}", idx), } } @@ -196,7 +196,7 @@ impl VTable for LegacyStats { vortex_ensure_eq!( args.children.nchildren(), 2, - "LegacyStatsLayout expects exactly 2 children (data, zones)" + InvalidArgument: "LegacyStatsLayout expects exactly 2 children (data, zones)" ); let stats_table_dtype = match &metadata.zone_map_schema { ZoneMapSchema::LegacyStats(stats) => legacy_stats_table_dtype(args.dtype, stats), @@ -217,7 +217,7 @@ impl VTable for LegacyStats { match idx { 0 => Ok(layout.dtype().clone()), 1 => Ok(layout.stats_table_dtype.clone()), - _ => vortex_bail!("Invalid child index: {idx}"), + _ => vortex_bail!(OutOfBounds: "Invalid child index: {idx}"), } } @@ -225,7 +225,7 @@ impl VTable for LegacyStats { match idx { 0 => LayoutChildType::Transparent("data".into()), 1 => LayoutChildType::Auxiliary("zones".into()), - _ => vortex_panic!("Invalid child index: {idx}"), + _ => vortex_panic!(OutOfBounds: "Invalid child index: {idx}"), } } @@ -293,7 +293,7 @@ impl ZonedLayout { ) -> VortexResult { let expected_dtype = aggregate_stats_table_dtype(data.dtype(), &aggregate_fns); if zones.dtype() != &expected_dtype { - vortex_bail!("Invalid zone map layout: zones dtype does not match expected dtype"); + vortex_bail!(MismatchedTypes: "Invalid zone map layout: zones dtype does not match expected dtype"); } // Verify that every aggregate is serializable. @@ -437,15 +437,15 @@ impl DeserializeMetadata for ZonedMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { let Some((&version, proto_bytes)) = metadata.split_first() else { - vortex_bail!("Zoned metadata missing protobuf version"); + vortex_bail!(Serde: "Zoned metadata missing protobuf version"); }; vortex_ensure_eq!( version, ZONED_METADATA_PROTO_VERSION, - "Unsupported zoned metadata version" + Serde: "Unsupported zoned metadata version" ); - vortex_ensure!(!proto_bytes.is_empty(), "Zoned metadata missing protobuf"); + vortex_ensure!(!proto_bytes.is_empty(), Serde: "Zoned metadata missing protobuf"); let proto = ZonedMetadataProto::decode(proto_bytes)?; Ok(Self { @@ -473,7 +473,7 @@ impl DeserializeMetadata for LegacyStatsMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { vortex_ensure!( metadata.len() >= 4, - "Legacy zoned metadata must contain at least 4 bytes for zone length, got {}", + Serde: "Legacy zoned metadata must contain at least 4 bytes for zone length, got {}", metadata.len() ); @@ -499,7 +499,7 @@ impl SerializeMetadata for LegacyStatsMetadata { metadata } ZoneMapSchema::AggregateFns(_) => { - vortex_panic!("Cannot serialize aggregate specs as legacy stats metadata") + vortex_panic!(NotImplemented: "Cannot serialize aggregate specs as legacy stats metadata") } } } diff --git a/vortex-layout/src/layouts/zoned/reader.rs b/vortex-layout/src/layouts/zoned/reader.rs index 46f1d229c46..b91ef0d7527 100644 --- a/vortex-layout/src/layouts/zoned/reader.rs +++ b/vortex-layout/src/layouts/zoned/reader.rs @@ -71,13 +71,13 @@ impl ZonedReader { // A zone count that disagrees with `row_count` / `zone_len` would index past the mask. vortex_ensure!( zone_len > 0, - "zoned layout reader requires a non-zero zone length" + InvalidArgument: "zoned layout reader requires a non-zero zone length" ); let expected_zones = row_count.div_ceil(zone_len as u64); vortex_ensure_eq!( zone_count as u64, expected_zones, - "zoned layout zone count must cover {row_count} rows of {zone_len}-row zones" + Serde: "zoned layout zone count must cover {row_count} rows of {zone_len}-row zones" ); Ok(Self { diff --git a/vortex-layout/src/layouts/zoned/schema.rs b/vortex-layout/src/layouts/zoned/schema.rs index 0e4d9db318a..3b30ca6664c 100644 --- a/vortex-layout/src/layouts/zoned/schema.rs +++ b/vortex-layout/src/layouts/zoned/schema.rs @@ -37,7 +37,7 @@ impl AggregateSpecProto { pub(crate) fn try_from_aggregate_fn(aggregate_fn: &AggregateFnRef) -> VortexResult { let options = aggregate_fn.options().serialize()?.ok_or_else(|| { vortex_err!( - "Aggregate function '{}' is not serializable", + Serde: "Aggregate function '{}' is not serializable", aggregate_fn.id() ) })?; @@ -62,13 +62,13 @@ impl AggregateSpecProto { return Ok(None); } - vortex_bail!("unknown aggregate function id: {}", self.id); + vortex_bail!(NotFound: "unknown aggregate function id: {}", self.id); }; let aggregate_fn = plugin.deserialize(&self.options, session)?; if aggregate_fn.id() != aggregate_fn_id { vortex_bail!( - "Aggregate function ID mismatch: expected {}, got {}", + MismatchedTypes: "Aggregate function ID mismatch: expected {}, got {}", aggregate_fn_id, aggregate_fn.id() ); diff --git a/vortex-layout/src/layouts/zoned/writer.rs b/vortex-layout/src/layouts/zoned/writer.rs index 6326f1b05eb..2cb11860f46 100644 --- a/vortex-layout/src/layouts/zoned/writer.rs +++ b/vortex-layout/src/layouts/zoned/writer.rs @@ -137,7 +137,7 @@ impl LayoutStrategy for ZonedStrategy { let aggregate_fns = stats_accumulator.lock().aggregate_fns(); for aggregate_fn in aggregate_fns.iter() { if !ctx.allows_aggregate(&aggregate_fn.id()) { - vortex_bail!("Aggregate {} not permitted by ctx", aggregate_fn.id()); + vortex_bail!(InvalidArgument: "Aggregate {} not permitted by ctx", aggregate_fn.id()); } } diff --git a/vortex-layout/src/layouts/zoned/zone_map.rs b/vortex-layout/src/layouts/zoned/zone_map.rs index 2b9011e330c..8279e9ff4ca 100644 --- a/vortex-layout/src/layouts/zoned/zone_map.rs +++ b/vortex-layout/src/layouts/zoned/zone_map.rs @@ -80,7 +80,7 @@ impl ZoneMap { ) -> VortexResult { let expected_dtype = aggregate_stats_table_dtype(&column_dtype, &aggregate_fns); if &expected_dtype != array.dtype() { - vortex_bail!("Array dtype does not match expected zone map dtype: {expected_dtype}"); + vortex_bail!(MismatchedTypes: "Array dtype does not match expected zone map dtype: {expected_dtype}"); } // SAFETY: We checked that the array matches the expected stats-table schema. @@ -121,7 +121,7 @@ impl ZoneMap { ) -> VortexResult { let expected_dtype = legacy_stats_table_dtype(&column_dtype, &stats); if &expected_dtype != array.dtype() { - vortex_bail!("Array dtype does not match expected zone map dtype: {expected_dtype}"); + vortex_bail!(MismatchedTypes: "Array dtype does not match expected zone map dtype: {expected_dtype}"); } // SAFETY: We checked that the array matches the expected legacy stats-table schema. @@ -228,7 +228,7 @@ impl StatBinder for ZoneMapStatsBinder<'_> { vortex_ensure_eq!( input.dtype(), &self.zone_map.column_dtype, - "Stats predicate root dtype does not match zone-map column dtype" + MismatchedTypes: "Stats predicate root dtype does not match zone-map column dtype" ); if let Some(stat_expr) = self.zone_map.aggregate_field_expr(aggregate_fn) { @@ -364,7 +364,7 @@ fn row_count_array(zone_len: u64, row_count: u64, num_zones: usize) -> VortexRes let leading_rows = zone_len.saturating_mul((num_zones as u64) - 1); let Some(last_zone_len) = row_count.checked_sub(leading_rows) else { vortex_bail!( - "Zone map declares {num_zones} zones of {zone_len} rows, which is more than the \ + Serde: "Zone map declares {num_zones} zones of {zone_len} rows, which is more than the \ {row_count} rows of the layout" ); }; diff --git a/vortex-layout/src/plan/physical/children.rs b/vortex-layout/src/plan/physical/children.rs index bfa1541b87c..72b7fc93bcf 100644 --- a/vortex-layout/src/plan/physical/children.rs +++ b/vortex-layout/src/plan/physical/children.rs @@ -58,10 +58,9 @@ impl PlanChildren { return Ok(Some(child)); } - let initializer = self - .initializer - .as_ref() - .ok_or_else(|| vortex_err!("Plan child {index} was not initialized"))?; + let initializer = self.initializer.as_ref().ok_or_else( + || vortex_err!(AssertionFailed: "Plan child {index} was not initialized"), + )?; Ok(Some(cell.get_or_try_init(|| initializer(index))?)) } @@ -69,7 +68,7 @@ impl PlanChildren { pub fn iter(&self) -> impl ExactSizeIterator> + '_ { (0..self.len()).map(|index| { self.get(index)? - .ok_or_else(|| vortex_err!("Plan child {index} is absent")) + .ok_or_else(|| vortex_err!(AssertionFailed: "Plan child {index} is absent")) }) } @@ -77,7 +76,7 @@ impl PlanChildren { pub(crate) fn iter_refs(&self) -> impl ExactSizeIterator> + '_ { (0..self.len()).map(|index| { self.get_ref(index)? - .ok_or_else(|| vortex_err!("Plan child {index} is absent")) + .ok_or_else(|| vortex_err!(AssertionFailed: "Plan child {index} is absent")) }) } diff --git a/vortex-layout/src/plan/physical/lower.rs b/vortex-layout/src/plan/physical/lower.rs index 1ea284cc1ca..0340c3dc4dd 100644 --- a/vortex-layout/src/plan/physical/lower.rs +++ b/vortex-layout/src/plan/physical/lower.rs @@ -67,7 +67,7 @@ pub fn lower(layout: &LayoutRef) -> VortexResult { return lower_zoned(layout); } vortex_bail!( - "No physical plan implementation for layout '{}'", + NotImplemented: "No physical plan implementation for layout '{}'", layout.encoding_id() ) } @@ -89,7 +89,7 @@ fn lower_chunked(layout: &ChunkedLayout) -> VortexResult { row_offsets.push(row_count); row_count = row_count .checked_add(layout.child_row_count(index)) - .ok_or_else(|| vortex_err!("Chunked row count overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "Chunked row count overflow"))?; } // SAFETY: Chunked layout construction validates that every child has the parent dtype and // that their row counts sum to the parent; offsets were computed with checked addition above. @@ -158,10 +158,10 @@ fn lazy_children(layout: LayoutRef, slots: Vec) -> PlanChildren { let slot = slots .get(index) .copied() - .ok_or_else(|| vortex_err!("Missing plan child slot {index}"))?; + .ok_or_else(|| vortex_err!(NotFound: "Missing plan child slot {index}"))?; let child = layout .slot(slot)? - .ok_or_else(|| vortex_err!("Layout child slot {slot} is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Layout child slot {slot} is absent"))?; lower(&child) }) } @@ -173,7 +173,7 @@ fn lower_zoned(layout: &LayoutRef) -> VortexResult { } else if let Some(layout) = layout.as_opt::() { layout.data() } else { - vortex_bail!("Zoned plan requires a zoned layout") + vortex_bail!(AssertionFailed: "Zoned plan requires a zoned layout") }; // Without zones, or with a zone table holding no statistics, nothing can be pruned. let no_stats = metadata @@ -183,7 +183,7 @@ fn lower_zoned(layout: &LayoutRef) -> VortexResult { if metadata.zone_len() == 0 || no_stats { let data = layout .slot(0)? - .ok_or_else(|| vortex_err!("Zoned layout has no data child"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Zoned layout has no data child"))?; return lower(&data); } let children = lazy_children(Arc::clone(layout), vec![0, 1]); diff --git a/vortex-layout/src/plan/physical/mod.rs b/vortex-layout/src/plan/physical/mod.rs index bedd3a7cad8..051d8581598 100644 --- a/vortex-layout/src/plan/physical/mod.rs +++ b/vortex-layout/src/plan/physical/mod.rs @@ -83,7 +83,7 @@ pub(crate) fn check_child_count( ) -> VortexResult<()> { if children.len() != expected { vortex_bail!( - "{name} expects {expected} children but got {}", + InvalidArgument: "{name} expects {expected} children but got {}", children.len() ); } diff --git a/vortex-layout/src/plan/physical/operators/concat.rs b/vortex-layout/src/plan/physical/operators/concat.rs index 57110556280..54aa61e8e7a 100644 --- a/vortex-layout/src/plan/physical/operators/concat.rs +++ b/vortex-layout/src/plan/physical/operators/concat.rs @@ -48,11 +48,9 @@ impl Operator for ConcatSource { Ok(if self.current == self.inlets { Step::End } else { - Step::Final( - cx.inlet(self.current) - .take() - .ok_or_else(|| vortex_err!("Concat computed before its inlet was ready"))?, - ) + Step::Final(cx.inlet(self.current).take().ok_or_else( + || vortex_err!(AssertionFailed: "Concat computed before its inlet was ready"), + )?) }) } } diff --git a/vortex-layout/src/plan/physical/operators/filter.rs b/vortex-layout/src/plan/physical/operators/filter.rs index ecd0943f97c..4948f8dbf4c 100644 --- a/vortex-layout/src/plan/physical/operators/filter.rs +++ b/vortex-layout/src/plan/physical/operators/filter.rs @@ -46,7 +46,7 @@ impl Operator for MaskStage { let end = self.cursor + batch.len(); vortex_ensure!( end <= self.mask.len(), - "Filter input is longer than its mask" + AssertionFailed: "Filter input is longer than its mask" ); let mask = self.mask.slice(self.cursor..end); self.cursor = end; diff --git a/vortex-layout/src/plan/physical/operators/mod.rs b/vortex-layout/src/plan/physical/operators/mod.rs index b0f5937d71d..9488719d1b5 100644 --- a/vortex-layout/src/plan/physical/operators/mod.rs +++ b/vortex-layout/src/plan/physical/operators/mod.rs @@ -44,9 +44,9 @@ fn take_rows(inlet: &mut Inlet<'_>, len: usize) -> VortexResult { let mut pieces: SmallVec<[ArrayRef; 2]> = SmallVec::new(); let mut left = len; while left > 0 { - let front = inlet - .peek_mut() - .ok_or_else(|| vortex_err!("Taking {len} rows from an inlet holding fewer"))?; + let front = inlet.peek_mut().ok_or_else( + || vortex_err!(AssertionFailed: "Taking {len} rows from an inlet holding fewer"), + )?; if front.len() <= left { left -= front.len(); pieces.extend(inlet.take()); diff --git a/vortex-layout/src/plan/physical/operators/pack.rs b/vortex-layout/src/plan/physical/operators/pack.rs index 4fefa368f05..5a66330cce0 100644 --- a/vortex-layout/src/plan/physical/operators/pack.rs +++ b/vortex-layout/src/plan/physical/operators/pack.rs @@ -78,7 +78,7 @@ impl Source for PackSource { let available = self.states.len() - self.waiting.indices().len() - self.ended; vortex_ensure!( self.ended == 0 || available == 0, - "Pack fields ended at different rows" + AssertionFailed: "Pack fields ended at different rows" ); Ok(match self.waiting.indices().last() { Some(&index) => SourceReady::Blocked(SourceBlocked::Inlet(index)), @@ -97,9 +97,9 @@ impl Operator for PackSource { let mut len = usize::MAX; for index in 0..self.states.len() { let mut inlet = cx.inlet(index); - let front = inlet - .peek_mut() - .ok_or_else(|| vortex_err!("Pack computed before every inlet was ready"))?; + let front = inlet.peek_mut().ok_or_else( + || vortex_err!(AssertionFailed: "Pack computed before every inlet was ready"), + )?; len = len.min(front.len()); } let mut arrays = Vec::with_capacity(self.states.len()); @@ -109,11 +109,9 @@ impl Operator for PackSource { self.observe(index, &inlet); } let validity = if self.nullable { - Validity::Array( - arrays - .pop() - .ok_or_else(|| vortex_err!("Nullable Pack is missing its validity"))?, - ) + Validity::Array(arrays.pop().ok_or_else( + || vortex_err!(AssertionFailed: "Nullable Pack is missing its validity"), + )?) } else { Validity::NonNullable }; diff --git a/vortex-layout/src/plan/physical/operators/scan.rs b/vortex-layout/src/plan/physical/operators/scan.rs index 842bd33ee87..0a0f6e7effe 100644 --- a/vortex-layout/src/plan/physical/operators/scan.rs +++ b/vortex-layout/src/plan/physical/operators/scan.rs @@ -105,7 +105,7 @@ impl Operator for ScanSource { } let (_, bytes) = cx .take_segment() - .ok_or_else(|| vortex_err!("Segment scan ran without its bytes"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Segment scan ran without its bytes"))?; self.done = true; let array = decode(&self.plan, bytes, cx.session())?; Ok(Step::Final(select( diff --git a/vortex-layout/src/plan/physical/optimizer/rules.rs b/vortex-layout/src/plan/physical/optimizer/rules.rs index 1c32e9c6f60..f31f4503d8b 100644 --- a/vortex-layout/src/plan/physical/optimizer/rules.rs +++ b/vortex-layout/src/plan/physical/optimizer/rules.rs @@ -106,12 +106,12 @@ impl PlanRuleSet { vortex_ensure_eq!( reduced.row_count(), plan.row_count(), - "Plan rewrite from {rule:?} changed row count" + AssertionFailed: "Plan rewrite from {rule:?} changed row count" ); vortex_ensure_eq!( reduced.dtype(), plan.dtype(), - "Plan rewrite from {rule:?} changed dtype" + AssertionFailed: "Plan rewrite from {rule:?} changed dtype" ); } @@ -239,12 +239,12 @@ impl PlanParentRuleSet { vortex_ensure_eq!( reduced.row_count(), parent.row_count(), - "Plan rewrite from {rule:?} changed row count" + AssertionFailed: "Plan rewrite from {rule:?} changed row count" ); vortex_ensure_eq!( reduced.dtype(), parent.dtype(), - "Plan rewrite from {rule:?} changed dtype" + AssertionFailed: "Plan rewrite from {rule:?} changed dtype" ); } diff --git a/vortex-layout/src/plan/physical/pipeline/scan.rs b/vortex-layout/src/plan/physical/pipeline/scan.rs index 816c3566d7e..6f757e89c6f 100644 --- a/vortex-layout/src/plan/physical/pipeline/scan.rs +++ b/vortex-layout/src/plan/physical/pipeline/scan.rs @@ -191,7 +191,7 @@ fn drive( cx.changed.clear(); vortex_ensure!( cx.reads.is_empty() || ready == SourceReady::Blocked(SourceBlocked::Io), - "A source that queues reads must block on IO" + AssertionFailed: "A source that queues reads must block on IO" ); match ready { SourceReady::Ready => {} @@ -395,7 +395,7 @@ impl Core { fn run(&mut self, id: PipelineId) -> VortexResult<()> { let pipe = self.pipelines[id] .as_mut() - .ok_or_else(|| vortex_err!("Pipeline {id} is not live"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Pipeline {id} is not live"))?; pipe.queued = false; let mut reads = SmallVec::new(); let progress = drive( @@ -526,7 +526,7 @@ impl Core { let (owner, segment) = self .reads .remove(&read) - .ok_or_else(|| vortex_err!("Unknown read {read:?}"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Unknown read {read:?}"))?; if let Some(id) = owner { let pipe = self.pipeline_mut(id); pipe.pending -= 1; @@ -629,7 +629,7 @@ impl Scan { split.rows.start <= split.rows.end && split.rows.end <= plan.row_count() && split.mask.len() as u64 == split.rows.end - split.rows.start, - "Split {:?} with a mask of {} rows does not fit a plan of {} rows", + InvalidArgument: "Split {:?} with a mask of {} rows does not fit a plan of {} rows", split.rows, split.mask.len(), plan.row_count() @@ -716,7 +716,7 @@ impl Scan { return Ok(Turn::Waiting); } vortex_bail!( - "Scan is stuck with nothing runnable and no read in flight: {}", + AssertionFailed: "Scan is stuck with nothing runnable and no read in flight: {}", self.core.describe_blocked() ); } @@ -733,20 +733,19 @@ impl Scan { .active .iter() .position(Option::is_none) - .ok_or_else(|| vortex_err!("No free split slot"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "No free split slot"))?; let index = self.next; self.next += 1; let split = self.splits[index].clone(); - let output = match self - .root - .as_ref() - .ok_or_else(|| vortex_err!("Scan has no plan for its next split"))? - { - Root::Plan(plan) => { - self.core - .compile_stage(plan, split.rows.clone(), &split.mask, slot)? - } - }; + let output = + match self.root.as_ref().ok_or_else( + || vortex_err!(AssertionFailed: "Scan has no plan for its next split"), + )? { + Root::Plan(plan) => { + self.core + .compile_stage(plan, split.rows.clone(), &split.mask, slot)? + } + }; if self.next == self.splits.len() { // Compiled operators own what they need. The last split no longer needs the // lowering tree or the source layouts retained by its lazy children. diff --git a/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs b/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs index 19bcb5504db..1fa3daed93d 100644 --- a/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs +++ b/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs @@ -66,7 +66,7 @@ fn run( } Turn::Waiting => { if inflight.is_empty() { - return Err(vortex_err!("scan waits with no reads in flight")); + return Err(vortex_err!(AssertionFailed: "scan waits with no reads in flight")); } let read = inflight.remove(pick(&inflight)); events.push(Some(*read.segment_id)); @@ -275,7 +275,7 @@ fn a_source_has_several_reads_in_flight(#[values(1, 3)] deliveries: usize) -> Vo for _ in 0..deliveries { let read = inflight .pop() - .ok_or_else(|| vortex_err!("no read in flight"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "no read in flight"))?; scan.deliver(read.id, empty_segment())?; } } @@ -325,7 +325,7 @@ impl Operator for ReadAfterInlet { }; let (segment, _) = cx .take_segment() - .ok_or_else(|| vortex_err!("computed before the read arrived"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "computed before the read arrived"))?; assert_eq!(*segment, u32::try_from(batch.len())?); Ok(Step::Final(batch)) } @@ -341,7 +341,7 @@ fn readiness_can_take_an_inlet_and_request_a_read() -> VortexResult<()> { move |rows, mask, compiler| { let chain = compiler .compile(&child, rows, mask)? - .ok_or_else(|| vortex_err!("child has no rows"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "child has no rows"))?; Ok(Some(compiler.join_with( vec![chain], |_| 1, @@ -389,9 +389,9 @@ impl Operator for FirstOf { if self.done { return Ok(Step::End); } - let (segment, _) = cx - .take_segment() - .ok_or_else(|| vortex_err!("FirstOf computed before a read arrived"))?; + let (segment, _) = cx.take_segment().ok_or_else( + || vortex_err!(AssertionFailed: "FirstOf computed before a read arrived"), + )?; self.done = true; Ok(Step::Final(indices([u64::from(*segment)]))) } @@ -627,7 +627,7 @@ mod contract { impl Operator for WaitsWhenFull { fn compute(&mut self, _input: Input, _cx: &mut Cx<'_>) -> VortexResult { - Err(vortex_err!("a blocked source must not compute")) + Err(vortex_err!(AssertionFailed: "a blocked source must not compute")) } } diff --git a/vortex-layout/src/plan/physical/pipeline/synthetic.rs b/vortex-layout/src/plan/physical/pipeline/synthetic.rs index 82c4f5bc3f6..8cb21770bfd 100644 --- a/vortex-layout/src/plan/physical/pipeline/synthetic.rs +++ b/vortex-layout/src/plan/physical/pipeline/synthetic.rs @@ -194,7 +194,7 @@ impl Operator for RowSource { if self.waiting { self.waiting = false; cx.take_segment() - .ok_or_else(|| vortex_err!("RowSource ran without its bytes"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "RowSource ran without its bytes"))?; } if self.remaining.is_empty() { return Ok(Step::End); diff --git a/vortex-layout/src/plan/physical/pipeline/tests.rs b/vortex-layout/src/plan/physical/pipeline/tests.rs index da9af0ab96c..f844c56f86e 100644 --- a/vortex-layout/src/plan/physical/pipeline/tests.rs +++ b/vortex-layout/src/plan/physical/pipeline/tests.rs @@ -232,7 +232,7 @@ fn drive( events.push(Event::Io(std::mem::take(&mut batch))); } if inflight.is_empty() { - return Err(vortex_err!("scan waits with no reads in flight")); + return Err(vortex_err!(AssertionFailed: "scan waits with no reads in flight")); } let read = inflight.remove(pick(&inflight)); events.push(Event::Delivered(*read.segment_id)); @@ -447,7 +447,7 @@ fn every_read_is_issued_before_any_is_delivered() -> VortexResult<()> { delivery(Delivery::Fifo), )?; let Some(Event::Io(first)) = run.events.first() else { - return Err(vortex_err!("first event must be a read batch")); + return Err(vortex_err!(AssertionFailed: "first event must be a read batch")); }; assert_eq!(first.len(), store.segments.len()); assert_eq!(reads(&run.events), store.segments.len()); @@ -592,7 +592,7 @@ fn scan_keeps_the_selection_with_or_without_a_filter(#[case] sel: Sel) -> Vortex let filtered = lower(&store.flat(&values)?)?; let scan = filtered .as_opt::() - .ok_or_else(|| vortex_err!("A flat layout lowers to a filter"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "A flat layout lowers to a filter"))? .child_plan()?; assert!(scan.is::()); @@ -807,7 +807,7 @@ fn pack_readiness_tracks_changes_and_consumption( assert_eq!(cx.touched.indices(), &[1]); let Step::Final(array) = pack.compute(Input::None, &mut cx)? else { return Err(vortex_err!( - "expected Pack's last currently available batch" + AssertionFailed: "expected Pack's last currently available batch" )); }; let expected = StructArray::from_fields(&[ @@ -868,7 +868,7 @@ fn bound_selection_never_initializes_skipped_chunks() -> VortexResult<()> { let children = PlanChildren::lazy(4, move |index| match index { 0 => Ok(first.clone()), 3 => Ok(last.clone()), - _ => Err(vortex_err!("unselected chunk {index} was initialized")), + _ => Err(vortex_err!(AssertionFailed: "unselected chunk {index} was initialized")), }); // SAFETY: All four logical chunks have five rows of the same primitive dtype. The two // unselected initializers deliberately fail to detect discovery as well as compilation. diff --git a/vortex-layout/src/plan/physical/plans/concat.rs b/vortex-layout/src/plan/physical/plans/concat.rs index 0d74d705f4b..ec9811adaed 100644 --- a/vortex-layout/src/plan/physical/plans/concat.rs +++ b/vortex-layout/src/plan/physical/plans/concat.rs @@ -74,14 +74,14 @@ impl ConcatPlan { for child in &children { if child.dtype() != &dtype { vortex_bail!( - "Concat child dtype {} does not match {dtype}", + MismatchedTypes: "Concat child dtype {} does not match {dtype}", child.dtype() ); } row_offsets.push(row_count); row_count = row_count .checked_add(child.row_count()) - .ok_or_else(|| vortex_error::vortex_err!("Concat row count overflow"))?; + .ok_or_else(|| vortex_error::vortex_err!(Overflow: "Concat row count overflow"))?; } // SAFETY: Child dtypes and the checked cumulative row metadata were validated above. Ok(unsafe { @@ -111,7 +111,7 @@ impl ConcatPlan { children: PlanChildren::lazy(self.children().len(), move |index| { let child = children .get(index)? - .ok_or_else(|| vortex_err!("Missing chunk {index}"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Missing chunk {index}"))?; let rows = child.row_count(); let mapped = map(child)?; vortex_ensure_eq!(mapped.dtype(), &child_dtype); @@ -144,7 +144,7 @@ impl PlanVTable for Concat { ) -> VortexResult<()> { if children.len() != plan.children().len() { vortex_bail!( - "Concat expects {} children but got {}", + InvalidArgument: "Concat expects {} children but got {}", plan.children().len(), children.len() ); @@ -156,7 +156,7 @@ impl PlanVTable for Concat { let child = child?; if child.dtype() != plan.dtype() { vortex_bail!( - "Concat child dtype {} does not match {}", + MismatchedTypes: "Concat child dtype {} does not match {}", child.dtype(), plan.dtype() ); @@ -164,11 +164,11 @@ impl PlanVTable for Concat { row_offsets.push(row_count); row_count = row_count .checked_add(child.row_count()) - .ok_or_else(|| vortex_error::vortex_err!("Concat row count overflow"))?; + .ok_or_else(|| vortex_error::vortex_err!(Overflow: "Concat row count overflow"))?; } if row_count != plan.row_count() { vortex_bail!( - "Concat children have {row_count} rows but the plan has {}", + InvalidArgument: "Concat children have {row_count} rows but the plan has {}", plan.row_count() ); } diff --git a/vortex-layout/src/plan/physical/plans/eval.rs b/vortex-layout/src/plan/physical/plans/eval.rs index b6a2f1ff620..b897cf23d65 100644 --- a/vortex-layout/src/plan/physical/plans/eval.rs +++ b/vortex-layout/src/plan/physical/plans/eval.rs @@ -108,11 +108,11 @@ impl PlanVTable for Eval { check_child_count("Eval", children, 1)?; let child = children .get(0)? - .ok_or_else(|| vortex_error::vortex_err!("Eval child is absent"))?; + .ok_or_else(|| vortex_error::vortex_err!(AssertionFailed: "Eval child is absent"))?; validate_expression_child(plan.expression(), &child)?; if child.row_count() != plan.row_count() { vortex_error::vortex_bail!( - "Eval child has {} rows but the plan has {}", + InvalidArgument: "Eval child has {} rows but the plan has {}", child.row_count(), plan.row_count() ); @@ -142,7 +142,7 @@ impl PlanVTable for Eval { fn validate_expression_child(expression: &BoundExpression, child: &PlanRef) -> VortexResult<()> { if !expression.is_root_bound_to(child.dtype()) { vortex_bail!( - "Eval expression is not bound to child dtype {}", + MismatchedTypes: "Eval expression is not bound to child dtype {}", child.dtype() ); } diff --git a/vortex-layout/src/plan/physical/plans/filter.rs b/vortex-layout/src/plan/physical/plans/filter.rs index 857a69a376e..7417208c38c 100644 --- a/vortex-layout/src/plan/physical/plans/filter.rs +++ b/vortex-layout/src/plan/physical/plans/filter.rs @@ -78,9 +78,9 @@ impl PlanVTable for Filter { check_child_count("Filter", children, 1)?; let child = children .get(0)? - .ok_or_else(|| vortex_err!("Filter child is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Filter child is absent"))?; if child.dtype() != plan.dtype() || child.row_count() != plan.row_count() { - vortex_bail!("Filter child does not match the filter's dtype and row count"); + vortex_bail!(MismatchedTypes: "Filter child does not match the filter's dtype and row count"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/legacy_stats.rs b/vortex-layout/src/plan/physical/plans/legacy_stats.rs index 7eb6bec85ff..f8823e38545 100644 --- a/vortex-layout/src/plan/physical/plans/legacy_stats.rs +++ b/vortex-layout/src/plan/physical/plans/legacy_stats.rs @@ -121,9 +121,9 @@ impl PlanVTable for LegacyStats { check_child_count("LegacyStats", children, 2)?; let data = children .get(DATA)? - .ok_or_else(|| vortex_err!("LegacyStats data child is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "LegacyStats data child is absent"))?; if data.dtype() != plan.dtype() || data.row_count() != plan.row_count() { - vortex_bail!("LegacyStats data child shape does not match the plan output"); + vortex_bail!(MismatchedTypes: "LegacyStats data child shape does not match the plan output"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/list_pack.rs b/vortex-layout/src/plan/physical/plans/list_pack.rs index bb075c7f4e2..8a9ddf4d70c 100644 --- a/vortex-layout/src/plan/physical/plans/list_pack.rs +++ b/vortex-layout/src/plan/physical/plans/list_pack.rs @@ -127,23 +127,23 @@ impl PlanVTable for ListPack { } fn validate_children(dtype: &DType, row_count: u64, children: &PlanChildren) -> VortexResult<()> { - let elements_dtype = dtype - .as_list_element_opt() - .ok_or_else(|| vortex_err!("ListPack output dtype must be a list, got {dtype}"))?; + let elements_dtype = dtype.as_list_element_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "ListPack output dtype must be a list, got {dtype}"), + )?; let expected_children = 2 + usize::from(dtype.is_nullable()); if children.len() != expected_children { vortex_bail!( - "ListPack expects {expected_children} children but got {}", + InvalidArgument: "ListPack expects {expected_children} children but got {}", children.len() ); } let elements = children .get(ELEMENTS)? - .ok_or_else(|| vortex_err!("ListPack elements child is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "ListPack elements child is absent"))?; if elements.dtype() != elements_dtype.as_ref() { vortex_bail!( - "ListPack elements child has dtype {} but the list element dtype is {}", + MismatchedTypes: "ListPack elements child has dtype {} but the list element dtype is {}", elements.dtype(), elements_dtype ); @@ -151,19 +151,19 @@ fn validate_children(dtype: &DType, row_count: u64, children: &PlanChildren) -> let offsets = children .get(OFFSETS)? - .ok_or_else(|| vortex_err!("ListPack offsets child is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "ListPack offsets child is absent"))?; if !offsets.dtype().is_int() || offsets.dtype().is_nullable() { vortex_bail!( - "ListPack offsets child must have a non-nullable integer dtype, got {}", + MismatchedTypes: "ListPack offsets child must have a non-nullable integer dtype, got {}", offsets.dtype() ); } let offsets_row_count = row_count .checked_add(1) - .ok_or_else(|| vortex_err!("ListPack offsets row count overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "ListPack offsets row count overflow"))?; if offsets.row_count() != offsets_row_count { vortex_bail!( - "ListPack offsets child has {} rows but must have {offsets_row_count}", + InvalidArgument: "ListPack offsets child has {} rows but must have {offsets_row_count}", offsets.row_count() ); } @@ -171,17 +171,17 @@ fn validate_children(dtype: &DType, row_count: u64, children: &PlanChildren) -> if dtype.is_nullable() { let validity = children .get(VALIDITY)? - .ok_or_else(|| vortex_err!("ListPack validity child is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "ListPack validity child is absent"))?; let validity_dtype = DType::Bool(Nullability::NonNullable); if validity.dtype() != &validity_dtype { vortex_bail!( - "ListPack validity child has dtype {} but must have dtype {validity_dtype}", + MismatchedTypes: "ListPack validity child has dtype {} but must have dtype {validity_dtype}", validity.dtype() ); } if validity.row_count() != row_count { vortex_bail!( - "ListPack validity child has {} rows but the plan has {row_count}", + InvalidArgument: "ListPack validity child has {} rows but the plan has {row_count}", validity.row_count() ); } diff --git a/vortex-layout/src/plan/physical/plans/pack.rs b/vortex-layout/src/plan/physical/plans/pack.rs index b37f50934e8..01400b7568a 100644 --- a/vortex-layout/src/plan/physical/plans/pack.rs +++ b/vortex-layout/src/plan/physical/plans/pack.rs @@ -96,13 +96,13 @@ impl PackPlan { ) -> VortexResult { if field_plans.len() != fields.nfields() { vortex_bail!( - "Pack expects {} field children but got {}", + InvalidArgument: "Pack expects {} field children but got {}", fields.nfields(), field_plans.len() ); } if validity.is_some() != (nullability == Nullability::Nullable) { - vortex_bail!("Pack validity child must be present exactly when the struct is nullable"); + vortex_bail!(InvalidArgument: "Pack validity child must be present exactly when the struct is nullable"); } for (index, (field_dtype, field_plan)) in @@ -181,21 +181,21 @@ impl PlanVTable for Pack { let expected_children = plan.nfields() + usize::from(plan.dtype().is_nullable()); if children.len() != expected_children { vortex_bail!( - "Pack expects {expected_children} children but got {}", + InvalidArgument: "Pack expects {expected_children} children but got {}", children.len() ); } for (index, field_dtype) in plan.fields().fields().enumerate() { - let child = children - .get(index)? - .ok_or_else(|| vortex_err!("Pack field child {index} is absent"))?; + let child = children.get(index)?.ok_or_else( + || vortex_err!(AssertionFailed: "Pack field child {index} is absent"), + )?; validate_field_child(index, &field_dtype, plan.row_count(), &child)?; } if plan.dtype().is_nullable() { let validity = children .get(plan.nfields())? - .ok_or_else(|| vortex_err!("Pack validity child is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Pack validity child is absent"))?; validate_validity_child(plan.row_count(), &validity)?; } Ok(()) @@ -237,7 +237,7 @@ impl PlanVTable for Pack { chains.push( compiler .compile(child?, rows.clone(), mask)? - .ok_or_else(|| vortex_err!("A Pack field produced no rows"))?, + .ok_or_else(|| vortex_err!(AssertionFailed: "A Pack field produced no rows"))?, ); } let nullable = plan.dtype().is_nullable(); @@ -259,13 +259,13 @@ fn validate_field_child( ) -> VortexResult<()> { if child.dtype() != expected_dtype { vortex_bail!( - "Pack field child {index} has dtype {} but the field has dtype {expected_dtype}", + MismatchedTypes: "Pack field child {index} has dtype {} but the field has dtype {expected_dtype}", child.dtype() ); } if child.row_count() != expected_row_count { vortex_bail!( - "Pack field child {index} has {} rows but the plan has {expected_row_count}", + InvalidArgument: "Pack field child {index} has {} rows but the plan has {expected_row_count}", child.row_count() ); } @@ -276,13 +276,13 @@ fn validate_validity_child(expected_row_count: u64, child: &PlanRef) -> VortexRe let expected_dtype = DType::Bool(Nullability::NonNullable); if child.dtype() != &expected_dtype { vortex_bail!( - "Pack validity child has dtype {} but must have dtype {expected_dtype}", + MismatchedTypes: "Pack validity child has dtype {} but must have dtype {expected_dtype}", child.dtype() ); } if child.row_count() != expected_row_count { vortex_bail!( - "Pack validity child has {} rows but the plan has {expected_row_count}", + InvalidArgument: "Pack validity child has {} rows but the plan has {expected_row_count}", child.row_count() ); } @@ -300,7 +300,7 @@ impl PackPlan { ) -> VortexResult { vortex_ensure!( !self.dtype().is_nullable(), - "Cannot prune fields from a nullable Pack" + InvalidArgument: "Cannot prune fields from a nullable Pack" ); let struct_fields = StructFields::from_iter( fields @@ -377,10 +377,10 @@ impl PlanParentReduceRule for ExpressionPackRule { let name = partitioned .partition_names .get(0) - .ok_or_else(|| vortex_err!("Struct expression partition has no field"))?; - let index = fields.find(name).ok_or_else(|| { - vortex_err!("Struct expression references unknown field '{name}'") - })?; + .ok_or_else(|| vortex_err!(NotFound: "Struct expression partition has no field"))?; + let index = fields.find(name).ok_or_else( + || vortex_err!(NotFound: "Struct expression references unknown field '{name}'"), + )?; let field = field_plan(child, index)?; let lowered = step_into_struct_field(expanded, name, field.dtype().clone())?; return Ok(Some(EvalPlan::try_new(lowered, field)?.into_plan())); @@ -392,19 +392,18 @@ impl PlanParentReduceRule for ExpressionPackRule { for index in 0..partitioned.partitions.len() { let name = &partitioned.partition_names[index]; let partition = &partitioned.partitions[index]; - let field_index = fields.find(name).ok_or_else(|| { - vortex_err!("Struct expression references unknown field '{name}'") - })?; + let field_index = fields.find(name).ok_or_else( + || vortex_err!(NotFound: "Struct expression references unknown field '{name}'"), + )?; let field = field_plan(child, field_index)?; let lowered = if let Some(pack) = partition .as_scalar() .and_then(|scalar_fn| scalar_fn.as_opt::()) && partition.children().len() == 1 { - let value_name = pack - .names - .get(0) - .ok_or_else(|| vortex_err!("Struct expression partition pack is empty"))?; + let value_name = pack.names.get(0).ok_or_else( + || vortex_err!(AssertionFailed: "Struct expression partition pack is empty"), + )?; collapsed.push((name.clone(), value_name.clone())); partition.children()[0].clone() } else { @@ -494,13 +493,13 @@ pub(super) fn rewrite_partition_root( fn field_name(fields: &StructFields, index: usize) -> VortexResult { Ok(fields .field_name(index) - .ok_or_else(|| vortex_err!("Struct field {index} has no name"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "Struct field {index} has no name"))? .clone()) } fn field_plan(plan: &Plan, index: usize) -> VortexResult { plan.child(index)? - .ok_or_else(|| vortex_err!("Struct field {index} has no plan")) + .ok_or_else(|| vortex_err!(NotFound: "Struct field {index} has no plan")) } fn expanded_struct_root( @@ -557,7 +556,7 @@ fn expand_struct_root( if let Some(field_name) = scalar_fn.as_opt::() { let index = fields.find(field_name).ok_or_else(|| { - vortex_err!("Field {field_name} not found while expanding struct root") + vortex_err!(NotFound: "Field {field_name} not found while expanding struct root") })?; return Ok(Transformed { value: expanded_root.children()[index].clone(), diff --git a/vortex-layout/src/plan/physical/plans/row_idx.rs b/vortex-layout/src/plan/physical/plans/row_idx.rs index 5c45d2cae4f..2c82ee57bdb 100644 --- a/vortex-layout/src/plan/physical/plans/row_idx.rs +++ b/vortex-layout/src/plan/physical/plans/row_idx.rs @@ -165,18 +165,22 @@ pub fn plan_row_idx_expression( vortex_ensure_eq!( partitioned.partition_annotations.len(), 2, - "Row-index expression produced more than two partitions" + AssertionFailed: "Row-index expression produced more than two partitions" ); let row_idx_index = partitioned .partition_annotations .iter() .position(|partition| *partition == RowIdxExpressionPartition::RowIdx) - .ok_or_else(|| vortex_err!("Row-index expression has no row-index partition"))?; + .ok_or_else( + || vortex_err!(AssertionFailed: "Row-index expression has no row-index partition"), + )?; let child_index = partitioned .partition_annotations .iter() .position(|partition| *partition == RowIdxExpressionPartition::Child) - .ok_or_else(|| vortex_err!("Row-index expression has no data partition"))?; + .ok_or_else( + || vortex_err!(AssertionFailed: "Row-index expression has no data partition"), + )?; let row_idx_partition = &partitioned.partitions[row_idx_index]; let child_partition = &partitioned.partitions[child_index]; @@ -189,7 +193,7 @@ pub fn plan_row_idx_expression( .and_then(|scalar_fn| scalar_fn.as_opt::()), ) else { return Err(vortex_err!( - "Row-index expression partitions must be struct packs" + MismatchedTypes: "Row-index expression partitions must be struct packs" )); }; let row_idx_partition_name = partitioned.partition_names[row_idx_index].clone(); @@ -198,7 +202,7 @@ pub fn plan_row_idx_expression( let row_idx_expression = if row_idx_partition.children().len() == 1 { let Some(value_name) = row_idx_pack.names.get(0) else { - return Err(vortex_err!("Row-index expression partition is empty")); + return Err(vortex_err!(AssertionFailed: "Row-index expression partition is empty")); }; collapsed.push((row_idx_partition_name, value_name.clone())); row_idx_partition.children()[0].clone() @@ -207,7 +211,7 @@ pub fn plan_row_idx_expression( }; let child_expression = if child_partition.children().len() == 1 { let Some(value_name) = child_pack.names.get(0) else { - return Err(vortex_err!("Data expression partition is empty")); + return Err(vortex_err!(AssertionFailed: "Data expression partition is empty")); }; collapsed.push((child_partition_name, value_name.clone())); child_partition.children()[0].clone() diff --git a/vortex-layout/src/plan/physical/plans/share.rs b/vortex-layout/src/plan/physical/plans/share.rs index 96166e7c81f..4e2697dde06 100644 --- a/vortex-layout/src/plan/physical/plans/share.rs +++ b/vortex-layout/src/plan/physical/plans/share.rs @@ -84,9 +84,9 @@ impl PlanVTable for Share { check_child_count("Share", children, 1)?; let child = children .get(0)? - .ok_or_else(|| vortex_err!("Share child is absent"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Share child is absent"))?; if child.dtype() != plan.dtype() || child.row_count() != plan.row_count() { - vortex_bail!("Share child does not match the share's dtype and row count"); + vortex_bail!(MismatchedTypes: "Share child does not match the share's dtype and row count"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/take.rs b/vortex-layout/src/plan/physical/plans/take.rs index b2a1703ff8a..8e354a923f3 100644 --- a/vortex-layout/src/plan/physical/plans/take.rs +++ b/vortex-layout/src/plan/physical/plans/take.rs @@ -114,17 +114,17 @@ impl PlanVTable for Take { _data: &mut Self::PlanData, ) -> VortexResult<()> { check_child_count("Take", children, 2)?; - let codes = children - .get(CODES)? - .ok_or_else(|| vortex_error::vortex_err!("Take codes child is absent"))?; - let values = children - .get(VALUES)? - .ok_or_else(|| vortex_error::vortex_err!("Take values child is absent"))?; + let codes = children.get(CODES)?.ok_or_else( + || vortex_error::vortex_err!(AssertionFailed: "Take codes child is absent"), + )?; + let values = children.get(VALUES)?.ok_or_else( + || vortex_error::vortex_err!(AssertionFailed: "Take values child is absent"), + )?; let dtype = values .dtype() .union_nullability(codes.dtype().nullability()); if codes.row_count() != plan.row_count() || &dtype != plan.dtype() { - vortex_error::vortex_bail!("Take child shape does not match the plan output"); + vortex_error::vortex_bail!(MismatchedTypes: "Take child shape does not match the plan output"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/zoned.rs b/vortex-layout/src/plan/physical/plans/zoned.rs index d1a17702ebf..574b1534c5f 100644 --- a/vortex-layout/src/plan/physical/plans/zoned.rs +++ b/vortex-layout/src/plan/physical/plans/zoned.rs @@ -307,11 +307,11 @@ impl PlanVTable for Zoned { } check_child_count("Zoned", children, 2)?; - let data = children - .get(DATA)? - .ok_or_else(|| vortex_error::vortex_err!("Zoned data child is absent"))?; + let data = children.get(DATA)?.ok_or_else( + || vortex_error::vortex_err!(AssertionFailed: "Zoned data child is absent"), + )?; if data.dtype() != plan.dtype() || data.row_count() != plan.row_count() { - vortex_error::vortex_bail!("Zoned data child shape does not match the plan output"); + vortex_error::vortex_bail!(MismatchedTypes: "Zoned data child shape does not match the plan output"); } Ok(()) } @@ -342,7 +342,7 @@ impl PlanVTable for Zoned { ) -> VortexResult> { if !plan.is_pruning() { let Some(data) = plan.data_plan()? else { - vortex_bail!("Zoned plan has no data child"); + vortex_bail!(AssertionFailed: "Zoned plan has no data child"); }; return compiler.compile(&data, rows, mask); } @@ -351,7 +351,7 @@ impl PlanVTable for Zoned { } let expression = plan .pruning_expression() - .ok_or_else(|| vortex_err!("Zoned pruning plan has no expression"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "Zoned pruning plan has no expression"))?; if let Some(pruned) = pruned_zones(plan)?.get(expression, compiler.session())? { return Ok(Some(Chain::new(OnceSource::new(expand_zones( plan, &rows, mask, &pruned, @@ -361,7 +361,7 @@ impl PlanVTable for Zoned { let count = usize::try_from(zones.row_count())?; let Some(chain) = compiler.compile(&zones, 0..zones.row_count(), &Mask::new_true(count))? else { - vortex_bail!("Zoned pruning plan has an empty zone table"); + vortex_bail!(AssertionFailed: "Zoned pruning plan has an empty zone table"); }; let zoned = plan.clone(); let mask = mask.clone(); @@ -376,7 +376,7 @@ impl PlanVTable for Zoned { /// The per-zone results kept on a pruning `plan`. fn pruned_zones(plan: &ZonedPlan) -> VortexResult<&Arc> { plan.pruned_zones() - .ok_or_else(|| vortex_err!("Zone pruning needs a pruning plan")) + .ok_or_else(|| vortex_err!(AssertionFailed: "Zone pruning needs a pruning plan")) } /// Builds the zone map from the zone table and proves the expression over it, one value per @@ -386,7 +386,7 @@ fn prune_zones(plan: &ZonedPlan, session: &VortexSession, table: ArrayRef) -> Vo let (Some(expression), Some(column_dtype)) = (plan.pruning_expression(), plan.pruning_column_dtype()) else { - vortex_bail!("Zone pruning needs a pruning plan"); + vortex_bail!(AssertionFailed: "Zone pruning needs a pruning plan"); }; let zone_map = ZoneMap::try_new( column_dtype.clone(), diff --git a/vortex-layout/src/plan/physical/selection.rs b/vortex-layout/src/plan/physical/selection.rs index 1087ad61538..d4e7d3daa41 100644 --- a/vortex-layout/src/plan/physical/selection.rs +++ b/vortex-layout/src/plan/physical/selection.rs @@ -77,7 +77,7 @@ impl SelectedData { fn mask(&self, rows: &Range) -> VortexResult { vortex_ensure!( rows.start >= self.rows.start && rows.end <= self.rows.end, - "Selected plan requested outside its bound row range" + OutOfBounds: "Selected plan requested outside its bound row range" ); Ok(self.mask.slice( usize::try_from(rows.start - self.rows.start)? diff --git a/vortex-layout/src/plan/physical/tests.rs b/vortex-layout/src/plan/physical/tests.rs index 47bad2dd94f..61ebbf72f26 100644 --- a/vortex-layout/src/plan/physical/tests.rs +++ b/vortex-layout/src/plan/physical/tests.rs @@ -98,7 +98,7 @@ fn make_row_idx_plan(expression: Expression, child: PlanRef) -> VortexResult VortexResult { plan.child(index)? - .ok_or_else(|| vortex_err!("missing child {index}")) + .ok_or_else(|| vortex_err!(NotFound: "missing child {index}")) } fn assert_unsupported(error: vortex_error::VortexError) { @@ -114,11 +114,9 @@ fn assert_unsupported(error: vortex_error::VortexError) { fn unsupported_layout_has_no_plan() -> VortexResult<()> { let layout = unsupported(3, DType::Null); - assert_unsupported( - lower(&layout) - .err() - .ok_or_else(|| vortex_err!("unsupported layout unexpectedly produced a plan"))?, - ); + assert_unsupported(lower(&layout).err().ok_or_else( + || vortex_err!(InvalidArgument: "unsupported layout unexpectedly produced a plan"), + )?); Ok(()) } @@ -167,9 +165,9 @@ fn optimize_preserves_unvisited_concat_children() -> VortexResult<()> { let plan = optimize(make_plan(layout)?)?; assert_eq!(child_of(&plan, 0)?.row_count(), 2); assert_unsupported( - child_of(&plan, 1) - .err() - .ok_or_else(|| vortex_err!("unsupported child unexpectedly lowered"))?, + child_of(&plan, 1).err().ok_or_else( + || vortex_err!(AssertionFailed: "unsupported child unexpectedly lowered"), + )?, ); Ok(()) } @@ -189,11 +187,9 @@ fn chunked_plan_lowers_each_chunk_on_access() -> VortexResult<()> { let plan = make_plan(layout)?; assert_eq!(child_of(&plan, 0)?.row_count(), 1); - assert_unsupported( - child_of(&plan, 1) - .err() - .ok_or_else(|| vortex_err!("unsupported chunk unexpectedly produced a plan"))?, - ); + assert_unsupported(child_of(&plan, 1).err().ok_or_else( + || vortex_err!(InvalidArgument: "unsupported chunk unexpectedly produced a plan"), + )?); Ok(()) } @@ -212,11 +208,9 @@ fn struct_plan_lowers_each_field_on_access() -> VortexResult<()> { let plan = make_plan(layout)?; assert_eq!(child_of(&plan, 0)?.row_count(), 1); - assert_unsupported( - child_of(&plan, 1) - .err() - .ok_or_else(|| vortex_err!("unsupported field unexpectedly produced a plan"))?, - ); + assert_unsupported(child_of(&plan, 1).err().ok_or_else( + || vortex_err!(InvalidArgument: "unsupported field unexpectedly produced a plan"), + )?); Ok(()) } @@ -325,7 +319,7 @@ fn with_children_rejects_mismatched_arity() -> VortexResult<()> { let error = plan .with_children(vec![child_of(&plan, 0)?]) .err() - .ok_or_else(|| vortex_err!("mismatched arity unexpectedly succeeded"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "mismatched arity unexpectedly succeeded"))?; assert!( error .to_string() @@ -358,9 +352,9 @@ fn eval_try_new_validates_expression_root_dtype() -> VortexResult<()> { let expression = root().bind(&primitive(PType::I32, Nullability::NonNullable))?; let child = make_plan(flat(3, primitive(PType::I64, Nullability::NonNullable), 0))?; - let error = EvalPlan::try_new(expression, child) - .err() - .ok_or_else(|| vortex_err!("mismatched Eval root dtype unexpectedly succeeded"))?; + let error = EvalPlan::try_new(expression, child).err().ok_or_else( + || vortex_err!(MismatchedTypes: "mismatched Eval root dtype unexpectedly succeeded"), + )?; assert!( error .to_string() @@ -646,13 +640,13 @@ fn empty_projection_prunes_row_idx_child_fields() -> VortexResult<()> { let plan = make_row_idx_plan(projection, make_plan(layout)?)?; let optimized = optimize(plan)?; - let projection = optimized - .as_opt::() - .ok_or_else(|| vortex_err!("optimized plan has no projection expression"))?; + let projection = optimized.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "optimized plan has no projection expression"), + )?; let child = projection.child_plan()?; - let empty_struct = child - .as_opt::() - .ok_or_else(|| vortex_err!("empty projection did not prune the RowIdx child"))?; + let empty_struct = child.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "empty projection did not prune the RowIdx child"), + )?; assert_eq!(empty_struct.nfields(), 0); assert_eq!(empty_struct.children().len(), 0); @@ -1180,7 +1174,7 @@ fn dictionary_pushdown_rejects_unsafe_expressions() -> VortexResult<()> { let plan = make_eval(expression.clone(), make_plan(Arc::clone(&dictionary))?)?.into_plan(); let optimized = optimize(plan)?; let eval = optimized.as_opt::().ok_or_else(|| { - vortex_err!("Expression unexpectedly pushed into dictionary: {expression}") + vortex_err!(AssertionFailed: "Expression unexpectedly pushed into dictionary: {expression}") })?; assert!(eval.child_plan()?.is::()); } @@ -1195,9 +1189,9 @@ fn non_strict_expression_pushes_into_dictionary_without_null_codes() -> VortexRe ) .into_layout(); let optimized = optimize(make_eval(is_null(root()), make_plan(dictionary)?)?.into_plan())?; - let take = optimized - .as_opt::() - .ok_or_else(|| vortex_err!("is_null was not pushed into the dictionary: {optimized}"))?; + let take = optimized.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "is_null was not pushed into the dictionary: {optimized}"), + )?; assert!(take.values()?.is::()); Ok(()) } @@ -1220,9 +1214,9 @@ fn nullable_struct_keeps_expression_above_parent_validity() -> VortexResult<()> let plan = make_eval(gt(get_item("a", root()), lit(5_i32)), make_plan(layout)?)?.into_plan(); let optimized = optimize(plan)?; - let eval = optimized - .as_opt::() - .ok_or_else(|| vortex_err!("Nullable struct expression unexpectedly pushed down"))?; + let eval = optimized.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "Nullable struct expression unexpectedly pushed down"), + )?; assert!(eval.child_plan()?.is::()); Ok(()) } @@ -1231,7 +1225,8 @@ fn nullable_struct_keeps_expression_above_parent_validity() -> VortexResult<()> fn zoned_plan_exposes_data_and_zones() -> VortexResult<()> { let dtype = primitive(PType::I32, Nullability::NonNullable); let (max, zones_dtype) = max_zones_dtype(&dtype)?; - let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; + let zone_len = + NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; let layout = ZonedLayout::try_new( flat(5, dtype, 0), flat(2, zones_dtype, 1), @@ -1258,12 +1253,13 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { let max = Max.bind(NumericalAggregateOpts::skip_nans()); let max_dtype = max .state_dtype(&dtype) - .ok_or_else(|| vortex_err!("max does not support {dtype}"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "max does not support {dtype}"))?; let zones_dtype = DType::Struct( StructFields::from_iter([(max.to_string(), max_dtype.as_nullable())]), Nullability::NonNullable, ); - let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; + let zone_len = + NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; let layout = ZonedLayout::try_new( flat(5, dtype.clone(), 0), flat(2, zones_dtype, 1), @@ -1276,7 +1272,7 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { let falsifier = filter .bind(&dtype)? .falsify(&session)? - .ok_or_else(|| vortex_err!("filter has no falsifier"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; let source = make_plan(layout)?; let plan = EvalPlan::try_new(falsifier.clone(), source.clone())?.into_plan(); @@ -1297,7 +1293,7 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { "); let zoned = optimized .as_opt::() - .ok_or_else(|| vortex_err!("optimized pruning plan is not zoned"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "optimized pruning plan is not zoned"))?; assert!(zoned.is_pruning()); assert_eq!(zoned.pruning_expression(), Some(&falsifier)); assert!(zoned.data_plan()?.is_none()); @@ -1305,15 +1301,15 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { let mixed_expression = bound_and(falsifier, gt(root(), lit(0_i32)).bind(&dtype)?); let mixed = optimize(EvalPlan::try_new(mixed_expression, source)?.into_plan())?; - let mixed = mixed - .as_opt::() - .ok_or_else(|| vortex_err!("expression with a data reference was pushed into zones"))?; + let mixed = mixed.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "expression with a data reference was pushed into zones"), + )?; let mixed_child = mixed.child_plan()?; assert!(mixed_child.is::()); assert!( !mixed_child .as_opt::() - .ok_or_else(|| vortex_err!("mixed expression child is not zoned"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "mixed expression child is not zoned"))? .is_pruning() ); Ok(()) @@ -1325,12 +1321,13 @@ fn pruning_expression_partitions_across_row_idx_and_zoned_struct_field() -> Vort let max = Max.bind(NumericalAggregateOpts::skip_nans()); let max_dtype = max .state_dtype(&value_dtype) - .ok_or_else(|| vortex_err!("max does not support {value_dtype}"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "max does not support {value_dtype}"))?; let zones_dtype = DType::Struct( StructFields::from_iter([(max.to_string(), max_dtype.as_nullable())]), Nullability::NonNullable, ); - let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; + let zone_len = + NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; let zoned = ZonedLayout::try_new( flat(5, value_dtype.clone(), 0), flat(2, zones_dtype, 1), @@ -1357,7 +1354,7 @@ fn pruning_expression_partitions_across_row_idx_and_zoned_struct_field() -> Vort let falsifier = filter .bind(&struct_dtype)? .falsify(&session)? - .ok_or_else(|| vortex_err!("filter has no falsifier"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; let optimized = optimize(plan_row_idx_expression(falsifier, source)?)?; insta::assert_snapshot!(optimized.display_tree(), @r" @@ -1425,7 +1422,8 @@ fn legacy_stats_layout_lowers_to_legacy_stats_plan() -> VortexResult<()> { fn zoned_layouts_without_statistics_lower_to_their_data() -> VortexResult<()> { let dtype = primitive(PType::I32, Nullability::NonNullable); let empty = DType::Struct(StructFields::empty(), Nullability::NonNullable); - let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; + let zone_len = + NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; let layouts = [ legacy_layout(&dtype, 0, &[Stat::Max], legacy_max_zones_dtype(&dtype))?, legacy_layout(&dtype, 3, &[], empty.clone())?, @@ -1471,7 +1469,7 @@ fn max_zones_dtype(dtype: &DType) -> VortexResult<(AggregateFnRef, DType)> { let max = Max.bind(NumericalAggregateOpts::skip_nans()); let max_dtype = max .state_dtype(dtype) - .ok_or_else(|| vortex_err!("max does not support {dtype}"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "max does not support {dtype}"))?; let zones_dtype = DType::Struct( StructFields::from_iter([(max.to_string(), max_dtype.as_nullable())]), Nullability::NonNullable, @@ -1488,7 +1486,7 @@ fn legacy_stats_rewrite_to_zoned_over_converted_zones() -> VortexResult<()> { let optimized = optimize(legacy.clone())?; let zoned = optimized .as_opt::() - .ok_or_else(|| vortex_err!("legacy stats did not become zoned"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "legacy stats did not become zoned"))?; assert!(!zoned.is_pruning()); assert_eq!(zoned.zone_len(), 3); assert_eq!( @@ -1506,11 +1504,11 @@ fn legacy_stats_rewrite_to_zoned_over_converted_zones() -> VortexResult<()> { let falsifier = gt(root(), lit(5_i32)) .bind(&dtype)? .falsify(&SESSION)? - .ok_or_else(|| vortex_err!("filter has no falsifier"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; let pruning = optimize(EvalPlan::try_new(falsifier, legacy)?.into_plan())?; - let pruning = pruning - .as_opt::() - .ok_or_else(|| vortex_err!("legacy stats predicate did not become a pruning plan"))?; + let pruning = pruning.as_opt::().ok_or_else( + || vortex_err!(AssertionFailed: "legacy stats predicate did not become a pruning plan"), + )?; assert!(pruning.is_pruning()); assert!(pruning.zones_plan()?.is::()); Ok(()) @@ -1542,7 +1540,7 @@ fn converted_legacy_zones_prune() -> VortexResult<()> { let falsifier = gt(root(), lit(5_i32)) .bind(&dtype)? .falsify(&SESSION)? - .ok_or_else(|| vortex_err!("filter has no falsifier"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; // Only the first zone's max proves no row exceeds 5. assert_eq!( zone_map.prune(&falsifier, &SESSION)?, @@ -1562,7 +1560,7 @@ fn legacy_stats_under_zoned_are_dropped() -> VortexResult<()> { let optimized = optimize(plan)?; let zoned = optimized .as_opt::() - .ok_or_else(|| vortex_err!("zoned plan was rewritten away"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "zoned plan was rewritten away"))?; assert!(zoned.data_plan()?.is_some_and(|data| data.is::())); assert!(PlanRef::ptr_eq(&zoned.zones_plan()?, &zones)); Ok(()) @@ -1630,11 +1628,11 @@ fn dynamic_predicates_stay_above_dictionary_values() -> VortexResult<()> { optimize(make_eval(predicate, make_plan(Arc::clone(&layout))?)?.into_plan())?; let eval = optimized .as_opt::() - .ok_or_else(|| vortex_err!("dynamic predicate was pushed down"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "dynamic predicate was pushed down"))?; let take = eval .child_plan()? .as_opt::() - .ok_or_else(|| vortex_err!("dynamic predicate is not over the take"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "dynamic predicate is not over the take"))? .clone(); assert!(!take.values()?.is::(), "{}", optimized.display_tree()); } @@ -1661,11 +1659,11 @@ fn expression_pushes_onto_values_less_nullable_than_the_take() -> VortexResult<( assert_eq!(optimized.dtype(), &dtype); let take = optimized .as_opt::() - .ok_or_else(|| vortex_err!("predicate was not pushed onto the values"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "predicate was not pushed onto the values"))?; let values = take.values()?; let eval = values .as_opt::() - .ok_or_else(|| vortex_err!("values are not evaluated"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "values are not evaluated"))?; assert!(eval.expression().is_root_bound_to(&values_dtype)); Ok(()) } @@ -1686,14 +1684,14 @@ fn zoned_pruning_plan_with_new_zones_proves_them_again() -> VortexResult<()> { let falsifier = gt(root(), lit(5_i32)) .bind(&dtype)? .falsify(&SESSION)? - .ok_or_else(|| vortex_err!("filter has no falsifier"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; let pruning = optimize(EvalPlan::try_new(falsifier.clone(), source)?.into_plan())?; let pruning = pruning .as_opt::() - .ok_or_else(|| vortex_err!("predicate did not become a pruning plan"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "predicate did not become a pruning plan"))?; let proof = pruning .pruned_zones() - .ok_or_else(|| vortex_err!("pruning plan has no proof"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "pruning plan has no proof"))?; let zone_map = |bounds: [i32; 2]| { let table = StructArray::from_fields(&[( @@ -1713,7 +1711,7 @@ fn zoned_pruning_plan_with_new_zones_proves_them_again() -> VortexResult<()> { let rebuilt_proof = rebuilt .as_opt::() .and_then(|zoned| zoned.pruned_zones()) - .ok_or_else(|| vortex_err!("rebuilt plan has no proof"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "rebuilt plan has no proof"))?; assert!(rebuilt_proof.get(&falsifier, &SESSION)?.is_none()); let updated = Mask::from_iter([false, true]); assert_eq!( diff --git a/vortex-layout/src/plan/physical/typed.rs b/vortex-layout/src/plan/physical/typed.rs index c783dc8137b..2b7618092a3 100644 --- a/vortex-layout/src/plan/physical/typed.rs +++ b/vortex-layout/src/plan/physical/typed.rs @@ -94,7 +94,7 @@ impl PlanRef { /// Returns the child at `index`, or an error when the index is out of bounds. pub fn child_required(&self, index: usize) -> VortexResult { self.child(index)? - .ok_or_else(|| vortex_err!("Missing plan child {index}")) + .ok_or_else(|| vortex_err!(NotFound: "Missing plan child {index}")) } /// Rebuilds this plan with `children` stored outside its erased operator data. @@ -143,12 +143,12 @@ impl PlanRef { ) -> VortexResult> { vortex_ensure!( rows.start <= rows.end && rows.end <= self.row_count(), - "Compile rows {rows:?} exceed plan row count {}", + OutOfBounds: "Compile rows {rows:?} exceed plan row count {}", self.row_count() ); vortex_ensure!( mask.len() as u64 == rows.end - rows.start, - "Compile mask length {} does not match rows {rows:?}", + InvalidArgument: "Compile mask length {} does not match rows {rows:?}", mask.len() ); self.dyn_plan().dyn_compile(self, rows, mask, compiler) diff --git a/vortex-layout/src/plan/physical/vtable.rs b/vortex-layout/src/plan/physical/vtable.rs index 75f3e4139c8..ac76b88c22f 100644 --- a/vortex-layout/src/plan/physical/vtable.rs +++ b/vortex-layout/src/plan/physical/vtable.rs @@ -88,6 +88,6 @@ pub trait PlanVTable: 'static + Clone + Sized + Send + Sync + Debug { compiler: &mut Compiler<'_>, ) -> VortexResult> { let _ = (rows, mask, compiler); - vortex_bail!("Plan {} has no pipeline implementation", plan.vtable().id()) + vortex_bail!(NotImplemented: "Plan {} has no pipeline implementation", plan.vtable().id()) } } diff --git a/vortex-layout/src/reader.rs b/vortex-layout/src/reader.rs index 91dda0e23c5..dad6c5920d0 100644 --- a/vortex-layout/src/reader.rs +++ b/vortex-layout/src/reader.rs @@ -41,7 +41,7 @@ impl SplitRange { /// Constructs a split range, returning an error if the local row range is invalid. pub fn try_new(row_offset: u64, row_range: Range) -> VortexResult { if row_range.start > row_range.end { - vortex_bail!("Invalid split range {:?}", row_range); + vortex_bail!(InvalidArgument: "Invalid split range {:?}", row_range); } Ok(Self { @@ -84,7 +84,7 @@ impl SplitRange { pub fn check_bounds(&self, row_count: u64) -> VortexResult<()> { if self.row_range.end > row_count { vortex_bail!( - "Split range {:?} is out of bounds for row count {}", + OutOfBounds: "Split range {:?} is out of bounds for row count {}", self.row_range, row_count ); @@ -364,7 +364,7 @@ impl LazyReaderChildren { /// Return the child reader at `idx`, constructing it on first access. pub fn get(&self, idx: usize) -> VortexResult<&LayoutReaderRef> { if idx >= self.cache.len() { - vortex_bail!("Child index out of bounds: {} of {}", idx, self.cache.len()); + vortex_bail!(OutOfBounds: "Child index out of bounds: {} of {}", idx, self.cache.len()); } self.cache[idx].get_or_try_init(|| { diff --git a/vortex-layout/src/scan/execution/adaptor.rs b/vortex-layout/src/scan/execution/adaptor.rs index fc6053d55ca..a3989595e5e 100644 --- a/vortex-layout/src/scan/execution/adaptor.rs +++ b/vortex-layout/src/scan/execution/adaptor.rs @@ -145,7 +145,7 @@ impl ScanAdaptor { self.next_id = self .next_id .checked_add(1) - .ok_or_else(|| vortex_err!("ScanAdaptor ran out of request ids"))?; + .ok_or_else(|| vortex_err!(Overflow: "ScanAdaptor ran out of request ids"))?; self.outstanding.insert(id, (read, segment_id)); Ok(request::IoRequest { intent: IoIntent::Fetch, @@ -159,10 +159,10 @@ impl ScanAdaptor { /// next compute. pub(super) fn set_io_result(&mut self, id: request::IoRequestId, result: IoResult) { let Some((read, segment_id)) = self.outstanding.remove(&id.0) else { - vortex_panic!("ScanAdaptor: delivery of {id:?}, which is not outstanding"); + vortex_panic!(AssertionFailed: "ScanAdaptor: delivery of {id:?}, which is not outstanding"); }; let IoResult::Bytes(bytes) = result else { - vortex_panic!("ScanAdaptor: segment {segment_id} answered with a size"); + vortex_panic!(AssertionFailed: "ScanAdaptor: segment {segment_id} answered with a size"); }; if let Err(error) = self.deliver(read, segment_id, bytes) && self.failed.is_none() @@ -191,6 +191,6 @@ impl ScanAdaptor { self.locations .get(*id as usize) .copied() - .ok_or_else(|| vortex_err!("segment {id} has no known location")) + .ok_or_else(|| vortex_err!(NotFound: "segment {id} has no known location")) } } diff --git a/vortex-layout/src/scan/execution/projection.rs b/vortex-layout/src/scan/execution/projection.rs index 00c0a0614f6..38260dc1caf 100644 --- a/vortex-layout/src/scan/execution/projection.rs +++ b/vortex-layout/src/scan/execution/projection.rs @@ -160,7 +160,7 @@ impl Morsel for ProjectionMorsel { fn compute(&mut self) -> VortexResult { if self.done { - vortex_bail!("ProjectionMorsel: compute called after Done"); + vortex_bail!(AssertionFailed: "ProjectionMorsel: compute called after Done"); } let Some(adaptor) = self.adaptor.as_mut() else { let plans = self diff --git a/vortex-layout/src/scan/filter.rs b/vortex-layout/src/scan/filter.rs index 2cb36068913..0bd6b44b0ad 100644 --- a/vortex-layout/src/scan/filter.rs +++ b/vortex-layout/src/scan/filter.rs @@ -97,7 +97,7 @@ impl FilterExpr { pub fn report_selectivity(&self, conjunct_idx: usize, selectivity: f64) { if !(0.0..=1.0).contains(&selectivity) { vortex_panic!( - "selectivity {} must be in the range [0.0, 1.0]", + InvalidArgument: "selectivity {} must be in the range [0.0, 1.0]", selectivity ); } @@ -121,7 +121,7 @@ impl FilterExpr { histogram .read() .quantile(self.selectivity_quantile) - .map_err(|e| vortex_err!("{e}")) // Only errors when the quantile is out of range + .map_err(|e| vortex_err!(InvalidArgument: "{e}")) // Only errors when the quantile is out of range .vortex_expect("quantile out of range") }) .collect::>>() diff --git a/vortex-layout/src/scan/layout.rs b/vortex-layout/src/scan/layout.rs index ae670958ff4..229dbf71921 100644 --- a/vortex-layout/src/scan/layout.rs +++ b/vortex-layout/src/scan/layout.rs @@ -109,7 +109,7 @@ impl DataSource for LayoutReaderDataSource { _data: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!("LayoutReader splits are not yet serializable"); + vortex_bail!(Serde: "LayoutReader splits are not yet serializable"); } async fn scan(&self, scan_request: ScanRequest) -> VortexResult { diff --git a/vortex-layout/src/scan/multi.rs b/vortex-layout/src/scan/multi.rs index c4a0d56fe3b..fe2227bb366 100644 --- a/vortex-layout/src/scan/multi.rs +++ b/vortex-layout/src/scan/multi.rs @@ -287,7 +287,7 @@ impl DataSource for MultiLayoutDataSource { _data: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!("MultiLayoutDataSource partitions are not yet serializable") + vortex_bail!(Serde: "MultiLayoutDataSource partitions are not yet serializable") } async fn scan(&self, scan_request: ScanRequest) -> VortexResult { @@ -488,7 +488,7 @@ fn reader_partition( ) -> PartitionStream { if reader.dtype() != source_dtype { let error = vortex_err!( - "Multi-layout reader dtype mismatch: expected {}, got {}", + MismatchedTypes: "Multi-layout reader dtype mismatch: expected {}, got {}", source_dtype, reader.dtype() ); diff --git a/vortex-layout/src/scan/repeated_scan.rs b/vortex-layout/src/scan/repeated_scan.rs index 4200d00614a..9b655210a49 100644 --- a/vortex-layout/src/scan/repeated_scan.rs +++ b/vortex-layout/src/scan/repeated_scan.rs @@ -109,7 +109,7 @@ impl RepeatedScan { row_range: Option>, ) -> VortexResult>>>> { if self.limit.is_some() { - vortex_bail!("Split futures do not support row limits; use a scan stream or iterator"); + vortex_bail!(NotImplemented: "Split futures do not support row limits; use a scan stream or iterator"); } let ctx = self.task_context(); @@ -467,7 +467,7 @@ mod tests { #[test] fn error_ends_before_pending_work() { - let arrays = stream::iter([Err::<(), _>(vortex_err!("scan failed"))]) + let arrays = stream::iter([Err::<(), _>(vortex_err!(Other: "scan failed"))]) .chain(stream::pending()) .boxed(); let mut stream = stop_on_error(arrays); diff --git a/vortex-layout/src/scan/scan_builder.rs b/vortex-layout/src/scan/scan_builder.rs index 21dc22c04ca..0e111e498e8 100644 --- a/vortex-layout/src/scan/scan_builder.rs +++ b/vortex-layout/src/scan/scan_builder.rs @@ -664,7 +664,7 @@ mod test { _expr: &BoundExpression, _mask: Mask, ) -> VortexResult { - vortex_bail!("not needed for this test"); + vortex_bail!(NotImplemented: "not needed for this test"); } fn filter_evaluation( @@ -673,7 +673,7 @@ mod test { _expr: &BoundExpression, _mask: MaskFuture, ) -> VortexResult { - vortex_bail!("not needed for this test"); + vortex_bail!(NotImplemented: "not needed for this test"); } fn projection_evaluation( @@ -792,20 +792,22 @@ mod test { _mask: MaskFuture, ) -> VortexResult { if let Some(blocking_projection) = &self.blocking_projection { - blocking_projection - .started - .send(()) - .map_err(|_| vortex_err!("test projection-start receiver dropped"))?; + blocking_projection.started.send(()).map_err( + |_| vortex_err!(AssertionFailed: "test projection-start receiver dropped"), + )?; let _guard = blocking_projection.gate.lock(); } let start = usize::try_from(row_range.start) - .map_err(|_| vortex_err!("row_range.start must fit in usize"))?; + .map_err(|_| vortex_err!(Overflow: "row_range.start must fit in usize"))?; let end = usize::try_from(row_range.end) - .map_err(|_| vortex_err!("row_range.end must fit in usize"))?; + .map_err(|_| vortex_err!(Overflow: "row_range.end must fit in usize"))?; let values: VortexResult> = (start..end) - .map(|v| i32::try_from(v).map_err(|_| vortex_err!("split value must fit in i32"))) + .map(|v| { + i32::try_from(v) + .map_err(|_| vortex_err!(Overflow: "split value must fit in i32")) + }) .collect(); let array = PrimitiveArray::from_iter(values?).into_array(); @@ -921,8 +923,9 @@ mod test { poll_result.is_ok_and(|poll_pending| poll_pending), "first poll must return while scan task construction is blocked" ); - projection_started - .map_err(|_| vortex_err!("stream construction did not begin in the background"))?; + projection_started.map_err( + |_| vortex_err!(AssertionFailed: "stream construction did not begin in the background"), + )?; assert_eq!(calls.load(Ordering::Relaxed), 1); Ok(()) @@ -1241,7 +1244,7 @@ mod test { _expr: &BoundExpression, _mask: Mask, ) -> VortexResult { - vortex_bail!("not needed for this test"); + vortex_bail!(NotImplemented: "not needed for this test"); } fn filter_evaluation( @@ -1250,7 +1253,7 @@ mod test { _expr: &BoundExpression, _mask: MaskFuture, ) -> VortexResult { - vortex_bail!("not needed for this test"); + vortex_bail!(NotImplemented: "not needed for this test"); } fn projection_evaluation( diff --git a/vortex-layout/src/scan/split_by.rs b/vortex-layout/src/scan/split_by.rs index b995e46222f..4023083ed3d 100644 --- a/vortex-layout/src/scan/split_by.rs +++ b/vortex-layout/src/scan/split_by.rs @@ -62,7 +62,7 @@ impl SplitBy { SplitBy::LayoutSubSplitting { max_rows } => { vortex_ensure!( max_rows > 0, - "SplitBy::LayoutSubSplitting requires a non-zero max_rows" + InvalidArgument: "SplitBy::LayoutSubSplitting requires a non-zero max_rows" ); subdivide_large_spans( layout_boundaries(layout_reader, row_range, field_mask)?, @@ -291,7 +291,7 @@ mod test { _: &BoundExpression, _: Mask, ) -> VortexResult { - vortex_bail!("not needed for this test") + vortex_bail!(NotImplemented: "not needed for this test") } fn filter_evaluation( @@ -300,7 +300,7 @@ mod test { _: &BoundExpression, _: MaskFuture, ) -> VortexResult { - vortex_bail!("not needed for this test") + vortex_bail!(NotImplemented: "not needed for this test") } fn projection_evaluation( @@ -309,7 +309,7 @@ mod test { _: &BoundExpression, _: MaskFuture, ) -> VortexResult>> { - vortex_bail!("not needed for this test") + vortex_bail!(NotImplemented: "not needed for this test") } } diff --git a/vortex-layout/src/scan/test.rs b/vortex-layout/src/scan/test.rs index 7d030f2c987..598da4936bc 100644 --- a/vortex-layout/src/scan/test.rs +++ b/vortex-layout/src/scan/test.rs @@ -184,14 +184,14 @@ impl LayoutReader for TestLayoutReader { if self.fail_first_filter && row_range.start == 0 { let len = mask.len(); return Ok(MaskFuture::new(len, async move { - Err(vortex_err!("first split filter failed")) + Err(vortex_err!(Other: "first split filter failed")) })); } let row_range = row_range.clone(); let keep_row = self.keep_row; let row_count = usize::try_from(row_range.end - row_range.start) - .map_err(|_| vortex_err!("row range must fit in usize"))?; + .map_err(|_| vortex_err!(Overflow: "row range must fit in usize"))?; Ok(MaskFuture::new(row_count, async move { let input_mask = mask.await?; @@ -220,12 +220,12 @@ impl LayoutReader for TestLayoutReader { projection_masks.lock().push(mask.true_count()); } if fail { - return Err(vortex_err!("projection failed")); + return Err(vortex_err!(Other: "projection failed")); } let start = i32::try_from(row_range.start) - .map_err(|_| vortex_err!("row_range.start must fit in i32"))?; + .map_err(|_| vortex_err!(Overflow: "row_range.start must fit in i32"))?; let end = i32::try_from(row_range.end) - .map_err(|_| vortex_err!("row_range.end must fit in i32"))?; + .map_err(|_| vortex_err!(Overflow: "row_range.end must fit in i32"))?; PrimitiveArray::from_iter((start..end).map(|value| base + value)) .into_array() .filter(mask) diff --git a/vortex-layout/src/scan/v2/io.rs b/vortex-layout/src/scan/v2/io.rs index ce565846d7e..dc2eb5c48a9 100644 --- a/vortex-layout/src/scan/v2/io.rs +++ b/vortex-layout/src/scan/v2/io.rs @@ -110,14 +110,14 @@ impl IoSource for SegmentIoSource { for request in batch { let IoTarget::Range { offset, len, .. } = request.target else { vortex_bail!( - "SegmentIoSource only serves byte ranges, not {:?}", + NotImplemented: "SegmentIoSource only serves byte ranges, not {:?}", request.target ); }; let segment = *self .ranges .get(&(offset, len)) - .ok_or_else(|| vortex_err!("No segment at bytes {offset}+{len}"))?; + .ok_or_else(|| vortex_err!(NotFound: "No segment at bytes {offset}+{len}"))?; if request.intent == IoIntent::Announce { self.announced .lock() @@ -149,7 +149,7 @@ impl IoSource for SegmentIoSource { let mut bytes = match prefetched.remove(&segment) { Some(read) => read .map_err(move |err| { - vortex_err!("prefetched read of segment {segment} failed: {err}") + vortex_err!(Io: "prefetched read of segment {segment} failed: {err}") }) .boxed(), None => self @@ -204,14 +204,14 @@ impl IoSource for SegmentIoSource { match self.reads.lock().poll_next_unpin(cx) { Poll::Ready(Some(completion)) => Poll::Ready(Ok(completion)), Poll::Ready(None) => Poll::Ready(Err(vortex_err!( - "The split's driver is waiting with no reads in flight" + AssertionFailed: "The split's driver is waiting with no reads in flight" ))), Poll::Pending => Poll::Pending, } } fn wait(&self) -> VortexResult { - vortex_bail!("SegmentIoSource is awaited through poll_completion, not waited on") + vortex_bail!(AssertionFailed: "SegmentIoSource is awaited through poll_completion, not waited on") } fn release(&self, _owner: IoOwnerId) {} @@ -286,7 +286,7 @@ mod tests { receiver .await .map(BufferHandle::new_host) - .map_err(|err| vortex_err!("{err}")) + .map_err(|err| vortex_err!(Io: "{err}")) } .boxed() } diff --git a/vortex-layout/src/scan/v2/tests.rs b/vortex-layout/src/scan/v2/tests.rs index 29fbcf22d11..8e32b7f3db1 100644 --- a/vortex-layout/src/scan/v2/tests.rs +++ b/vortex-layout/src/scan/v2/tests.rs @@ -595,10 +595,10 @@ async fn unordered_yields_before_the_split_finishes() -> VortexResult<()> { .await?; let blocked = *layout .slot(1)? - .ok_or_else(|| vortex_err!("second chunk is missing"))? + .ok_or_else(|| vortex_err!(AssertionFailed: "second chunk is missing"))? .segment_ids() .first() - .ok_or_else(|| vortex_err!("second chunk has no segment"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "second chunk has no segment"))?; let (release, gate) = oneshot::channel(); let segments: Arc = Arc::new(GatedSegments { inner: segments, @@ -612,7 +612,7 @@ async fn unordered_yields_before_the_split_finishes() -> VortexResult<()> { let mut batches = scan.execute_stream()?; let first = batches.try_next().await; let _ = release.send(()); - let first = first?.ok_or_else(|| vortex_err!("first batch is missing"))?; + let first = first?.ok_or_else(|| vortex_err!(AssertionFailed: "first batch is missing"))?; assert_arrays_eq!( first, PrimitiveArray::from_iter(0i32..i32::try_from(MAX_ROWS_PER_CHUNK)?), diff --git a/vortex-layout/src/segments/test.rs b/vortex-layout/src/segments/test.rs index d880d15cc1a..74f227d92bb 100644 --- a/vortex-layout/src/segments/test.rs +++ b/vortex-layout/src/segments/test.rs @@ -31,7 +31,7 @@ impl SegmentSource for TestSegments { async move { buffer .map(BufferHandle::new_host) - .ok_or_else(|| vortex_err!("Segment not found")) + .ok_or_else(|| vortex_err!(NotFound: "Segment not found")) } .boxed() } diff --git a/vortex-layout/src/serde.rs b/vortex-layout/src/serde.rs index 0c67f7dd681..6b8eb2edda7 100644 --- a/vortex-layout/src/serde.rs +++ b/vortex-layout/src/serde.rs @@ -67,16 +67,17 @@ pub fn layout_from_flatbuffer_with_options( let layout_session = session.layouts(); let layouts = layout_session.registry(); let fb_layout = root_with_opts::(&LAYOUT_VERIFIER, &flatbuffer)?; - let encoding_id = layout_ctx - .resolve(fb_layout.encoding()) - .ok_or_else(|| vortex_err!("Invalid encoding ID: {}", fb_layout.encoding()))?; + let encoding_id = layout_ctx.resolve(fb_layout.encoding()).ok_or_else( + || vortex_err!(InvalidArgument: "Invalid encoding ID: {}", fb_layout.encoding()), + )?; let encoding = layouts.get(&encoding_id); if encoding.is_none() && allow_unknown { return foreign_layout_from_fb(fb_layout, dtype, layout_ctx); } - let encoding = - encoding.ok_or_else(|| vortex_err!("Invalid encoding ID: {}", fb_layout.encoding()))?; + let encoding = encoding.ok_or_else( + || vortex_err!(InvalidArgument: "Invalid encoding ID: {}", fb_layout.encoding()), + )?; // SAFETY: we validate the flatbuffer above in the `root` call, and extract a loc. let viewed_children = unsafe { @@ -120,9 +121,9 @@ fn foreign_layout_from_fb( dtype: &DType, layout_ctx: &ReadContext, ) -> VortexResult { - let encoding_id = layout_ctx - .resolve(fb_layout.encoding()) - .ok_or_else(|| vortex_err!("Invalid encoding ID: {}", fb_layout.encoding()))?; + let encoding_id = layout_ctx.resolve(fb_layout.encoding()).ok_or_else( + || vortex_err!(InvalidArgument: "Invalid encoding ID: {}", fb_layout.encoding()), + )?; let children = fb_layout .children() @@ -203,7 +204,7 @@ impl WriteFlatBuffer for LayoutFlatBufferWriter<'_> { // Dictionary-encode the layout ID let encoding = self.ctx.intern(&self.layout.encoding_id()).ok_or_else(|| { vortex_err!( - "Layout encoding {} not permitted by ctx", + Serde: "Layout encoding {} not permitted by ctx", self.layout.encoding_id() ) })?; diff --git a/vortex-layout/src/test.rs b/vortex-layout/src/test.rs index 29eeb8c3eba..7cdbe21f54f 100644 --- a/vortex-layout/src/test.rs +++ b/vortex-layout/src/test.rs @@ -35,6 +35,6 @@ impl crate::LayoutStrategy for FailingStrategy { _eof: crate::sequence::SequencePointer, _session: &VortexSession, ) -> vortex_error::VortexResult { - vortex_error::vortex_bail!("{}", Self::MESSAGE) + vortex_error::vortex_bail!(InvalidArgument: "{}", Self::MESSAGE) } } diff --git a/vortex-mask/src/bitops.rs b/vortex-mask/src/bitops.rs index e795c57204f..7c7b822eed3 100644 --- a/vortex-mask/src/bitops.rs +++ b/vortex-mask/src/bitops.rs @@ -15,7 +15,7 @@ impl BitAnd for &Mask { fn bitand(self, rhs: Self) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!("Masks must have the same length"); + vortex_panic!(InvalidArgument: "Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -34,7 +34,7 @@ impl BitAnd<&Mask> for Mask { /// Owned-left AND: can reuse the left buffer in-place when possible. fn bitand(self, rhs: &Mask) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!("Masks must have the same length"); + vortex_panic!(InvalidArgument: "Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -53,7 +53,7 @@ impl BitOr for &Mask { fn bitor(self, rhs: Self) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!("Masks must have the same length"); + vortex_panic!(InvalidArgument: "Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -72,7 +72,7 @@ impl BitOr<&Mask> for Mask { /// Owned-left OR: can reuse the left buffer in-place when possible. fn bitor(self, rhs: &Mask) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!("Masks must have the same length"); + vortex_panic!(InvalidArgument: "Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -90,7 +90,7 @@ impl Mask { /// Computes `self & !rhs` (AND NOT), equivalent to set difference. pub fn bitand_not(self, rhs: &Mask) -> Mask { if self.len() != rhs.len() { - vortex_panic!("Masks must have the same length"); + vortex_panic!(InvalidArgument: "Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { (AllOr::None, _) | (_, AllOr::All) => Mask::new_false(self.len()), diff --git a/vortex-mask/src/lib.rs b/vortex-mask/src/lib.rs index 14dc417e5bc..eebacb30ee7 100644 --- a/vortex-mask/src/lib.rs +++ b/vortex-mask/src/lib.rs @@ -534,7 +534,7 @@ impl Mask { pub fn rank(&self, n: usize) -> usize { if n >= self.true_count() { vortex_panic!( - "Rank {n} out of bounds for mask with true count {}", + OutOfBounds: "Rank {n} out of bounds for mask with true count {}", self.true_count() ); } @@ -548,7 +548,7 @@ impl Mask { values.buffer.select(n).unwrap_or_else(|| { vortex_panic!( - "Rank {} out of bounds for mask with true count {}", + OutOfBounds: "Rank {} out of bounds for mask with true count {}", values.true_count - 1, values.true_count ) diff --git a/vortex-python-cuda/src/lib.rs b/vortex-python-cuda/src/lib.rs index 61bda67cd7d..655176a39c0 100644 --- a/vortex-python-cuda/src/lib.rs +++ b/vortex-python-cuda/src/lib.rs @@ -218,17 +218,19 @@ impl ArrayChildren for MetadataChildren { .0 .as_slice() .get(index) - .ok_or_else(|| vortex_err!("array metadata child index {index} out of bounds"))? + .ok_or_else( + || vortex_err!(OutOfBounds: "array metadata child index {index} out of bounds"), + )? .clone(); vortex_ensure_eq!( child.dtype(), dtype, - "array metadata child {index} dtype mismatch" + MismatchedTypes: "array metadata child {index} dtype mismatch" ); vortex_ensure_eq!( child.len(), len, - "array metadata child {index} length mismatch" + InvalidArgument: "array metadata child {index} length mismatch" ); Ok(child) } @@ -297,11 +299,10 @@ fn deserialize_metadata_tree( let children = MetadataChildren(children); #[expect(clippy::disallowed_methods, reason = "interning a dynamic id")] let encoding_id = ArrayId::new(&metadata.encoding_id); - let plugin = session - .arrays() - .registry() - .get(&encoding_id) - .ok_or_else(|| vortex_err!("Unknown array encoding: {}", metadata.encoding_id))?; + let plugin = + session.arrays().registry().get(&encoding_id).ok_or_else( + || vortex_err!(NotFound: "Unknown array encoding: {}", metadata.encoding_id), + )?; let decoded = plugin.deserialize( ArrayDeserialization::new( encoding_id, @@ -316,18 +317,18 @@ fn deserialize_metadata_tree( vortex_ensure_eq!( decoded.len(), metadata.len, - "Array decoded from {} has incorrect length", + InvalidArgument: "Array decoded from {} has incorrect length", metadata.encoding_id ); vortex_ensure_eq!( decoded.dtype(), &dtype, - "Array decoded from {} has incorrect dtype", + MismatchedTypes: "Array decoded from {} has incorrect dtype", metadata.encoding_id ); vortex_ensure!( plugin.is_supported_encoding(&decoded.encoding_id()), - "Array decoded from {} has incorrect encoding {}", + MismatchedTypes: "Array decoded from {} has incorrect encoding {}", metadata.encoding_id, decoded.encoding_id() ); diff --git a/vortex-python/src/arrays/py/vtable.rs b/vortex-python/src/arrays/py/vtable.rs index 686390fdddf..37d975cdc0c 100644 --- a/vortex-python/src/arrays/py/vtable.rs +++ b/vortex-python/src/arrays/py/vtable.rs @@ -66,9 +66,9 @@ impl VTable for PythonVTable { len: usize, _slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(data.vtable.id, self.id, "PythonArray vtable id mismatch"); - vortex_ensure_eq!(&data.dtype, dtype, "PythonArray dtype mismatch"); - vortex_ensure_eq!(data.len, len, "PythonArray len mismatch"); + vortex_ensure_eq!(data.vtable.id, self.id, MismatchedTypes: "PythonArray vtable id mismatch"); + vortex_ensure_eq!(&data.dtype, dtype, MismatchedTypes: "PythonArray dtype mismatch"); + vortex_ensure_eq!(data.len, len, InvalidArgument: "PythonArray len mismatch"); Ok(()) } @@ -77,7 +77,7 @@ impl VTable for PythonVTable { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!("PythonArray buffer index {idx} out of bounds") + vortex_panic!(OutOfBounds: "PythonArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -109,15 +109,15 @@ impl VTable for PythonVTable { _session: &VortexSession, ) -> VortexResult> { _ = bytes; - vortex_bail!("PythonArray deserialization is not supported"); + vortex_bail!(Serde: "PythonArray deserialization is not supported"); } fn slot_name(_array: ArrayView<'_, Self>, _idx: usize) -> String { - vortex_panic!("PythonArray has no slots") + vortex_panic!(OutOfBounds: "PythonArray has no slots") } fn execute(_array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { - vortex_bail!("PythonArray execution is not supported"); + vortex_bail!(NotImplemented: "PythonArray execution is not supported"); } } @@ -129,12 +129,12 @@ impl OperationsVTable for PythonVTable { _index: usize, _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!("PythonArray scalar_at is not supported"); + vortex_bail!(NotImplemented: "PythonArray scalar_at is not supported"); } } impl ValidityVTable for PythonVTable { fn validity(_array: ArrayView<'_, PythonVTable>) -> VortexResult { - vortex_bail!("PythonArray validity is not supported"); + vortex_bail!(NotImplemented: "PythonArray validity is not supported"); } } diff --git a/vortex-python/src/arrays/range_to_sequence.rs b/vortex-python/src/arrays/range_to_sequence.rs index c8804c565a4..8ab88a749e2 100644 --- a/vortex-python/src/arrays/range_to_sequence.rs +++ b/vortex-python/src/arrays/range_to_sequence.rs @@ -23,7 +23,7 @@ pub fn sequence_array_from_range + Into> dtype: DType, ) -> VortexResult { if step == 0 { - vortex_bail!("Step must not be zero"); + vortex_bail!(InvalidArgument: "Step must not be zero"); } // A `Sequence` holds at least one element, so an empty range returns a primitive array @@ -39,13 +39,13 @@ pub fn sequence_array_from_range + Into> } let Ok(start) = T::try_from(start) else { vortex_bail!( - "Start, {}, does not fit in requested dtype: {}", + Overflow: "Start, {}, does not fit in requested dtype: {}", start, dtype ); }; let Ok(step) = T::try_from(step) else { - vortex_bail!("Step, {}, does not fit in requested dtype: {}", step, dtype); + vortex_bail!(Overflow: "Step, {}, does not fit in requested dtype: {}", step, dtype); }; Ok(Sequence::try_new_typed::(start, step, dtype.nullability(), len)?.into_array()) diff --git a/vortex-python/src/dtype/decimal.rs b/vortex-python/src/dtype/decimal.rs index 9e249c4c8e4..ec89db8db13 100644 --- a/vortex-python/src/dtype/decimal.rs +++ b/vortex-python/src/dtype/decimal.rs @@ -22,7 +22,7 @@ impl PyDecimalDType { #[getter] fn precision(slf: PyRef) -> PyResult { let DType::Decimal(decimal_dtype, _) = slf.as_ref().deref() else { - vortex_panic!("Not a decimal DType"); + vortex_panic!(MismatchedTypes: "Not a decimal DType"); }; Ok(decimal_dtype.precision()) } @@ -32,7 +32,7 @@ impl PyDecimalDType { #[getter] fn scale(slf: PyRef) -> PyResult { let DType::Decimal(decimal_dtype, _) = slf.as_ref().deref() else { - vortex_panic!("Not a decimal DType"); + vortex_panic!(MismatchedTypes: "Not a decimal DType"); }; Ok(decimal_dtype.scale()) } diff --git a/vortex-python/src/dtype/primitive.rs b/vortex-python/src/dtype/primitive.rs index e6c4625d2e3..922761c2431 100644 --- a/vortex-python/src/dtype/primitive.rs +++ b/vortex-python/src/dtype/primitive.rs @@ -20,7 +20,7 @@ impl PyPrimitiveDType { #[getter] fn ptype(slf: PyRef) -> PyPType { let DType::Primitive(ptype, _) = slf.as_ref().deref() else { - vortex_panic!("Not a primitive DType"); + vortex_panic!(MismatchedTypes: "Not a primitive DType"); }; PyPType::from(*ptype) } diff --git a/vortex-python/src/dtype/struct_.rs b/vortex-python/src/dtype/struct_.rs index 709147ee96b..3dd2140d41c 100644 --- a/vortex-python/src/dtype/struct_.rs +++ b/vortex-python/src/dtype/struct_.rs @@ -18,7 +18,7 @@ impl PyStructDType { /// Returns the names of the struct fields. pub fn names(self_: PyRef<'_, Self>) -> PyResult> { let DType::Struct(dtype, _) = self_.as_ref().deref() else { - vortex_panic!("Not a struct DType"); + vortex_panic!(MismatchedTypes: "Not a struct DType"); }; Ok(dtype.names().iter().map(|name| name.to_string()).collect()) @@ -27,7 +27,7 @@ impl PyStructDType { /// Returns the field DTypes of the struct. pub fn fields(self_: PyRef<'_, Self>) -> PyResult>> { let DType::Struct(dtype, _) = self_.as_ref().deref() else { - vortex_panic!("Not a struct DType"); + vortex_panic!(MismatchedTypes: "Not a struct DType"); }; let mut fields = Vec::with_capacity(dtype.names().len()); diff --git a/vortex-python/src/error.rs b/vortex-python/src/error.rs index d419892d047..f7957259203 100644 --- a/vortex-python/src/error.rs +++ b/vortex-python/src/error.rs @@ -3,8 +3,17 @@ use pyo3::CastError; use pyo3::PyErr; +use pyo3::exceptions::PyAssertionError; +use pyo3::exceptions::PyIndexError; +use pyo3::exceptions::PyKeyError; +use pyo3::exceptions::PyNotImplementedError; +use pyo3::exceptions::PyOSError; +use pyo3::exceptions::PyOverflowError; use pyo3::exceptions::PyRuntimeError; +use pyo3::exceptions::PyTypeError; +use pyo3::exceptions::PyValueError; use vortex::error::VortexError; +use vortex::error::VortexErrorKind; /// Error type to merge [`VortexError`] and [`PyErr`]. pub enum PyVortexError { @@ -37,7 +46,24 @@ impl From for PyErr { fn from(value: PyVortexError) -> Self { match value { PyVortexError::Py(py) => py, - PyVortexError::Vortex(vx) => PyRuntimeError::new_err(vx.to_string()), + PyVortexError::Vortex(vx) => vortex_to_py_err(vx), } } } + +/// Raises a [`VortexError`] as the Python exception its kind is the analogue of. +fn vortex_to_py_err(error: VortexError) -> PyErr { + let message = error.to_string(); + match error.kind() { + VortexErrorKind::OutOfBounds => PyIndexError::new_err(message), + VortexErrorKind::NotFound => PyKeyError::new_err(message), + VortexErrorKind::Overflow => PyOverflowError::new_err(message), + VortexErrorKind::InvalidArgument | VortexErrorKind::Serde => PyValueError::new_err(message), + VortexErrorKind::NotImplemented => PyNotImplementedError::new_err(message), + VortexErrorKind::MismatchedTypes => PyTypeError::new_err(message), + VortexErrorKind::AssertionFailed => PyAssertionError::new_err(message), + VortexErrorKind::Io => PyOSError::new_err(message), + // `Other`, and any kind added after this binding was written. + _ => PyRuntimeError::new_err(message), + } +} diff --git a/vortex-python/src/iter/python.rs b/vortex-python/src/iter/python.rs index 10d061ff0b8..2f99ad49883 100644 --- a/vortex-python/src/iter/python.rs +++ b/vortex-python/src/iter/python.rs @@ -52,7 +52,7 @@ impl Iterator for PythonArrayIterator { Ok(array) } }) - .map_err(|pyerr| vortex_err!("{}", pyerr)) + .map_err(|pyerr| vortex_err!(Other: "{}", pyerr)) }) }) } diff --git a/vortex-python/src/object_store/resolve.rs b/vortex-python/src/object_store/resolve.rs index ab392c1a038..f45e2281b1e 100644 --- a/vortex-python/src/object_store/resolve.rs +++ b/vortex-python/src/object_store/resolve.rs @@ -37,9 +37,9 @@ pub(crate) fn resolve_store( None => { match Url::parse(url_or_path) { Ok(url) if url.scheme() == "file" => { - let path = url - .to_file_path() - .map_err(|_| vortex_err!("invalid file URL: {url_or_path}"))?; + let path = url.to_file_path().map_err( + |_| vortex_err!(InvalidArgument: "invalid file URL: {url_or_path}"), + )?; Ok(ResolvedStore::Path(path)) } // `Url::parse` accepts a Windows absolute path like `C:\data` as a URL whose diff --git a/vortex-python/src/python_repr.rs b/vortex-python/src/python_repr.rs index ebddf6f3f89..5fcbba58f19 100644 --- a/vortex-python/src/python_repr.rs +++ b/vortex-python/src/python_repr.rs @@ -92,7 +92,7 @@ impl Display for DTypePythonRepr<'_> { .join(", "), n.python_repr() ), - DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), DType::Variant(_) => write!(f, "variant()"), DType::Extension(ext) => { write!( diff --git a/vortex-python/src/readable.rs b/vortex-python/src/readable.rs index e8d78e54c1c..f6dbbf187fe 100644 --- a/vortex-python/src/readable.rs +++ b/vortex-python/src/readable.rs @@ -202,9 +202,9 @@ impl VortexReadAt for PyReadable { // Reject an invalid range before it waits for a permit or occupies a blocking thread. let end = offset .checked_add(length as u64) - .ok_or_else(|| vortex_err!("read {offset}+{length} overflows u64"))?; + .ok_or_else(|| vortex_err!(Overflow: "read {offset}+{length} overflows u64"))?; if end > len { - vortex_bail!("read {offset}..{end} out of bounds for file of length {len}"); + vortex_bail!(OutOfBounds: "read {offset}..{end} out of bounds for file of length {len}"); } // Take a permit before occupying a blocking thread. For file objects the single permit @@ -228,7 +228,7 @@ impl VortexReadAt for PyReadable { read_fully(py, obj, protocol, offset, buffer).map(|b| b.freeze()) } } - .map_err(|err| vortex_err!("Python read of {offset}..{end} failed: {err}")) + .map_err(|err| vortex_err!(Io: "Python read of {offset}..{end} failed: {err}")) })?; Ok(BufferHandle::new_host(buffer)) }) diff --git a/vortex-python/src/scalar/into_py.rs b/vortex-python/src/scalar/into_py.rs index 5c98dd9e022..489c0da9913 100644 --- a/vortex-python/src/scalar/into_py.rs +++ b/vortex-python/src/scalar/into_py.rs @@ -129,7 +129,7 @@ impl<'py> IntoPyObject<'py> for PyVortex> { let dict = PyDict::new(py); for (child, name) in fields.zip(self.0.names().iter()) { dict.set_item(name.to_string(), PyVortex(&child).into_pyobject(py)?) - .map_err(|e| vortex_err!("Failed to set item in dictionary {}", e)) + .map_err(|e| vortex_err!(Other: "Failed to set item in dictionary {}", e)) .vortex_expect("Failed to set item in dictionary"); } Ok(dict.into_pyobject(py)?.into_any()) diff --git a/vortex-python/src/scalar/struct_.rs b/vortex-python/src/scalar/struct_.rs index bdcfd65ecb9..7ddd83227e8 100644 --- a/vortex-python/src/scalar/struct_.rs +++ b/vortex-python/src/scalar/struct_.rs @@ -31,7 +31,7 @@ impl PyStructScalar { let scalar = self_.as_scalar_ref(); let child = scalar .field(name) - .ok_or_else(|| vortex_err!("No field {name}"))?; + .ok_or_else(|| vortex_err!(NotFound: "No field {name}"))?; Ok(PyVortex(&child) .into_pyobject(self_.py()) .map(|v| v.into())?) diff --git a/vortex-python/test/test_file_arrow_indices.py b/vortex-python/test/test_file_arrow_indices.py index d911c2e6933..c9e2222e134 100644 --- a/vortex-python/test/test_file_arrow_indices.py +++ b/vortex-python/test/test_file_arrow_indices.py @@ -75,7 +75,7 @@ def test_arrow_indices_apply_filter_then_limit(indexed_file): def test_arrow_indices_use_scan_validation(indexed_file, indices): file, _ = indexed_file indices = vx.array(pa.array(indices, type=pa.uint64())) - with pytest.raises(RuntimeError): + with pytest.raises(ValueError): file.to_arrow(indices=indices) diff --git a/vortex-row/src/codec.rs b/vortex-row/src/codec.rs index 2814ca03390..9b2e2cc8bc1 100644 --- a/vortex-row/src/codec.rs +++ b/vortex-row/src/codec.rs @@ -241,12 +241,12 @@ pub(crate) fn row_width_for_dtype(dtype: &DType) -> VortexResult { // FSL is fixed iff its element type is fixed. Add a sentinel byte for the FSL // itself, then `n` copies of the element width. RowWidth::Fixed(w) => { - let body = w - .checked_mul(*n) - .ok_or_else(|| vortex_error::vortex_err!("FSL row width overflows u32"))?; - let total = body - .checked_add(1) - .ok_or_else(|| vortex_error::vortex_err!("FSL row width overflows u32"))?; + let body = w.checked_mul(*n).ok_or_else( + || vortex_error::vortex_err!(Overflow: "FSL row width overflows u32"), + )?; + let total = body.checked_add(1).ok_or_else( + || vortex_error::vortex_err!(Overflow: "FSL row width overflows u32"), + )?; Ok(RowWidth::Fixed(total)) } RowWidth::Variable => Ok(RowWidth::Variable), @@ -258,7 +258,7 @@ pub(crate) fn row_width_for_dtype(dtype: &DType) -> VortexResult { match row_width_for_dtype(&field_dtype)? { RowWidth::Fixed(w) => { total = total.checked_add(w).ok_or_else(|| { - vortex_error::vortex_err!("Struct row width overflows u32") + vortex_error::vortex_err!(Overflow: "Struct row width overflows u32") })?; } RowWidth::Variable => return Ok(RowWidth::Variable), @@ -271,10 +271,12 @@ pub(crate) fn row_width_for_dtype(dtype: &DType) -> VortexResult { Ok(RowWidth::Variable) } DType::Variant(_) => { - vortex_bail!("row encoding does not support Variant arrays (no well-defined ordering)") + vortex_bail!(InvalidArgument: "row encoding does not support Variant arrays (no well-defined ordering)") } - DType::Union(..) => vortex_bail!("row encoding does not support Union arrays"), - dtype => vortex_bail!("row encoding does not support dtype: {dtype:?}"), + DType::Union(..) => { + vortex_bail!(InvalidArgument: "row encoding does not support Union arrays") + } + dtype => vortex_bail!(InvalidArgument: "row encoding does not support dtype: {dtype:?}"), } } @@ -303,11 +305,11 @@ pub(crate) fn field_size( Canonical::List(arr) => add_size_list(arr, field, sizes, ctx)?, Canonical::Map(arr) => add_size_map(arr, field, sizes, ctx)?, Canonical::Variant(_) => { - vortex_bail!("row encoding does not support Variant arrays (no well-defined ordering)") + vortex_bail!(InvalidArgument: "row encoding does not support Variant arrays (no well-defined ordering)") } unsupported => { vortex_bail!( - "row encoding does not support canonical array: {:?}", + InvalidArgument: "row encoding does not support canonical array: {:?}", unsupported.dtype() ) } @@ -414,11 +416,11 @@ pub(crate) fn field_encode( Canonical::List(arr) => encode_list(arr, field, offsets, cursors, out, ctx)?, Canonical::Map(arr) => encode_map(arr, field, offsets, cursors, out, ctx)?, Canonical::Variant(_) => { - vortex_bail!("row encoding does not support Variant arrays (no well-defined ordering)") + vortex_bail!(InvalidArgument: "row encoding does not support Variant arrays (no well-defined ordering)") } unsupported => { vortex_bail!( - "row encoding does not support canonical array: {:?}", + InvalidArgument: "row encoding does not support canonical array: {:?}", unsupported.dtype() ) } @@ -522,9 +524,9 @@ fn prepare_list( let mut total = 0u32; for &size in &element_sizes { element_offsets.push(total); - total = total - .checked_add(size) - .ok_or_else(|| vortex_error::vortex_err!("list element bytes overflow u32"))?; + total = total.checked_add(size).ok_or_else( + || vortex_error::vortex_err!(Overflow: "list element bytes overflow u32"), + )?; } Ok(PreparedList { mask, @@ -545,17 +547,18 @@ fn add_size_prepared_list(prepared: &PreparedList, sizes: &mut [u32]) -> VortexR let body = prepared.element_sizes[offset..offset + len] .iter() .try_fold(0u32, |sum, &size| sum.checked_add(size)) - .ok_or_else(|| vortex_error::vortex_err!("list element sizes overflow u32"))?; - body.checked_add( - u32::try_from(len) - .map_err(|_| vortex_error::vortex_err!("list element count overflows u32"))?, - ) + .ok_or_else( + || vortex_error::vortex_err!(Overflow: "list element sizes overflow u32"), + )?; + body.checked_add(u32::try_from(len).map_err( + |_| vortex_error::vortex_err!(Overflow: "list element count overflows u32"), + )?) .and_then(|size| size.checked_add(2)) - .ok_or_else(|| vortex_error::vortex_err!("list row size overflows u32"))? + .ok_or_else(|| vortex_error::vortex_err!(Overflow: "list row size overflows u32"))? }; sizes[i] = sizes[i] .checked_add(contribution) - .ok_or_else(|| vortex_error::vortex_err!("per-row size overflow"))?; + .ok_or_else(|| vortex_error::vortex_err!(Overflow: "per-row size overflow"))?; } Ok(()) } diff --git a/vortex-row/src/encode.rs b/vortex-row/src/encode.rs index c88f164c10a..9bcf48eb287 100644 --- a/vortex-row/src/encode.rs +++ b/vortex-row/src/encode.rs @@ -106,7 +106,7 @@ fn execute_row_encode( ) -> VortexResult { let nrows = args.row_count(); if u32::try_from(nrows).is_err() { - vortex_bail!("row-encoded input has {} rows, exceeds u32::MAX", nrows); + vortex_bail!(Overflow: "row-encoded input has {} rows, exceeds u32::MAX", nrows); } // ===== Phase 1: classify + size pass ===== @@ -126,10 +126,10 @@ fn execute_row_encode( .checked_mul(u64::from(fixed_per_row)) .and_then(|t| t.checked_add(var_total)) .ok_or_else(|| { - vortex_error::vortex_err!("row-encoded total bytes overflow u64 (nrows * fixed + var)") + vortex_error::vortex_err!(Overflow: "row-encoded total bytes overflow u64 (nrows * fixed + var)") })?; if total > u32::MAX as u64 { - vortex_bail!("row-encoded output size {} bytes exceeds u32::MAX", total); + vortex_bail!(Overflow: "row-encoded output size {} bytes exceeds u32::MAX", total); } let total_len = usize::try_from(total).vortex_expect("validated row-encoded output size must fit usize"); diff --git a/vortex-row/src/encoder.rs b/vortex-row/src/encoder.rs index 1346d8ffc7e..1f24526d091 100644 --- a/vortex-row/src/encoder.rs +++ b/vortex-row/src/encoder.rs @@ -93,13 +93,13 @@ impl RowEncoder { /// [`encode`](Self::encode) and [`row_sizes`](Self::row_sizes). fn prepare(&self, cols: &[ArrayRef]) -> VortexResult<(RowEncodingOptions, VecExecutionArgs)> { if cols.is_empty() { - vortex_bail!("RowEncoder: at least one column is required"); + vortex_bail!(InvalidArgument: "RowEncoder: at least one column is required"); } let options = match &self.options { Some(options) => { if options.len() != cols.len() { vortex_bail!( - "RowEncoder: options describe {} columns but {} were provided", + InvalidArgument: "RowEncoder: options describe {} columns but {} were provided", options.len(), cols.len() ); @@ -113,7 +113,7 @@ impl RowEncoder { reject_extension_dtype(col.dtype())?; if col.len() != nrows { vortex_bail!( - "RowEncoder: column {} has length {} but expected {}", + InvalidArgument: "RowEncoder: column {} has length {} but expected {}", i, col.len(), nrows @@ -128,7 +128,7 @@ fn reject_extension_dtype(dtype: &DType) -> VortexResult<()> { match dtype { DType::Extension(ext_dtype) => { vortex_bail!( - "row encoding does not support Extension arrays yet: {}", + InvalidArgument: "row encoding does not support Extension arrays yet: {}", ext_dtype.id() ) } diff --git a/vortex-row/src/options.rs b/vortex-row/src/options.rs index 380c9a3827f..eaf744c2c2a 100644 --- a/vortex-row/src/options.rs +++ b/vortex-row/src/options.rs @@ -168,14 +168,14 @@ pub(crate) fn deserialize_row_encoding_options( ) -> vortex_error::VortexResult { if bytes.len() < 4 { vortex_error::vortex_bail!( - "RowEncodingOptions metadata must contain a 4-byte length prefix" + Serde: "RowEncodingOptions metadata must contain a 4-byte length prefix" ); } let n = u32::from_le_bytes([bytes[0], bytes[1], bytes[2], bytes[3]]) as usize; let expected = 4 + 2 * n; if bytes.len() != expected { vortex_error::vortex_bail!( - "RowEncodingOptions metadata wrong size: got {}, expected {}", + InvalidArgument: "RowEncodingOptions metadata wrong size: got {}, expected {}", bytes.len(), expected ); diff --git a/vortex-row/src/size.rs b/vortex-row/src/size.rs index d475d3e6412..d7607821bd7 100644 --- a/vortex-row/src/size.rs +++ b/vortex-row/src/size.rs @@ -84,11 +84,11 @@ pub(crate) fn compute_sizes( ) -> VortexResult { let n_inputs = args.num_inputs(); if n_inputs == 0 { - vortex_bail!("at least one input column is required"); + vortex_bail!(InvalidArgument: "at least one input column is required"); } if options.len() != n_inputs { vortex_bail!( - "options len ({}) does not match num_inputs ({})", + MismatchedTypes: "options len ({}) does not match num_inputs ({})", options.len(), n_inputs ); @@ -106,7 +106,7 @@ pub(crate) fn compute_sizes( let col = args.get(i)?; if col.len() != nrows { vortex_bail!( - "column {} has length {} but expected {}", + InvalidArgument: "column {} has length {} but expected {}", i, col.len(), nrows @@ -121,8 +121,7 @@ pub(crate) fn compute_sizes( prefix: running_fixed_prefix, before_varlen: first_varlen_idx.is_none(), }); - let overflow = - || vortex_error::vortex_err!("per-row fixed width overflows u32 at column {i}"); + let overflow = || vortex_error::vortex_err!(Overflow: "per-row fixed width overflows u32 at column {i}"); fixed_per_row = fixed_per_row.checked_add(w).ok_or_else(overflow)?; running_fixed_prefix = running_fixed_prefix.checked_add(w).ok_or_else(overflow)?; columns.push(PreparedField::Canonical(canonical)); diff --git a/vortex-scan/src/lib.rs b/vortex-scan/src/lib.rs index a15b49d4a67..1e9bb1dd57c 100644 --- a/vortex-scan/src/lib.rs +++ b/vortex-scan/src/lib.rs @@ -113,7 +113,7 @@ pub trait DataSource: 'static + Send + Sync { session: &VortexSession, ) -> VortexResult { let _ = (data, session); - vortex_bail!("DataSource does not support deserialization") + vortex_bail!(Serde: "DataSource does not support deserialization") } /// Returns a scan over the source. diff --git a/vortex-scan/src/planning/driver/mod.rs b/vortex-scan/src/planning/driver/mod.rs index 8cb78099272..620f4494178 100644 --- a/vortex-scan/src/planning/driver/mod.rs +++ b/vortex-scan/src/planning/driver/mod.rs @@ -131,12 +131,12 @@ impl Work { fn deliver(&mut self, request: IoRequestId, result: IoResult) -> VortexResult<()> { let Some(target) = self.outstanding.remove(&request) else { vortex_bail!( - "completion for {request:?} of {:?}, which is not outstanding", + AssertionFailed: "completion for {request:?} of {:?}, which is not outstanding", self.id ); }; if !result.matches(&target) { - vortex_bail!("IO source answered {target:?} with {}", result.kind()); + vortex_bail!(AssertionFailed: "IO source answered {target:?} with {}", result.kind()); } self.consumer().set_io_result(request, result); Ok(()) @@ -279,7 +279,7 @@ impl Run { if let Some(limit) = self.step_limit && self.steps > limit { - vortex_bail!("driver exceeded its step limit of {limit}"); + vortex_bail!(AssertionFailed: "driver exceeded its step limit of {limit}"); } self.visit(work)?; } @@ -302,7 +302,7 @@ impl Run { self.queue.insert(work); } else if work.outstanding.is_empty() { vortex_bail!( - "work for scope {:?} waits with no outstanding fetch", + AssertionFailed: "work for scope {:?} waits with no outstanding fetch", work.scope ); } @@ -310,7 +310,7 @@ impl Run { } // An item that published fetches and had CPU work left is still in the run queue. let Some(work) = self.queue.work.get_mut(&owner) else { - vortex_bail!("completion for unknown work {owner:?}"); + vortex_bail!(AssertionFailed: "completion for unknown work {owner:?}"); }; work.deliver(request, result) } @@ -327,7 +327,7 @@ impl Run { .collect(); if sources.is_empty() { return Poll::Ready(Err(vortex_err!( - "the run is waiting for IO with no live root" + AssertionFailed: "the run is waiting for IO with no live root" ))); } let mut delivered = false; @@ -410,7 +410,7 @@ impl Run { fn park(&mut self, work: Box) -> VortexResult<()> { if work.outstanding.is_empty() { vortex_bail!( - "work for scope {:?} waits with no outstanding fetch", + AssertionFailed: "work for scope {:?} waits with no outstanding fetch", work.scope ); } @@ -464,7 +464,7 @@ impl Run { } Output::Morsel(MorselOutput::Batch(array)) => { if array.is_empty() { - vortex_bail!("morsel for scope {:?} returned an empty batch", work.scope); + vortex_bail!(AssertionFailed: "morsel for scope {:?} returned an empty batch", work.scope); } self.events.push_back(Progress::Batch(Batch { root: work.root, @@ -480,7 +480,7 @@ impl Run { /// Registers the requests an item published with its root's session. fn submit(&mut self, work: &mut Work, batch: IoBatch) -> VortexResult<()> { if batch.is_empty() { - vortex_bail!("compute() published an empty batch"); + vortex_bail!(AssertionFailed: "compute() published an empty batch"); } for request in &batch { if request.intent == IoIntent::Fetch @@ -490,14 +490,14 @@ impl Run { .is_some() { vortex_bail!( - "fetch {:?} of {:?} was published while it is outstanding", + AssertionFailed: "fetch {:?} of {:?} was published while it is outstanding", request.request, work.id ); } } let Some(root) = self.roots.get(&work.root) else { - vortex_bail!("work {:?} outlived its root {:?}", work.id, work.root); + vortex_bail!(AssertionFailed: "work {:?} outlived its root {:?}", work.id, work.root); }; root.io.submit(work.id, batch) } diff --git a/vortex-scan/src/planning/next.rs b/vortex-scan/src/planning/next.rs index 49d500593ad..119aef7fc81 100644 --- a/vortex-scan/src/planning/next.rs +++ b/vortex-scan/src/planning/next.rs @@ -62,7 +62,7 @@ mod tests { #[test] fn next_fn_reports_constructor_errors() { let next: Next = next_fn(|input: u32| -> VortexResult { - vortex_bail!("constructor rejected {input}") + vortex_bail!(InvalidArgument: "constructor rejected {input}") }); let err = next(7).err().map(|e| e.to_string()); assert!( diff --git a/vortex-scan/src/planning/tests/scripted.rs b/vortex-scan/src/planning/tests/scripted.rs index 5573dafa7df..083db3c0385 100644 --- a/vortex-scan/src/planning/tests/scripted.rs +++ b/vortex-scan/src/planning/tests/scripted.rs @@ -361,8 +361,10 @@ impl IoSource for RecordingIoSource { Ok(IoResult::Bytes(BufferHandle::new_host(bytes.clone()))) } Some(Canned::Size(size)) => Ok(IoResult::Size(*size)), - Some(Canned::Fail(message)) => Err(vortex_err!("{message}")), - None => Err(vortex_err!("no canned answer for {:?}", request.target)), + Some(Canned::Fail(message)) => Err(vortex_err!(Io: "{message}")), + None => { + Err(vortex_err!(AssertionFailed: "no canned answer for {:?}", request.target)) + } }; self.ready.lock().push(Completion { owner: work, @@ -399,7 +401,9 @@ impl IoSource for RecordingIoSource { Order::Fifo => None, Order::Lifo => ready.pop(), }; - completion.ok_or_else(|| vortex_err!("RecordingIoSource: wait with nothing outstanding")) + completion.ok_or_else( + || vortex_err!(AssertionFailed: "RecordingIoSource: wait with nothing outstanding"), + ) } } diff --git a/vortex-scan/src/selection.rs b/vortex-scan/src/selection.rs index 3df51aaccab..f830fc8841a 100644 --- a/vortex-scan/src/selection.rs +++ b/vortex-scan/src/selection.rs @@ -147,7 +147,7 @@ fn relativize(range: &Range, idx: u64) -> usize { .and_then(|relative| usize::try_from(relative).ok()) .unwrap_or_else(|| { vortex_panic!( - "index {:?} is not a usize offset into range {:?}", + Overflow: "index {:?} is not a usize offset into range {:?}", idx, range ) diff --git a/vortex-scan/src/strict_sorted_buffer.rs b/vortex-scan/src/strict_sorted_buffer.rs index d508345cdd8..f4da7eac651 100644 --- a/vortex-scan/src/strict_sorted_buffer.rs +++ b/vortex-scan/src/strict_sorted_buffer.rs @@ -40,7 +40,7 @@ impl StrictSortedBuffer { for (idx, window) in buffer.windows(2).enumerate() { if window[0] >= window[1] { vortex_bail!( - "buffer values must be strictly increasing at positions {} and {}", + InvalidArgument: "buffer values must be strictly increasing at positions {} and {}", idx, idx + 1 ); diff --git a/vortex-session/src/session.rs b/vortex-session/src/session.rs index 0103a95eb52..572035cecd0 100644 --- a/vortex-session/src/session.rs +++ b/vortex-session/src/session.rs @@ -222,7 +222,7 @@ impl VortexSession { pub fn with_some(self, var: V) -> Self { if self.get_opt::().is_some() { vortex_panic!( - "Session variable of type {} already exists", + InvalidArgument: "Session variable of type {} already exists", type_name::() ); } diff --git a/vortex-spatial/src/aggregate_fn/aabb.rs b/vortex-spatial/src/aggregate_fn/aabb.rs index 3ef24a619a7..d767f64e820 100644 --- a/vortex-spatial/src/aggregate_fn/aabb.rs +++ b/vortex-spatial/src/aggregate_fn/aabb.rs @@ -97,7 +97,7 @@ fn rect_from_storage(scalar: &Scalar) -> VortexResult>> f64::try_from( &fields .field(name) - .ok_or_else(|| vortex_err!("AABB missing {name}"))?, + .ok_or_else(|| vortex_err!(NotFound: "AABB missing {name}"))?, ) }; Ok(Some(SpatialRect::new( diff --git a/vortex-spatial/src/extension/coordinate.rs b/vortex-spatial/src/extension/coordinate.rs index 43599a705b7..71a093be803 100644 --- a/vortex-spatial/src/extension/coordinate.rs +++ b/vortex-spatial/src/extension/coordinate.rs @@ -49,7 +49,7 @@ impl Dimension { let mut strs = [""; 4]; vortex_ensure!( names.len() <= strs.len(), - "not a valid GeoArrow coordinate dimension: {names:?}" + InvalidArgument: "not a valid GeoArrow coordinate dimension: {names:?}" ); for (slot, name) in strs.iter_mut().zip(names.iter()) { *slot = name.as_ref(); @@ -59,7 +59,9 @@ impl Dimension { ["x", "y", "z"] => Dimension::Xyz, ["x", "y", "m"] => Dimension::Xym, ["x", "y", "z", "m"] => Dimension::Xyzm, - _ => vortex_bail!("not a valid GeoArrow coordinate dimension: {names:?}"), + _ => { + vortex_bail!(InvalidArgument: "not a valid GeoArrow coordinate dimension: {names:?}") + } }) } @@ -154,7 +156,7 @@ impl Display for Coordinate { /// [`Dimension`]. Any of the four GeoArrow dimensions validates. pub(crate) fn coordinate_dimension(dtype: &DType) -> VortexResult { let DType::Struct(fields, _) = dtype else { - vortex_bail!("coordinate storage must be a Struct, was {dtype}"); + vortex_bail!(MismatchedTypes: "coordinate storage must be a Struct, was {dtype}"); }; for (name, field) in fields.names().iter().zip(fields.fields()) { vortex_ensure!( @@ -162,7 +164,7 @@ pub(crate) fn coordinate_dimension(dtype: &DType) -> VortexResult { field, DType::Primitive(PType::F64, Nullability::NonNullable) ), - "coordinate field {name} must be non-nullable f64, was {field}" + MismatchedTypes: "coordinate field {name} must be non-nullable f64, was {field}" ); } Dimension::from_field_names(fields.names()) @@ -191,7 +193,7 @@ pub(crate) fn coordinate_from_struct(scalar: &Scalar) -> VortexResult VortexResult> { diff --git a/vortex-spatial/src/extension/linestring.rs b/vortex-spatial/src/extension/linestring.rs index 824692617da..9a744d11b2f 100644 --- a/vortex-spatial/src/extension/linestring.rs +++ b/vortex-spatial/src/extension/linestring.rs @@ -107,7 +107,7 @@ pub(crate) fn linestring_storage_dtype(dim: Dimension, nullability: Nullability) /// Validate `dtype` is `List` and return its [`Dimension`]. pub(crate) fn linestring_dimension(dtype: &DType) -> VortexResult { let DType::List(coords, _) = dtype else { - vortex_bail!("linestring storage must be a List of coordinates, was {dtype}"); + vortex_bail!(MismatchedTypes: "linestring storage must be a List of coordinates, was {dtype}"); }; coordinate_dimension(coords) } @@ -136,15 +136,15 @@ pub(crate) fn linestring_array_from_point_pairs( vortex_ensure_eq!( len, ends.len(), - "spatial: line string point columns must have equal lengths" + InvalidArgument: "spatial: line string point columns must have equal lengths" ); let vertex_count = len .checked_mul(2) - .ok_or_else(|| vortex_err!("spatial: two-vertex line string length overflow"))?; + .ok_or_else(|| vortex_err!(Overflow: "spatial: two-vertex line string length overflow"))?; let last_offset = i32::try_from(vertex_count) - .map_err(|_| vortex_err!("spatial: two-vertex line string offset overflow"))?; + .map_err(|_| vortex_err!(Overflow: "spatial: two-vertex line string offset overflow"))?; let row_count = u32::try_from(len) - .map_err(|_| vortex_err!("spatial: two-vertex line string row count overflow"))?; + .map_err(|_| vortex_err!(Overflow: "spatial: two-vertex line string row count overflow"))?; let dimension = linestring_dimension(ext_dtype.storage_dtype())?; let start_dimension = coordinate_dimension(starts.dtype())?; let end_dimension = coordinate_dimension(ends.dtype())?; @@ -202,8 +202,10 @@ pub(crate) fn linestring_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? - .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), + )? + .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -218,7 +220,7 @@ fn linestring_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult< let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; LineStringArray::try_from((arrow.as_ref(), linestring_type)) - .map_err(|e| vortex_err!("failed to construct LineStringArray: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct LineStringArray: {e}")) } /// A validated `LineString` array (`try_from` checks the extension type). @@ -230,7 +232,7 @@ impl TryFrom for LineStringData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - "expected a LineString extension array" + MismatchedTypes: "expected a LineString extension array" ); Ok(LineStringData(ext)) } @@ -311,7 +313,9 @@ impl ArrowExportVTable for LineString { // Round-trip through GeoArrow's line-string array; `into_arrow` is concrete, so wrap in `Arc`. let linestrings = LineStringArray::try_from((arrow_storage.as_ref(), linestring_meta)) - .map_err(|e| vortex_err!("failed to construct LineStringArray: {e}"))?; + .map_err( + |e| vortex_err!(InvalidArgument: "failed to construct LineStringArray: {e}"), + )?; Ok(ArrowExport::Exported(Arc::new(linestrings.into_arrow()))) } @@ -331,36 +335,37 @@ impl ArrowImportVTable for LineString { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = - if let Ok(linestring_meta) = field.try_extension_type::() { - vortex_ensure!( - linestring_meta.coord_type() == CoordType::Separated, - "geoarrow.linestring with interleaved coordinates is not supported; \ - re-encode with separated (struct) coordinates" - ); - ( - linestring_meta.dimension().into(), - spatial_metadata_from_arrow(linestring_meta.metadata()), - ) - } else { - // Literal: peel the `List` layer to the coordinate struct and read its dimension from - // the field names (the canonical check rejects nullable coordinates). - if field.extension_type_name() != Some(LineStringType::NAME) { - return Ok(None); - } - let Ok(DType::List(coords, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) + let (dimension, metadata) = if let Ok(linestring_meta) = + field.try_extension_type::() + { + vortex_ensure!( + linestring_meta.coord_type() == CoordType::Separated, + NotImplemented: "geoarrow.linestring with interleaved coordinates is not supported; \ + re-encode with separated (struct) coordinates" + ); + ( + linestring_meta.dimension().into(), + spatial_metadata_from_arrow(linestring_meta.metadata()), + ) + } else { + // Literal: peel the `List` layer to the coordinate struct and read its dimension from + // the field names (the canonical check rejects nullable coordinates). + if field.extension_type_name() != Some(LineStringType::NAME) { + return Ok(None); + } + let Ok(DType::List(coords, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) + }; let storage_dtype = linestring_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/mod.rs b/vortex-spatial/src/extension/mod.rs index 047109bcec8..8227dd80d3c 100644 --- a/vortex-spatial/src/extension/mod.rs +++ b/vortex-spatial/src/extension/mod.rs @@ -88,7 +88,7 @@ pub(crate) fn flatten_coordinates( ) -> VortexResult { if !is_native_geometry(array.dtype()) { vortex_bail!( - "spatial: operand is not a native geometry extension type, was {}", + MismatchedTypes: "spatial: operand is not a native geometry extension type, was {}", array.dtype() ); } @@ -139,7 +139,7 @@ pub(crate) fn flatten_row_offsets( .execute::>(ctx)?; for row_offset in &mut row_offsets { *row_offset = usize::try_from(offsets[*row_offset]) - .map_err(|_| vortex_err!("spatial: list offset exceeds usize"))?; + .map_err(|_| vortex_err!(Overflow: "spatial: list offset exceeds usize"))?; } level = list.elements().clone(); } @@ -153,7 +153,7 @@ pub(crate) fn geometries( ) -> VortexResult>> { let Some(ext) = array.dtype().as_extension_opt() else { vortex_bail!( - "spatial: operand is not a geometry extension type, was {}", + MismatchedTypes: "spatial: operand is not a geometry extension type, was {}", array.dtype() ); }; @@ -177,7 +177,7 @@ pub(crate) fn geometries( } else if ext.is::() { rect_geometries(&storage, ctx) } else { - vortex_bail!("spatial: unsupported geometry extension {}", array.dtype()) + vortex_bail!(InvalidArgument: "spatial: unsupported geometry extension {}", array.dtype()) } } @@ -188,9 +188,9 @@ pub(crate) fn single_geometry( ctx: &mut ExecutionCtx, ) -> VortexResult> { let array = ConstantArray::new(scalar.clone(), 1).into_array(); - geometries(&array, ctx)? - .pop() - .ok_or_else(|| vortex_err!("spatial: constant operand decoded to no geometry")) + geometries(&array, ctx)?.pop().ok_or_else( + || vortex_err!(AssertionFailed: "spatial: constant operand decoded to no geometry"), + ) } /// Decode a WKB geometry literal (DuckDB's wire form for `GEOMETRY` constants) to its native @@ -205,12 +205,12 @@ pub fn native_geometry_scalar_from_wkb( &binary as &dyn arrow_array::Array, WkbType::new(Arc::clone(&metadata)), )) - .map_err(|e| vortex_err!("failed to read WKB literal: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to read WKB literal: {e}"))?; // Cast the WKB value to `target`, import its native storage as a Vortex array. let to_storage = |target: &GeoArrowType| -> VortexResult { - let native = - cast(&wkb, target).map_err(|e| vortex_err!("failed to cast WKB literal: {e}"))?; + let native = cast(&wkb, target) + .map_err(|e| vortex_err!(Serde: "failed to cast WKB literal: {e}"))?; session .arrow() .from_arrow_array(native.to_array_ref(), false) @@ -315,7 +315,7 @@ pub(crate) fn geoarrow_to_wkb( let wkb_type = GeoArrowType::WkbView(WkbType::new(geoarrow_metadata(&SpatialMetadata::default()))); let wkb = cast(geoarrow_array, &wkb_type) - .map_err(|e| vortex_err!("failed to cast geometry to WKB: {e}"))?; + .map_err(|e| vortex_err!(Serde: "failed to cast geometry to WKB: {e}"))?; session.from_arrow_array(wkb.to_array_ref(), false) } @@ -404,7 +404,7 @@ mod tests { let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&3u32.to_le_bytes()); // geometry type: polygon wkb.extend_from_slice(&1u32.to_le_bytes()); // one ring - let ring_len = u32::try_from(ring.len()).map_err(|e| vortex_err!("{e}"))?; + let ring_len = u32::try_from(ring.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; wkb.extend_from_slice(&ring_len.to_le_bytes()); for (x, y) in ring { wkb.extend_from_slice(&f64::to_le_bytes(x)); @@ -438,7 +438,7 @@ mod tests { let points = [(0.0, 0.0), (1.0, 1.0)]; let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&2u32.to_le_bytes()); // geometry type: linestring - let len = u32::try_from(points.len()).map_err(|e| vortex_err!("{e}"))?; + let len = u32::try_from(points.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; wkb.extend_from_slice(&len.to_le_bytes()); for (x, y) in points { wkb.extend_from_slice(&f64::to_le_bytes(x)); @@ -467,7 +467,7 @@ mod tests { let points = [(0.0, 0.0), (1.0, 1.0)]; let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&4u32.to_le_bytes()); // geometry type: multipoint - let len = u32::try_from(points.len()).map_err(|e| vortex_err!("{e}"))?; + let len = u32::try_from(points.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; wkb.extend_from_slice(&len.to_le_bytes()); for (x, y) in points { // each member is a full WKB point @@ -499,13 +499,13 @@ mod tests { let lines = [[(0.0, 0.0), (1.0, 1.0)], [(2.0, 2.0), (3.0, 3.0)]]; let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&5u32.to_le_bytes()); // geometry type: multilinestring - let num_lines = u32::try_from(lines.len()).map_err(|e| vortex_err!("{e}"))?; + let num_lines = u32::try_from(lines.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; wkb.extend_from_slice(&num_lines.to_le_bytes()); for line in lines { // each member is a full WKB linestring wkb.push(1u8); wkb.extend_from_slice(&2u32.to_le_bytes()); - let len = u32::try_from(line.len()).map_err(|e| vortex_err!("{e}"))?; + let len = u32::try_from(line.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; wkb.extend_from_slice(&len.to_le_bytes()); for (x, y) in line { wkb.extend_from_slice(&f64::to_le_bytes(x)); diff --git a/vortex-spatial/src/extension/multilinestring.rs b/vortex-spatial/src/extension/multilinestring.rs index 93ff0e31c8e..c74fdcb5f4e 100644 --- a/vortex-spatial/src/extension/multilinestring.rs +++ b/vortex-spatial/src/extension/multilinestring.rs @@ -100,10 +100,10 @@ pub(crate) fn multilinestring_storage_dtype(dim: Dimension, nullability: Nullabi /// Validate `dtype` is `List>` and return its [`Dimension`]. pub(crate) fn multilinestring_dimension(dtype: &DType) -> VortexResult { let DType::List(line, _) = dtype else { - vortex_bail!("multilinestring storage must be a List of line strings, was {dtype}"); + vortex_bail!(MismatchedTypes: "multilinestring storage must be a List of line strings, was {dtype}"); }; let DType::List(coords, _) = line.as_ref() else { - vortex_bail!("multilinestring line storage must be a List of coordinates, was {line}"); + vortex_bail!(MismatchedTypes: "multilinestring line storage must be a List of coordinates, was {line}"); }; coordinate_dimension(coords) } @@ -127,8 +127,10 @@ pub(crate) fn multilinestring_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? - .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), + )? + .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -146,7 +148,7 @@ fn multilinestring_array( let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; MultiLineStringArray::try_from((arrow.as_ref(), multilinestring_type)) - .map_err(|e| vortex_err!("failed to construct MultiLineStringArray: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct MultiLineStringArray: {e}")) } /// A validated `MultiLineString` array (`try_from` checks the extension type). @@ -158,7 +160,7 @@ impl TryFrom for MultiLineStringData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - "expected a MultiLineString extension array" + MismatchedTypes: "expected a MultiLineString extension array" ); Ok(MultiLineStringData(ext)) } @@ -237,9 +239,13 @@ impl ArrowExportVTable for MultiLineString { .exporter(options) .execute_arrow(storage, Some(&storage_field), ctx)?; - let multilinestrings = - MultiLineStringArray::try_from((arrow_storage.as_ref(), multilinestring_meta)) - .map_err(|e| vortex_err!("failed to construct MultiLineStringArray: {e}"))?; + let multilinestrings = MultiLineStringArray::try_from(( + arrow_storage.as_ref(), + multilinestring_meta, + )) + .map_err( + |e| vortex_err!(InvalidArgument: "failed to construct MultiLineStringArray: {e}"), + )?; Ok(ArrowExport::Exported(Arc::new( multilinestrings.into_arrow(), @@ -259,39 +265,40 @@ impl ArrowImportVTable for MultiLineString { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = - if let Ok(multilinestring_meta) = field.try_extension_type::() { - vortex_ensure!( - multilinestring_meta.coord_type() == CoordType::Separated, - "geoarrow.multilinestring with interleaved coordinates is not supported; \ - re-encode with separated (struct) coordinates" - ); - ( - multilinestring_meta.dimension().into(), - spatial_metadata_from_arrow(multilinestring_meta.metadata()), - ) - } else { - // Literal: peel the two `List` layers to the coordinate struct and read its dimension - // from the field names (the canonical check rejects nullable coordinates). - if field.extension_type_name() != Some(MultiLineStringType::NAME) { - return Ok(None); - } - let Ok(DType::List(line, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::List(coords, _) = line.as_ref() else { - return Ok(None); - }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) + let (dimension, metadata) = if let Ok(multilinestring_meta) = + field.try_extension_type::() + { + vortex_ensure!( + multilinestring_meta.coord_type() == CoordType::Separated, + NotImplemented: "geoarrow.multilinestring with interleaved coordinates is not supported; \ + re-encode with separated (struct) coordinates" + ); + ( + multilinestring_meta.dimension().into(), + spatial_metadata_from_arrow(multilinestring_meta.metadata()), + ) + } else { + // Literal: peel the two `List` layers to the coordinate struct and read its dimension + // from the field names (the canonical check rejects nullable coordinates). + if field.extension_type_name() != Some(MultiLineStringType::NAME) { + return Ok(None); + } + let Ok(DType::List(line, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::List(coords, _) = line.as_ref() else { + return Ok(None); }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) + }; let storage_dtype = multilinestring_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/multipoint.rs b/vortex-spatial/src/extension/multipoint.rs index c0a2f9d95a5..37aa5b51c2c 100644 --- a/vortex-spatial/src/extension/multipoint.rs +++ b/vortex-spatial/src/extension/multipoint.rs @@ -97,7 +97,7 @@ pub(crate) fn multipoint_storage_dtype(dim: Dimension, nullability: Nullability) /// Validate `dtype` is `List` and return its [`Dimension`]. pub(crate) fn multipoint_dimension(dtype: &DType) -> VortexResult { let DType::List(coords, _) = dtype else { - vortex_bail!("multipoint storage must be a List of coordinates, was {dtype}"); + vortex_bail!(MismatchedTypes: "multipoint storage must be a List of coordinates, was {dtype}"); }; coordinate_dimension(coords) } @@ -118,8 +118,10 @@ pub(crate) fn multipoint_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? - .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), + )? + .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -134,7 +136,7 @@ fn multipoint_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult< let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; MultiPointArray::try_from((arrow.as_ref(), multipoint_type)) - .map_err(|e| vortex_err!("failed to construct MultiPointArray: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct MultiPointArray: {e}")) } /// A validated `MultiPoint` array (`try_from` checks the extension type). @@ -146,7 +148,7 @@ impl TryFrom for MultiPointData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - "expected a MultiPoint extension array" + MismatchedTypes: "expected a MultiPoint extension array" ); Ok(MultiPointData(ext)) } @@ -227,7 +229,9 @@ impl ArrowExportVTable for MultiPoint { // Round-trip through GeoArrow's multipoint array; `into_arrow` is concrete, so wrap in `Arc`. let multipoints = MultiPointArray::try_from((arrow_storage.as_ref(), multipoint_meta)) - .map_err(|e| vortex_err!("failed to construct MultiPointArray: {e}"))?; + .map_err( + |e| vortex_err!(InvalidArgument: "failed to construct MultiPointArray: {e}"), + )?; Ok(ArrowExport::Exported(Arc::new(multipoints.into_arrow()))) } @@ -246,34 +250,35 @@ impl ArrowImportVTable for MultiPoint { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = - if let Ok(multipoint_meta) = field.try_extension_type::() { - vortex_ensure!( - multipoint_meta.coord_type() == CoordType::Separated, - "geoarrow.multipoint with interleaved coordinates is not supported; \ - re-encode with separated (struct) coordinates" - ); - ( - multipoint_meta.dimension().into(), - spatial_metadata_from_arrow(multipoint_meta.metadata()), - ) - } else { - if field.extension_type_name() != Some(MultiPointType::NAME) { - return Ok(None); - } - let Ok(DType::List(coords, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) + let (dimension, metadata) = if let Ok(multipoint_meta) = + field.try_extension_type::() + { + vortex_ensure!( + multipoint_meta.coord_type() == CoordType::Separated, + NotImplemented: "geoarrow.multipoint with interleaved coordinates is not supported; \ + re-encode with separated (struct) coordinates" + ); + ( + multipoint_meta.dimension().into(), + spatial_metadata_from_arrow(multipoint_meta.metadata()), + ) + } else { + if field.extension_type_name() != Some(MultiPointType::NAME) { + return Ok(None); + } + let Ok(DType::List(coords, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) + }; let storage_dtype = multipoint_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/multipolygon.rs b/vortex-spatial/src/extension/multipolygon.rs index f6891e7708e..909c9581410 100644 --- a/vortex-spatial/src/extension/multipolygon.rs +++ b/vortex-spatial/src/extension/multipolygon.rs @@ -98,13 +98,13 @@ pub(crate) fn multipolygon_storage_dtype(dim: Dimension, nullability: Nullabilit /// Validate `dtype` is `List>>` and return its [`Dimension`]. pub(crate) fn multipolygon_dimension(dtype: &DType) -> VortexResult { let DType::List(polygon, _) = dtype else { - vortex_bail!("multipolygon storage must be a List of polygons, was {dtype}"); + vortex_bail!(MismatchedTypes: "multipolygon storage must be a List of polygons, was {dtype}"); }; let DType::List(ring, _) = polygon.as_ref() else { - vortex_bail!("multipolygon polygon storage must be a List of rings, was {polygon}"); + vortex_bail!(MismatchedTypes: "multipolygon polygon storage must be a List of rings, was {polygon}"); }; let DType::List(coords, _) = ring.as_ref() else { - vortex_bail!("multipolygon ring storage must be a List of coordinates, was {ring}"); + vortex_bail!(MismatchedTypes: "multipolygon ring storage must be a List of coordinates, was {ring}"); }; coordinate_dimension(coords) } @@ -125,8 +125,10 @@ pub(crate) fn multipolygon_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? - .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), + )? + .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -144,7 +146,7 @@ fn multipolygon_array( let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; MultiPolygonArray::try_from((arrow.as_ref(), multipolygon_type)) - .map_err(|e| vortex_err!("failed to construct MultiPolygonArray: {e}")) + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct MultiPolygonArray: {e}")) } /// A validated `MultiPolygon` array (`try_from` checks the extension type). @@ -156,7 +158,7 @@ impl TryFrom for MultiPolygonData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - "expected a MultiPolygon extension array" + MismatchedTypes: "expected a MultiPolygon extension array" ); Ok(MultiPolygonData(ext)) } @@ -236,8 +238,9 @@ impl ArrowExportVTable for MultiPolygon { .execute_arrow(storage, Some(&storage_field), ctx)?; let multipolygons = - MultiPolygonArray::try_from((arrow_storage.as_ref(), multipolygon_meta)) - .map_err(|e| vortex_err!("failed to construct MultiPolygonArray: {e}"))?; + MultiPolygonArray::try_from((arrow_storage.as_ref(), multipolygon_meta)).map_err( + |e| vortex_err!(InvalidArgument: "failed to construct MultiPolygonArray: {e}"), + )?; Ok(ArrowExport::Exported(Arc::new(multipolygons.into_arrow()))) } @@ -255,42 +258,43 @@ impl ArrowImportVTable for MultiPolygon { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = - if let Ok(multipolygon_meta) = field.try_extension_type::() { - vortex_ensure!( - multipolygon_meta.coord_type() == CoordType::Separated, - "geoarrow.multipolygon with interleaved coordinates is not supported; \ - re-encode with separated (struct) coordinates" - ); - ( - multipolygon_meta.dimension().into(), - spatial_metadata_from_arrow(multipolygon_meta.metadata()), - ) - } else { - // Literal: peel the three `List` layers to the coordinate struct and read its - // dimension from the field names (the canonical check rejects nullable coordinates). - if field.extension_type_name() != Some(MultiPolygonType::NAME) { - return Ok(None); - } - let Ok(DType::List(polygon, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::List(ring, _) = polygon.as_ref() else { - return Ok(None); - }; - let DType::List(coords, _) = ring.as_ref() else { - return Ok(None); - }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) + let (dimension, metadata) = if let Ok(multipolygon_meta) = + field.try_extension_type::() + { + vortex_ensure!( + multipolygon_meta.coord_type() == CoordType::Separated, + NotImplemented: "geoarrow.multipolygon with interleaved coordinates is not supported; \ + re-encode with separated (struct) coordinates" + ); + ( + multipolygon_meta.dimension().into(), + spatial_metadata_from_arrow(multipolygon_meta.metadata()), + ) + } else { + // Literal: peel the three `List` layers to the coordinate struct and read its + // dimension from the field names (the canonical check rejects nullable coordinates). + if field.extension_type_name() != Some(MultiPolygonType::NAME) { + return Ok(None); + } + let Ok(DType::List(polygon, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::List(ring, _) = polygon.as_ref() else { + return Ok(None); + }; + let DType::List(coords, _) = ring.as_ref() else { + return Ok(None); }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) + }; let storage_dtype = multipolygon_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/point.rs b/vortex-spatial/src/extension/point.rs index 9de00619d8a..5cd7821aefb 100644 --- a/vortex-spatial/src/extension/point.rs +++ b/vortex-spatial/src/extension/point.rs @@ -106,7 +106,7 @@ impl TryFrom for PointData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - "expected a Point extension array" + MismatchedTypes: "expected a Point extension array" ); Ok(PointData(ext)) } @@ -132,7 +132,7 @@ fn point_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult VortexResult> { Ok(geometry - .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? - .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), + )? + .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -217,7 +219,7 @@ impl ArrowExportVTable for Point { // Round-trip through the GeoArrow point array type: this validates that the storage is // the separated-coordinate struct layout expected for a `PointType` extension field. let points = PointArray::try_from((arrow_storage.as_ref(), point_meta)) - .map_err(|e| vortex_err!("failed to construct PointArray: {e}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct PointArray: {e}"))?; Ok(ArrowExport::Exported(points.into_arrow())) } @@ -241,7 +243,7 @@ impl ArrowImportVTable for Point { { vortex_ensure!( point_meta.coord_type() == CoordType::Separated, - "geoarrow.point with interleaved coordinates is not supported; \ + NotImplemented: "geoarrow.point with interleaved coordinates is not supported; \ re-encode with separated (struct) coordinates" ); ( diff --git a/vortex-spatial/src/extension/polygon.rs b/vortex-spatial/src/extension/polygon.rs index 73b39597899..9e278540f23 100644 --- a/vortex-spatial/src/extension/polygon.rs +++ b/vortex-spatial/src/extension/polygon.rs @@ -103,10 +103,10 @@ pub(crate) fn polygon_storage_dtype(dim: Dimension, nullability: Nullability) -> /// Validate `dtype` is `List>` and return its [`Dimension`]. pub(crate) fn polygon_dimension(dtype: &DType) -> VortexResult { let DType::List(ring, _) = dtype else { - vortex_bail!("polygon storage must be a List of rings, was {dtype}"); + vortex_bail!(MismatchedTypes: "polygon storage must be a List of rings, was {dtype}"); }; let DType::List(coords, _) = ring.as_ref() else { - vortex_bail!("polygon ring storage must be a List of coordinates, was {ring}"); + vortex_bail!(MismatchedTypes: "polygon ring storage must be a List of coordinates, was {ring}"); }; coordinate_dimension(coords) } @@ -136,14 +136,13 @@ pub(crate) fn build_polygon_storage( for ring in exterior.into_iter().chain(polygon.interiors()) { xs.extend(ring.0.iter().map(|coord| coord.x)); ys.extend(ring.0.iter().map(|coord| coord.y)); - ring_offsets.push( - u64::try_from(xs.len()) - .map_err(|_| vortex_err!("spatial: polygon coordinate count exceeds u64"))?, - ); + ring_offsets.push(u64::try_from(xs.len()).map_err( + |_| vortex_err!(Overflow: "spatial: polygon coordinate count exceeds u64"), + )?); } polygon_offsets.push( u64::try_from(ring_offsets.len() - 1) - .map_err(|_| vortex_err!("spatial: polygon ring count exceeds u64"))?, + .map_err(|_| vortex_err!(Overflow: "spatial: polygon ring count exceeds u64"))?, ); } @@ -190,8 +189,10 @@ pub(crate) fn polygon_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? - .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), + )? + .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -206,7 +207,7 @@ fn polygon_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult for PolygonData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - "expected a Polygon extension array" + MismatchedTypes: "expected a Polygon extension array" ); Ok(PolygonData(ext)) } @@ -299,7 +300,7 @@ impl ArrowExportVTable for Polygon { // Round-trip through GeoArrow's polygon array; `into_arrow` is concrete, so wrap in `Arc`. let polygons = PolygonArray::try_from((arrow_storage.as_ref(), polygon_meta)) - .map_err(|e| vortex_err!("failed to construct PolygonArray: {e}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct PolygonArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new(polygons.into_arrow()))) } @@ -319,40 +320,41 @@ impl ArrowImportVTable for Polygon { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = - if let Ok(polygon_meta) = field.try_extension_type::() { - vortex_ensure!( - polygon_meta.coord_type() == CoordType::Separated, - "geoarrow.polygon with interleaved coordinates is not supported; \ - re-encode with separated (struct) coordinates" - ); - ( - polygon_meta.dimension().into(), - spatial_metadata_from_arrow(polygon_meta.metadata()), - ) - } else { - // Infer the dimension from the field names, not the canonical storage check: a literal's - // coordinate fields may be nullable, which that check rejects. Peel the two `List` layers - // (polygon → rings → coordinates) to reach the struct. - if field.extension_type_name() != Some(PolygonType::NAME) { - return Ok(None); - } - let Ok(DType::List(ring, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::List(coords, _) = ring.as_ref() else { - return Ok(None); - }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) + let (dimension, metadata) = if let Ok(polygon_meta) = + field.try_extension_type::() + { + vortex_ensure!( + polygon_meta.coord_type() == CoordType::Separated, + NotImplemented: "geoarrow.polygon with interleaved coordinates is not supported; \ + re-encode with separated (struct) coordinates" + ); + ( + polygon_meta.dimension().into(), + spatial_metadata_from_arrow(polygon_meta.metadata()), + ) + } else { + // Infer the dimension from the field names, not the canonical storage check: a literal's + // coordinate fields may be nullable, which that check rejects. Peel the two `List` layers + // (polygon → rings → coordinates) to reach the struct. + if field.extension_type_name() != Some(PolygonType::NAME) { + return Ok(None); + } + let Ok(DType::List(ring, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::List(coords, _) = ring.as_ref() else { + return Ok(None); }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) + }; let storage_dtype = polygon_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/rect.rs b/vortex-spatial/src/extension/rect.rs index 162071e29a6..f89f177762a 100644 --- a/vortex-spatial/src/extension/rect.rs +++ b/vortex-spatial/src/extension/rect.rs @@ -141,7 +141,7 @@ pub(crate) fn box_storage_dtype(dim: Dimension, nullability: Nullability) -> DTy /// [`Dimension`]. pub(crate) fn box_dimension(dtype: &DType) -> VortexResult { let DType::Struct(fields, _) = dtype else { - vortex_bail!("box storage must be a Struct, was {dtype}"); + vortex_bail!(MismatchedTypes: "box storage must be a Struct, was {dtype}"); }; for (name, field) in fields.names().iter().zip(fields.fields()) { vortex_ensure!( @@ -149,11 +149,12 @@ pub(crate) fn box_dimension(dtype: &DType) -> VortexResult { field, DType::Primitive(PType::F64, Nullability::NonNullable) ), - "box field {name} must be non-nullable f64, was {field}" + MismatchedTypes: "box field {name} must be non-nullable f64, was {field}" ); } - box_dimension_from_names(fields.names()) - .ok_or_else(|| vortex_err!("not a valid geoarrow.box dimension: {:?}", fields.names())) + box_dimension_from_names(fields.names()).ok_or_else( + || vortex_err!(InvalidArgument: "not a valid geoarrow.box dimension: {:?}", fields.names()), + ) } /// Build a native [`Rect`] array from canonical min/max ordinate columns. @@ -187,7 +188,7 @@ fn rect_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult VortexResult> { Ok(geometry - .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? - .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? + .ok_or_else( + || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), + )? + .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -268,7 +271,7 @@ impl ArrowExportVTable for Rect { // Round-trip through GeoArrow's rect array; `into_arrow` is concrete, so wrap in `Arc`. let rects = RectArray::try_from((arrow_storage.as_ref(), box_meta)) - .map_err(|e| vortex_err!("failed to construct RectArray: {e}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct RectArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new(rects.into_arrow()))) } diff --git a/vortex-spatial/src/extension/wkb.rs b/vortex-spatial/src/extension/wkb.rs index 8b0b42fb97b..783a5b499e5 100644 --- a/vortex-spatial/src/extension/wkb.rs +++ b/vortex-spatial/src/extension/wkb.rs @@ -72,7 +72,7 @@ impl TryFrom for WellKnownBinaryData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - "array extension dtype {} is not a WKB", + MismatchedTypes: "array extension dtype {} is not a WKB", ext.ext_dtype() ); @@ -100,7 +100,7 @@ impl<'a> Wkb<'a> { /// validation on the structure of the WKB. pub fn try_from_bytes(bytes: &'a [u8]) -> VortexResult { wkb::reader::Wkb::try_new(bytes) - .map_err(|e| vortex_err!("failed parsing WKB: {e}")) + .map_err(|e| vortex_err!(Serde: "failed parsing WKB: {e}")) .map(Wkb) } } @@ -151,7 +151,7 @@ impl ExtVTable for WellKnownBinary { fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( ext_dtype.storage_dtype().is_binary(), - "vortex.st.wkb must have binary storage type, was {}", + MismatchedTypes: "vortex.st.wkb must have binary storage type, was {}", ext_dtype.storage_dtype() ); @@ -233,17 +233,21 @@ impl ArrowExportVTable for WellKnownBinary { let arrow_ref: ArrowArrayRef = match target.data_type() { DataType::Binary => Arc::new( GenericWkbArray::::try_from((arrow_storage.as_ref(), wkb_meta)) - .map_err(|e| vortex_err!("failed to construct WkbArray: {e}"))? + .map_err(|e| vortex_err!(InvalidArgument: "failed to construct WkbArray: {e}"))? .into_arrow(), ), DataType::LargeBinary => Arc::new( GenericWkbArray::::try_from((arrow_storage.as_ref(), wkb_meta)) - .map_err(|e| vortex_err!("failed to construct LargeWkbArray: {e}"))? + .map_err( + |e| vortex_err!(InvalidArgument: "failed to construct LargeWkbArray: {e}"), + )? .into_arrow(), ), DataType::BinaryView => Arc::new( WkbViewArray::try_from((arrow_storage.as_ref(), wkb_meta)) - .map_err(|e| vortex_err!("failed to construct WkbViewArray: {e}"))? + .map_err( + |e| vortex_err!(InvalidArgument: "failed to construct WkbViewArray: {e}"), + )? .into_arrow(), ), _ => unreachable!("target data type was validated above"), diff --git a/vortex-spatial/src/lib.rs b/vortex-spatial/src/lib.rs index 26287e64d39..ecb3e1e55fd 100644 --- a/vortex-spatial/src/lib.rs +++ b/vortex-spatial/src/lib.rs @@ -11,7 +11,6 @@ use vortex_array::scalar_fn::session::ScalarFnSessionExt; use vortex_arrow::ArrowSessionExt; use vortex_edition::EditionSessionExt; use vortex_error::VortexExpect; -use vortex_error::vortex_err; use vortex_expr::stats::session::StatsSessionExt; use vortex_session::VortexSession; @@ -104,15 +103,12 @@ pub fn initialize(session: &VortexSession) { session .editions() .declare_family(&editions::FAMILY) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("spatial edition family is valid"); session .register_edition(&editions::DECLARATION) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("spatial edition declaration is valid"); } session .enable_edition(editions::SPATIAL_2026_08) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("spatial edition is registered"); } diff --git a/vortex-spatial/src/scalar_fn/collect.rs b/vortex-spatial/src/scalar_fn/collect.rs index ce52bd8fda8..fe1ada7b7f4 100644 --- a/vortex-spatial/src/scalar_fn/collect.rs +++ b/vortex-spatial/src/scalar_fn/collect.rs @@ -61,10 +61,10 @@ fn collect_dtype(dtypes: &[DType]) -> VortexResult { vortex_ensure_eq!( dtypes.len(), 1, - "spatial: collect requires exactly one list operand" + InvalidArgument: "spatial: collect requires exactly one list operand" ); let DType::List(element_dtype, nullability) = &dtypes[0] else { - vortex_bail!("spatial: collect operand {} is not a list", dtypes[0]); + vortex_bail!(MismatchedTypes: "spatial: collect operand {} is not a list", dtypes[0]); }; // Execution ignores null list elements, so the result's element storage is non-nullable. let multi_storage = |element: &ExtDTypeRef| { @@ -90,7 +90,7 @@ fn collect_dtype(dtypes: &[DType]) -> VortexResult { )? .erased()), _ => vortex_bail!( - "spatial: collect list element {element_dtype} is not a native Point, LineString, \ + MismatchedTypes: "spatial: collect list element {element_dtype} is not a native Point, LineString, \ or Polygon" ), } @@ -131,12 +131,13 @@ fn compact_row_views( .filter(|end| *end <= element_mask.len()) .ok_or_else(|| { vortex_err!( - "spatial: collect row at element {start} exceeds the {} list elements", + OutOfBounds: "spatial: collect row at element {start} exceeds the {} list elements", element_mask.len() ) })?; - let valid = u64::try_from(count_valid(element_mask, start, end)) - .map_err(|_| vortex_err!("spatial: collect valid element count exceeds u64"))?; + let valid = u64::try_from(count_valid(element_mask, start, end)).map_err( + |_| vortex_err!(Overflow: "spatial: collect valid element count exceeds u64"), + )?; compact_offsets.push(offset); compact_sizes.push(valid); offset += valid; @@ -516,7 +517,7 @@ mod tests { let result = SpatialCollect::try_new(input)?.into_array(); let Columnar::Constant(constant) = result.clone().execute::(&mut ctx)? else { return Err(vortex_err!( - "collect of a constant list should remain constant" + AssertionFailed: "collect of a constant list should remain constant" )); }; assert_eq!(constant.len(), 3); diff --git a/vortex-spatial/src/scalar_fn/contains.rs b/vortex-spatial/src/scalar_fn/contains.rs index 34864cfaa5a..1bce23d103c 100644 --- a/vortex-spatial/src/scalar_fn/contains.rs +++ b/vortex-spatial/src/scalar_fn/contains.rs @@ -120,10 +120,10 @@ mod tests { fn geometry_constant(geometry: &Geometry, len: usize) -> VortexResult { let mut buf = Vec::new(); wkb::writer::write_geometry(&mut buf, geometry, &WriteOptions::default()) - .map_err(|e| vortex_err!("writing WKB failed: {e}"))?; + .map_err(|e| vortex_err!(Serde: "writing WKB failed: {e}"))?; let session = VortexSession::empty(); let scalar = crate::extension::native_geometry_scalar_from_wkb(&buf, &session)? - .ok_or_else(|| vortex_err!("unsupported geometry type"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "unsupported geometry type"))?; Ok(ConstantArray::new(scalar, len).into_array()) } diff --git a/vortex-spatial/src/scalar_fn/convex_hull.rs b/vortex-spatial/src/scalar_fn/convex_hull.rs index 244dae0f5d2..4bdadc9c4ab 100644 --- a/vortex-spatial/src/scalar_fn/convex_hull.rs +++ b/vortex-spatial/src/scalar_fn/convex_hull.rs @@ -34,17 +34,17 @@ fn convex_hull_dtype(dtypes: &[DType]) -> VortexResult { vortex_ensure_eq!( dtypes.len(), 1, - "spatial: convex_hull requires exactly one MultiPoint operand" + InvalidArgument: "spatial: convex_hull requires exactly one MultiPoint operand" ); let Some(input) = dtypes[0].as_extension_opt() else { vortex_bail!( - "spatial: convex_hull operand {} is not a native MultiPoint", + MismatchedTypes: "spatial: convex_hull operand {} is not a native MultiPoint", dtypes[0] ); }; vortex_ensure!( input.is::(), - "spatial: convex_hull operand {} is not a native MultiPoint", + MismatchedTypes: "spatial: convex_hull operand {} is not a native MultiPoint", dtypes[0] ); @@ -216,7 +216,7 @@ mod tests { let result = SpatialConvexHull::try_new(input)?.into_array(); let Columnar::Constant(constant) = result.clone().execute::(&mut ctx)? else { return Err(vortex_err!( - "convex_hull of a constant should remain constant" + AssertionFailed: "convex_hull of a constant should remain constant" )); }; assert_eq!(constant.len(), 3); diff --git a/vortex-spatial/src/scalar_fn/envelope.rs b/vortex-spatial/src/scalar_fn/envelope.rs index 37c99f4b1b9..c3d98257aaa 100644 --- a/vortex-spatial/src/scalar_fn/envelope.rs +++ b/vortex-spatial/src/scalar_fn/envelope.rs @@ -58,11 +58,11 @@ fn validate_envelope_operands(dtypes: &[DType]) -> VortexResult<()> { vortex_ensure_eq!( dtypes.len(), 1, - "spatial: envelope requires exactly one geometry operand" + InvalidArgument: "spatial: envelope requires exactly one geometry operand" ); vortex_ensure!( is_native_geometry(&dtypes[0]), - "spatial: envelope operand {} is not a native geometry type", + MismatchedTypes: "spatial: envelope operand {} is not a native geometry type", dtypes[0] ); Ok(()) @@ -151,7 +151,7 @@ fn envelope_array( let is_rect = array .dtype() .as_extension_opt() - .ok_or_else(|| vortex_err!("spatial: envelope operand is not a geometry extension type"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "spatial: envelope operand is not a geometry extension type"))? .is::(); let storage = array .execute::(ctx)? @@ -562,7 +562,9 @@ mod tests { let points = ConstantArray::new(scalar, 3).into_array(); let result = boxes(points)?.execute::(&mut ctx)?; let Columnar::Constant(boxes) = result else { - return Err(vortex_err!("envelope of a constant should remain constant")); + return Err( + vortex_err!(AssertionFailed: "envelope of a constant should remain constant"), + ); }; assert_eq!(boxes.len(), 3); diff --git a/vortex-spatial/src/scalar_fn/intersects.rs b/vortex-spatial/src/scalar_fn/intersects.rs index 81cc1ca0522..addf97f32b3 100644 --- a/vortex-spatial/src/scalar_fn/intersects.rs +++ b/vortex-spatial/src/scalar_fn/intersects.rs @@ -141,10 +141,10 @@ mod tests { fn geometry_constant(geometry: &Geometry, len: usize) -> VortexResult { let mut buf = Vec::new(); wkb::writer::write_geometry(&mut buf, geometry, &WriteOptions::default()) - .map_err(|e| vortex_err!("writing WKB failed: {e}"))?; + .map_err(|e| vortex_err!(Serde: "writing WKB failed: {e}"))?; let session = VortexSession::empty(); let scalar = crate::extension::native_geometry_scalar_from_wkb(&buf, &session)? - .ok_or_else(|| vortex_err!("unsupported geometry type"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "unsupported geometry type"))?; Ok(ConstantArray::new(scalar, len).into_array()) } diff --git a/vortex-spatial/src/scalar_fn/length.rs b/vortex-spatial/src/scalar_fn/length.rs index 9512008e2c4..b21ffa9c03f 100644 --- a/vortex-spatial/src/scalar_fn/length.rs +++ b/vortex-spatial/src/scalar_fn/length.rs @@ -49,13 +49,13 @@ fn validate_length_operands(dtypes: &[DType]) -> VortexResult<()> { vortex_ensure_eq!( dtypes.len(), 1, - "spatial: length requires exactly one lineal operand" + InvalidArgument: "spatial: length requires exactly one lineal operand" ); vortex_ensure!( dtypes[0].as_extension_opt().is_some_and(|extension| { extension.is::() || extension.is::() }), - "spatial: length operand {} is not a native LineString or MultiLineString", + MismatchedTypes: "spatial: length operand {} is not a native LineString or MultiLineString", dtypes[0] ); Ok(()) @@ -68,7 +68,8 @@ fn list_offsets(list: &ListArray, ctx: &mut ExecutionCtx) -> VortexResult>(ctx)? .iter() .map(|&offset| { - usize::try_from(offset).map_err(|_| vortex_err!("spatial: list offset exceeds usize")) + usize::try_from(offset) + .map_err(|_| vortex_err!(Overflow: "spatial: list offset exceeds usize")) }) .collect() } @@ -323,7 +324,9 @@ mod tests { .into_array() .execute::(&mut ctx)?; let Columnar::Constant(lengths) = result else { - return Err(vortex_err!("length of a constant should remain constant")); + return Err( + vortex_err!(AssertionFailed: "length of a constant should remain constant"), + ); }; assert_eq!(lengths.len(), 3); assert_eq!(f64::try_from(lengths.scalar())?, 9.0); @@ -341,7 +344,7 @@ mod tests { .execute::(&mut ctx)?; let Columnar::Constant(lengths) = result else { return Err(vortex_err!( - "length of a null constant should remain constant" + AssertionFailed: "length of a null constant should remain constant" )); }; assert_eq!(lengths.len(), 2); diff --git a/vortex-spatial/src/scalar_fn/make_line.rs b/vortex-spatial/src/scalar_fn/make_line.rs index 406b05e6dc1..8730be2a3f1 100644 --- a/vortex-spatial/src/scalar_fn/make_line.rs +++ b/vortex-spatial/src/scalar_fn/make_line.rs @@ -44,14 +44,14 @@ fn validate_make_line_operands(dtypes: &[DType]) -> VortexResult<()> { vortex_ensure_eq!( dtypes.len(), 2, - "spatial: make_line requires exactly two point operands" + InvalidArgument: "spatial: make_line requires exactly two point operands" ); for dtype in dtypes { vortex_ensure!( dtype .as_extension_opt() .is_some_and(|extension| extension.is::()), - "spatial: make_line operand {dtype} is not a native point" + MismatchedTypes: "spatial: make_line operand {dtype} is not a native point" ); } Ok(()) @@ -67,7 +67,7 @@ fn make_line_metadata( vortex_ensure_eq!( left_crs, right_crs, - "spatial: make_line operands have different coordinate reference systems" + InvalidArgument: "spatial: make_line operands have different coordinate reference systems" ); Ok(left.clone()) } @@ -107,7 +107,9 @@ fn point_coordinates( fields .field(name) .map(|value| ConstantArray::new(value, len).into_array()) - .ok_or_else(|| vortex_err!("spatial: point coordinate missing {name}")) + .ok_or_else( + || vortex_err!(NotFound: "spatial: point coordinate missing {name}"), + ) }) .collect::>>()?; StructArray::try_new(names, arrays, len, Validity::NonNullable) @@ -340,7 +342,7 @@ mod tests { .execute::(&mut ctx)?; let Columnar::Constant(lines) = result else { return Err(vortex_err!( - "make_line of two constants should remain constant" + AssertionFailed: "make_line of two constants should remain constant" )); }; assert_eq!(lines.len(), 3); @@ -400,7 +402,7 @@ mod tests { .execute::(&mut ctx)?; let Columnar::Constant(lines) = result else { return Err(vortex_err!( - "make_line with a null constant should remain constant" + AssertionFailed: "make_line with a null constant should remain constant" )); }; assert_eq!(lines.len(), 2); diff --git a/vortex-spatial/src/scalar_fn/row.rs b/vortex-spatial/src/scalar_fn/row.rs index 4d3c1fe5977..b305fe6268a 100644 --- a/vortex-spatial/src/scalar_fn/row.rs +++ b/vortex-spatial/src/scalar_fn/row.rs @@ -84,7 +84,7 @@ unsafe impl InputElement for GeometryRow { fn validate(dtype: &DType) -> VortexResult<()> { vortex_ensure!( is_native_geometry(dtype), - "spatial: operand {dtype} is not a native geometry type" + MismatchedTypes: "spatial: operand {dtype} is not a native geometry type" ); Ok(()) } @@ -98,7 +98,7 @@ unsafe impl InputElement for GeometryRow { vortex_ensure_eq!( geometries.len(), 1, - "a geometry batch constant must decode to one value", + AssertionFailed: "a geometry batch constant must decode to one value", ); Ok(geometries diff --git a/vortex-spatial/src/test_harness.rs b/vortex-spatial/src/test_harness.rs index d6f30d51162..9c28c9bb317 100644 --- a/vortex-spatial/src/test_harness.rs +++ b/vortex-spatial/src/test_harness.rs @@ -64,7 +64,7 @@ fn xy_struct(xs: Vec, ys: Vec) -> VortexResult { /// A list offset as `i32`. fn offset(n: usize) -> VortexResult { - i32::try_from(n).map_err(|_| vortex_err!("geometry offset overflow")) + i32::try_from(n).map_err(|_| vortex_err!(Overflow: "geometry offset overflow")) } /// Wrap `elements` — built from `rows` flattened one level — in a non-nullable `List` with one diff --git a/vortex-spatial/src/tests/point.rs b/vortex-spatial/src/tests/point.rs index aec2e91bcbf..e06a53b2e69 100644 --- a/vortex-spatial/src/tests/point.rs +++ b/vortex-spatial/src/tests/point.rs @@ -92,7 +92,7 @@ fn exports_to_struct() -> VortexResult<()> { let ordinates = |name: &str| -> VortexResult> { Ok(points .column_by_name(name) - .ok_or_else(|| vortex_err!("missing {name} column"))? + .ok_or_else(|| vortex_err!(NotFound: "missing {name} column"))? .as_primitive::() .values() .to_vec()) @@ -176,7 +176,7 @@ fn roundtrips_through_arrow() -> VortexResult<()> { let ext = reimported .dtype() .as_extension_opt() - .ok_or_else(|| vortex_err!("expected Extension dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Extension dtype"))?; assert_eq!(ext.metadata::().crs.as_deref(), Some("EPSG:4326")); assert_eq!( diff --git a/vortex-spatial/src/tests/rect.rs b/vortex-spatial/src/tests/rect.rs index 9639e5ba400..6e616272795 100644 --- a/vortex-spatial/src/tests/rect.rs +++ b/vortex-spatial/src/tests/rect.rs @@ -86,7 +86,7 @@ fn roundtrips_through_arrow() -> VortexResult<()> { let ext = reimported .dtype() .as_extension_opt() - .ok_or_else(|| vortex_err!("expected Extension dtype"))?; + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Extension dtype"))?; assert!(ext.is::()); assert_eq!(ext.metadata::().crs.as_deref(), Some("EPSG:4326")); @@ -94,13 +94,13 @@ fn roundtrips_through_arrow() -> VortexResult<()> { let scalar = reimported.execute_scalar(row, &mut ctx)?; let storage = scalar .as_extension_opt() - .ok_or_else(|| vortex_err!("expected extension scalar"))? + .ok_or_else(|| vortex_err!(MismatchedTypes: "expected extension scalar"))? .to_storage_scalar(); f64::try_from( &storage .as_struct() .field(name) - .ok_or_else(|| vortex_err!("missing {name}"))?, + .ok_or_else(|| vortex_err!(NotFound: "missing {name}"))?, ) }; assert_eq!(corner(0, "xmin")?, 0.0); diff --git a/vortex-spatial/src/tests/wkb.rs b/vortex-spatial/src/tests/wkb.rs index 05b14ad1942..558d0956ac3 100644 --- a/vortex-spatial/src/tests/wkb.rs +++ b/vortex-spatial/src/tests/wkb.rs @@ -62,7 +62,7 @@ fn wkb_extension_array() -> VortexResult<(Vec, vortex_array::ArrayRef)> { let mut buf = Vec::new(); // We should always prefer to write little-endian, which is the default option. wkb::writer::write_geometry(&mut buf, &test_polygon(), &WriteOptions::default()) - .map_err(|e| vortex_err!("writing WKB failed: {e}"))?; + .map_err(|e| vortex_err!(Serde: "writing WKB failed: {e}"))?; let mut builder = VarBinBuilder::::with_capacity_in( DType::Binary(Nullability::NonNullable), diff --git a/vortex-tensor/src/lib.rs b/vortex-tensor/src/lib.rs index a6f9ea2a623..b2939c21d82 100644 --- a/vortex-tensor/src/lib.rs +++ b/vortex-tensor/src/lib.rs @@ -21,7 +21,6 @@ use vortex_array::session::ArraySessionExt; use vortex_arrow::ArrowSessionExt; use vortex_edition::EditionSessionExt; use vortex_error::VortexExpect; -use vortex_error::vortex_err; use vortex_session::VortexSession; use crate::scalar_fns::cosine_similarity::CosineSimilarity; @@ -84,16 +83,13 @@ pub fn initialize(session: &VortexSession) { session .editions() .declare_family(&editions::FAMILY) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("tensor edition family is valid"); session .register_edition(&editions::DECLARATION) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("tensor edition declaration is valid"); } session .enable_edition(editions::TENSOR_2026_04) - .map_err(|error| vortex_err!("{error}")) .vortex_expect("tensor edition is registered"); } diff --git a/vortex-tensor/src/scalar_fns/l2_norm.rs b/vortex-tensor/src/scalar_fns/l2_norm.rs index 0d4ffc03447..3cdb7ee998e 100644 --- a/vortex-tensor/src/scalar_fns/l2_norm.rs +++ b/vortex-tensor/src/scalar_fns/l2_norm.rs @@ -128,11 +128,11 @@ impl ScalarFnArrayVTable for L2Norm { session: &VortexSession, ) -> VortexResult> { let metadata = L2NormMetadata::decode(metadata) - .map_err(|error| vortex_err!("failed to decode L2Norm metadata: {error}"))?; + .map_err(|error| vortex_err!(Serde: "failed to decode L2Norm metadata: {error}"))?; let input_pb = metadata .input_dtype .as_ref() - .ok_or_else(|| vortex_err!("L2Norm metadata must contain input_dtype"))?; + .ok_or_else(|| vortex_err!(Serde: "L2Norm metadata must contain input_dtype"))?; let input_dtype = DType::from_proto(input_pb, session)?; let child = children.get(0, &input_dtype, len)?; Ok(ScalarFnArrayParts { diff --git a/vortex-tensor/src/scalar_fns/l2_normalize.rs b/vortex-tensor/src/scalar_fns/l2_normalize.rs index ff3d068529d..fbe967b0ab6 100644 --- a/vortex-tensor/src/scalar_fns/l2_normalize.rs +++ b/vortex-tensor/src/scalar_fns/l2_normalize.rs @@ -213,12 +213,13 @@ impl ScalarFnArrayVTable for L2Normalize { children: &dyn ArrayChildren, session: &VortexSession, ) -> VortexResult> { - let metadata = L2NormalizeMetadata::decode(metadata) - .map_err(|error| vortex_err!("failed to decode L2Normalize metadata: {error}"))?; + let metadata = L2NormalizeMetadata::decode(metadata).map_err( + |error| vortex_err!(Serde: "failed to decode L2Normalize metadata: {error}"), + )?; let input_dtype = metadata .input_dtype .as_ref() - .ok_or_else(|| vortex_err!("L2Normalize metadata must contain input_dtype"))?; + .ok_or_else(|| vortex_err!(Serde: "L2Normalize metadata must contain input_dtype"))?; let input_dtype = DType::from_proto(input_dtype, session)?; l2_normalize_dtype(&input_dtype)?; let child = children.get(0, &input_dtype, len)?; diff --git a/vortex-tensor/src/scalar_fns/row.rs b/vortex-tensor/src/scalar_fns/row.rs index cc079c21445..c6d6df75259 100644 --- a/vortex-tensor/src/scalar_fns/row.rs +++ b/vortex-tensor/src/scalar_fns/row.rs @@ -37,14 +37,14 @@ use crate::utils::validate_tensor_float_input; /// Returns the common float element type of tensor row-function arguments. pub fn tensor_element_ptype(args: &[DType]) -> VortexResult { - let (first, rest) = args - .split_first() - .ok_or_else(|| vortex_err!("tensor row function requires at least one input"))?; + let (first, rest) = args.split_first().ok_or_else( + || vortex_err!(InvalidArgument: "tensor row function requires at least one input"), + )?; for argument in rest { vortex_ensure!( first.eq_ignore_nullability(argument), - "tensor row-function inputs must have the same dtype, got {first} and {argument}", + MismatchedTypes: "tensor row-function inputs must have the same dtype, got {first} and {argument}", ); } @@ -85,16 +85,16 @@ fn decode_tensor_storage( vortex_ensure_eq!( stride, row_width, - "per-row tensor stride must equal its width", + InvalidArgument: "per-row tensor stride must equal its width", ); let Some(expected_elements) = row_count.checked_mul(stride) else { vortex_bail!( - "tensor row storage length must fit usize, got {row_count} rows of width {stride}", + Overflow: "tensor row storage length must fit usize, got {row_count} rows of width {stride}", ); }; expected_elements }; - vortex_ensure_eq!(elements.len(), expected_elements); + vortex_ensure_eq!(elements.len(), expected_elements, InvalidArgument); Ok(TensorRows { elements, @@ -121,7 +121,7 @@ unsafe impl InputElement for TensorRow { vortex_ensure_eq!( tensor_match.element_ptype(), expected_element_ptype, - "tensor row input {dtype} has the wrong element type", + MismatchedTypes: "tensor row input {dtype} has the wrong element type", ); Ok(()) @@ -149,14 +149,14 @@ unsafe impl InputElement for TensorRow { extension.storage_array().clone() } else { vortex_bail!( - "a tensor batch constant must use the Constant encoding or constant extension \ + MismatchedTypes: "a tensor batch constant must use the Constant encoding or constant extension \ storage, got {}", array.encoding_id() ); }; let decoded = decode_tensor_storage::(&storage, 1, row_width, ctx)?; - vortex_ensure_eq!(decoded.elements.len(), row_width); + vortex_ensure_eq!(decoded.elements.len(), row_width, InvalidArgument); Ok(decoded.elements) } diff --git a/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs b/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs index e4e460c21a2..9e35b984ad4 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs @@ -48,7 +48,7 @@ impl Matcher for AnyFixedShapeTensor { let DType::FixedSizeList(element_dtype, list_size, _) = ext_dtype.storage_dtype() else { vortex_panic!( - "`FixedShapeTensor` type somehow did not have a `FixedSizeList` storage type" + AssertionFailed: "`FixedShapeTensor` type somehow did not have a `FixedSizeList` storage type" ) }; diff --git a/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs b/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs index ed174c93d95..c935a507855 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs @@ -54,7 +54,7 @@ impl FixedShapeTensorMetadata { /// The number of names must match the number of logical dimensions. pub fn with_dim_names(mut self, names: Vec) -> VortexResult { if !names.is_empty() { - vortex_ensure_eq!(names.len(), self.logical_shape.len()); + vortex_ensure_eq!(names.len(), self.logical_shape.len(), InvalidArgument); self.dim_names = Some(names); } @@ -68,17 +68,17 @@ impl FixedShapeTensorMetadata { /// number of logical dimensions. pub fn with_permutation(mut self, permutation: Vec) -> VortexResult { if !permutation.is_empty() { - vortex_ensure_eq!(permutation.len(), self.logical_shape.len()); + vortex_ensure_eq!(permutation.len(), self.logical_shape.len(), InvalidArgument); // Verify this is actually a permutation of [0..N). let mut seen = vec![false; permutation.len()]; for &p in &permutation { vortex_ensure!( p < permutation.len(), - "permutation index {p} is out of range for {} dimensions", + OutOfBounds: "permutation index {p} is out of range for {} dimensions", permutation.len() ); - vortex_ensure!(!seen[p], "permutation contains duplicate index {p}"); + vortex_ensure!(!seen[p], InvalidArgument: "permutation contains duplicate index {p}"); seen[p] = true; } diff --git a/vortex-tensor/src/types/fixed_shape_tensor/proto.rs b/vortex-tensor/src/types/fixed_shape_tensor/proto.rs index 2bd608d717d..52f6a37a41a 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/proto.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/proto.rs @@ -67,7 +67,8 @@ pub(crate) fn serialize(metadata: &FixedShapeTensorMetadata) -> Vec { /// For 0-dimensional tensors, all three repeated fields are empty, which correctly produces a /// metadata with an empty shape and no names or permutation. pub(crate) fn deserialize(bytes: &[u8]) -> VortexResult { - let proto = FixedShapeTensorMetadataProto::decode(bytes).map_err(|e| vortex_err!("{e}"))?; + let proto = + FixedShapeTensorMetadataProto::decode(bytes).map_err(|e| vortex_err!(Serde: "{e}"))?; let logical_shape = proto .logical_shape diff --git a/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs b/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs index b98e3dd0acf..590808a8753 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs @@ -39,26 +39,26 @@ impl ExtVTable for FixedShapeTensor { let storage_dtype = ext_dtype.storage_dtype(); let DType::FixedSizeList(element_dtype, list_size, _nullability) = storage_dtype else { vortex_bail!( - "FixedShapeTensor storage dtype must be a FixedSizeList, got {storage_dtype}" + InvalidArgument: "FixedShapeTensor storage dtype must be a FixedSizeList, got {storage_dtype}" ); }; // Note that these constraints may be relaxed in the future. vortex_ensure!( element_dtype.is_primitive(), - "FixedShapeTensor element dtype must be primitive, got {element_dtype} \ + MismatchedTypes: "FixedShapeTensor element dtype must be primitive, got {element_dtype} \ (may change in the future)" ); vortex_ensure!( !element_dtype.is_nullable(), - "FixedShapeTensor element dtype must be non-nullable (may change in the future)" + InvalidArgument: "FixedShapeTensor element dtype must be non-nullable (may change in the future)" ); let element_count: usize = ext_dtype.metadata().logical_shape().iter().product(); vortex_ensure_eq!( element_count, *list_size as usize, - "FixedShapeTensor logical shape product must match FixedSizeList size" + InvalidArgument: "FixedShapeTensor logical shape product must match FixedSizeList size" ); Ok(()) diff --git a/vortex-tensor/src/types/vector/matcher.rs b/vortex-tensor/src/types/vector/matcher.rs index 9f5b0037029..66fed38ceb8 100644 --- a/vortex-tensor/src/types/vector/matcher.rs +++ b/vortex-tensor/src/types/vector/matcher.rs @@ -44,7 +44,7 @@ impl Matcher for AnyVector { } let DType::FixedSizeList(element_dtype, list_size, _) = ext_dtype.storage_dtype() else { - vortex_panic!("`Vector` type somehow did not have a `FixedSizeList` storage type") + vortex_panic!(AssertionFailed: "`Vector` type somehow did not have a `FixedSizeList` storage type") }; let dimensions = *list_size; diff --git a/vortex-tensor/src/types/vector/mod.rs b/vortex-tensor/src/types/vector/mod.rs index af424b9cc41..441e23c1b73 100644 --- a/vortex-tensor/src/types/vector/mod.rs +++ b/vortex-tensor/src/types/vector/mod.rs @@ -23,16 +23,16 @@ use vortex_error::vortex_ensure; /// elements. The outer nullability is not constrained. pub(crate) fn validate_vector_storage_dtype(storage: &DType) -> VortexResult<()> { let DType::FixedSizeList(element_dtype, _list_size, _nullability) = storage else { - vortex_bail!("Vector storage dtype must be a FixedSizeList, got {storage}"); + vortex_bail!(InvalidArgument: "Vector storage dtype must be a FixedSizeList, got {storage}"); }; vortex_ensure!( element_dtype.is_float(), - "Vector element dtype must be a float, got {element_dtype}" + MismatchedTypes: "Vector element dtype must be a float, got {element_dtype}" ); vortex_ensure!( !element_dtype.is_nullable(), - "Vector element dtype must be non-nullable" + InvalidArgument: "Vector element dtype must be non-nullable" ); Ok(()) diff --git a/vortex-tensor/src/utils.rs b/vortex-tensor/src/utils.rs index 69ef4378648..cf3eefb0cae 100644 --- a/vortex-tensor/src/utils.rs +++ b/vortex-tensor/src/utils.rs @@ -29,18 +29,18 @@ use crate::matcher::TensorMatch; /// Validates that `input_dtype` is a float-valued tensor-like extension dtype. pub fn validate_tensor_float_input(input_dtype: &DType) -> VortexResult> { - let ext = input_dtype - .as_extension_opt() - .ok_or_else(|| vortex_err!("expected an extension type, got {input_dtype}"))?; + let ext = input_dtype.as_extension_opt().ok_or_else( + || vortex_err!(MismatchedTypes: "expected an extension type, got {input_dtype}"), + )?; - let tensor_match = ext - .metadata_opt::() - .ok_or_else(|| vortex_err!("expected an `AnyTensor`, got {input_dtype}"))?; + let tensor_match = ext.metadata_opt::().ok_or_else( + || vortex_err!(MismatchedTypes: "expected an `AnyTensor`, got {input_dtype}"), + )?; let ptype = tensor_match.element_ptype(); vortex_ensure!( ptype.is_float(), - "expected a float element dtype, got {ptype}", + MismatchedTypes: "expected a float element dtype, got {ptype}", ); Ok(tensor_match) @@ -54,7 +54,7 @@ pub fn validate_binary_tensor_float_inputs<'a>( ) -> VortexResult> { vortex_ensure!( lhs.eq_ignore_nullability(rhs), - "binary tensor expression expects inputs to have the same dtype, got {lhs} and {rhs}" + MismatchedTypes: "binary tensor expression expects inputs to have the same dtype, got {lhs} and {rhs}" ); validate_tensor_float_input(lhs) } @@ -123,7 +123,7 @@ pub fn extract_flat_elements( let elems: PrimitiveArray = fsl.elements().clone().execute(ctx)?; vortex_ensure!( !elems.nullability().is_nullable(), - "tensor storage elements must be non-nullable, got {}", + InvalidArgument: "tensor storage elements must be non-nullable, got {}", elems.dtype(), ); Ok(FlatElements { @@ -172,15 +172,15 @@ impl BinaryTensorOpMetadata { session: &VortexSession, ) -> VortexResult> { let metadata = Self::decode(metadata) - .map_err(|e| vortex_err!("Failed to decode BinaryTensorOpMetadata: {e}"))?; + .map_err(|e| vortex_err!(Serde: "Failed to decode BinaryTensorOpMetadata: {e}"))?; let lhs_pb = metadata .lhs_dtype .as_ref() - .ok_or_else(|| vortex_err!("metadata missing lhs_dtype"))?; + .ok_or_else(|| vortex_err!(Serde: "metadata missing lhs_dtype"))?; let rhs_pb = metadata .rhs_dtype .as_ref() - .ok_or_else(|| vortex_err!("metadata missing rhs_dtype"))?; + .ok_or_else(|| vortex_err!(Serde: "metadata missing rhs_dtype"))?; let lhs_dtype = DType::from_proto(lhs_pb, session)?; let rhs_dtype = DType::from_proto(rhs_pb, session)?; diff --git a/vortex-test/compat-gen/src/adapter.rs b/vortex-test/compat-gen/src/adapter.rs index f1c518a1186..aed22317db6 100644 --- a/vortex-test/compat-gen/src/adapter.rs +++ b/vortex-test/compat-gen/src/adapter.rs @@ -31,7 +31,7 @@ use vortex_error::vortex_err; use vortex_session::VortexSession; fn runtime() -> VortexResult { - Runtime::new().map_err(|e| vortex_err!("failed to create tokio runtime: {e}")) + Runtime::new().map_err(|e| vortex_err!(Io: "failed to create tokio runtime: {e}")) } /// Compute all statistics on every node in the array tree. @@ -76,7 +76,7 @@ pub fn write_compressed( let session = VortexSession::default().with_tokio(); let mut file = tokio::fs::File::create(path) .await - .map_err(|e| vortex_err!("failed to create {}: {e}", path.display()))?; + .map_err(|e| vortex_err!(Io: "failed to create {}: {e}", path.display()))?; let _summary = session .write_options() .with_strategy(strategy) @@ -155,8 +155,8 @@ pub fn read_layout_tree(bytes: ByteBuffer) -> VortexResult<()> { &session, &Default::default(), )?; - let len = - usize::try_from(row_count).map_err(|e| vortex_err!("row count overflow: {e}"))?; + let len = usize::try_from(row_count) + .map_err(|e| vortex_err!(Overflow: "row count overflow: {e}"))?; let expr = root().bind(reader.dtype())?; reader .projection_evaluation(&(0..row_count), &expr, MaskFuture::new_true(len))? diff --git a/vortex-test/compat-gen/src/check.rs b/vortex-test/compat-gen/src/check.rs index a2834fa733b..7295c5cd93a 100644 --- a/vortex-test/compat-gen/src/check.rs +++ b/vortex-test/compat-gen/src/check.rs @@ -63,7 +63,8 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { } // Generate fresh fixtures into a temp directory. - let tmp_dir = tempfile::tempdir().map_err(|e| vortex_err!("failed to create temp dir: {e}"))?; + let tmp_dir = + tempfile::tempdir().map_err(|e| vortex_err!(Io: "failed to create temp dir: {e}"))?; eprintln!("generating fresh fixtures for comparison..."); for fixture in &fixtures { @@ -72,7 +73,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { // Collect .vortex files in the check directory. let dir_files: Vec = std::fs::read_dir(dir) - .map_err(|e| vortex_err!("failed to read dir {}: {e}", dir.display()))? + .map_err(|e| vortex_err!(Io: "failed to read dir {}: {e}", dir.display()))? .filter_map(|entry| { let entry = entry.ok()?; let name = entry.file_name().to_string_lossy().to_string(); @@ -82,7 +83,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { // Collect all fixture names (each fixture may produce multiple files). let fresh_files: Vec = std::fs::read_dir(tmp_dir.path()) - .map_err(|e| vortex_err!("failed to read tmp dir: {e}"))? + .map_err(|e| vortex_err!(Io: "failed to read tmp dir: {e}"))? .filter_map(|entry| { let entry = entry.ok()?; let name = entry.file_name().to_string_lossy().to_string(); @@ -199,7 +200,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { // Print JSON result to stdout. let json = serde_json::to_string_pretty(&result) - .map_err(|e| vortex_err!("failed to serialize result: {e}"))?; + .map_err(|e| vortex_err!(Serde: "failed to serialize result: {e}"))?; println!("{json}"); // Summary to stderr. @@ -214,7 +215,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { for f in &result.failed { eprintln!(" FAIL {}: {}", f.name, f.error); } - vortex_bail!("{} fixture(s) failed", result.failed.len()); + vortex_bail!(AssertionFailed: "{} fixture(s) failed", result.failed.len()); } Ok(()) diff --git a/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs b/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs index ba24c20dc82..13f94358acd 100644 --- a/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs +++ b/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs @@ -39,7 +39,7 @@ fn cached_clickbench_parquet() -> VortexResult { return Ok(dest); } - fs::create_dir_all(&data_dir).map_err(|e| vortex_err!("failed to create data dir: {e}"))?; + fs::create_dir_all(&data_dir).map_err(|e| vortex_err!(Io: "failed to create data dir: {e}"))?; // Download full partition 0 to a temp file. let source_bytes = download_with_retries(CLICKBENCH_URL)?; @@ -54,18 +54,18 @@ fn download_with_retries(url: &str) -> VortexResult { let client = reqwest::blocking::Client::builder() .timeout(std::time::Duration::from_secs(300)) .build() - .map_err(|e| vortex_err!("failed to build HTTP client: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to build HTTP client: {e}"))?; for attempt in 1..=MAX_RETRIES { match client.get(url).send() { Ok(response) if response.status().is_success() => { return response .bytes() - .map_err(|e| vortex_err!("failed to read response body: {e}")); + .map_err(|e| vortex_err!(Io: "failed to read response body: {e}")); } Ok(response) if response.status().is_client_error() => { return Err(vortex_err!( - "HTTP {}: failed to download {url}", + Io: "HTTP {}: failed to download {url}", response.status() )); } @@ -87,7 +87,7 @@ fn download_with_retries(url: &str) -> VortexResult { } Err(vortex_err!( - "failed to download {url} after {MAX_RETRIES} attempts" + Io: "failed to download {url} after {MAX_RETRIES} attempts" )) } @@ -95,7 +95,7 @@ fn download_with_retries(url: &str) -> VortexResult { fn sample_and_write(source_bytes: &[u8], dest: &std::path::Path) -> VortexResult<()> { let source_bytes = Bytes::copy_from_slice(source_bytes); let builder = ParquetRecordBatchReaderBuilder::try_new(source_bytes.clone()) - .map_err(|e| vortex_err!("failed to open source parquet: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to open source parquet: {e}"))?; let metadata = Arc::clone(builder.metadata()); let total_rows: usize = metadata @@ -135,35 +135,35 @@ fn sample_and_write(source_bytes: &[u8], dest: &std::path::Path) -> VortexResult let mut sampled_batches: Vec = Vec::new(); for &(rg_idx, local_offset, count) in &ranges { let reader = ParquetRecordBatchReaderBuilder::try_new(source_bytes.clone()) - .map_err(|e| vortex_err!("failed to open parquet for sampling: {e}"))? + .map_err(|e| vortex_err!(Io: "failed to open parquet for sampling: {e}"))? .with_row_groups(vec![rg_idx]) .with_offset(local_offset) .with_limit(count) .with_batch_size(count) .build() - .map_err(|e| vortex_err!("failed to build parquet reader: {e}"))?; + .map_err(|e| vortex_err!(Serde: "failed to build parquet reader: {e}"))?; for batch in reader { sampled_batches - .push(batch.map_err(|e| vortex_err!("failed to read parquet batch: {e}"))?); + .push(batch.map_err(|e| vortex_err!(Io: "failed to read parquet batch: {e}"))?); } } // Write sampled batches to a parquet file. let schema = sampled_batches[0].schema(); let combined = arrow_select::concat::concat_batches(&schema, &sampled_batches) - .map_err(|e| vortex_err!("failed to concat batches: {e}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "failed to concat batches: {e}"))?; - let file = - fs::File::create(dest).map_err(|e| vortex_err!("failed to create output parquet: {e}"))?; + let file = fs::File::create(dest) + .map_err(|e| vortex_err!(Io: "failed to create output parquet: {e}"))?; let mut writer = parquet::arrow::ArrowWriter::try_new(file, schema, None) - .map_err(|e| vortex_err!("failed to create parquet writer: {e}"))?; + .map_err(|e| vortex_err!(Serde: "failed to create parquet writer: {e}"))?; writer .write(&combined) - .map_err(|e| vortex_err!("failed to write parquet: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to write parquet: {e}"))?; writer .close() - .map_err(|e| vortex_err!("failed to close parquet writer: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to close parquet writer: {e}"))?; Ok(()) } @@ -181,19 +181,20 @@ impl DatasetFixture for ClickBenchHits5kFixture { fn build(&self, arrow: &ArrowSession) -> VortexResult { let path = cached_clickbench_parquet()?; - let file_bytes = fs::read(&path) - .map_err(|e| vortex_err!("failed to read cached parquet at {}: {e}", path.display()))?; + let file_bytes = fs::read(&path).map_err( + |e| vortex_err!(Io: "failed to read cached parquet at {}: {e}", path.display()), + )?; let bytes = Bytes::from(file_bytes); let reader = ParquetRecordBatchReaderBuilder::try_new(bytes) - .map_err(|e| vortex_err!("failed to open parquet: {e}"))? + .map_err(|e| vortex_err!(Io: "failed to open parquet: {e}"))? .with_batch_size(1000) .build() - .map_err(|e| vortex_err!("failed to build parquet reader: {e}"))?; + .map_err(|e| vortex_err!(Serde: "failed to build parquet reader: {e}"))?; let batches: Vec = reader .collect::, _>>() - .map_err(|e| vortex_err!("failed to read parquet batches: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to read parquet batches: {e}"))?; Ok(ChunkedArray::from_iter( batches diff --git a/vortex-test/compat-gen/src/fixtures/mod.rs b/vortex-test/compat-gen/src/fixtures/mod.rs index 3749a1f1483..3f1e0d34437 100644 --- a/vortex-test/compat-gen/src/fixtures/mod.rs +++ b/vortex-test/compat-gen/src/fixtures/mod.rs @@ -184,7 +184,7 @@ pub fn check_expected_encodings( if !missing.is_empty() { vortex_bail!( - "fixture '{}' is missing expected encodings: {:?} (found: {:?})", + InvalidArgument: "fixture '{}' is missing expected encodings: {:?} (found: {:?})", fixture.name(), missing, found, diff --git a/vortex-test/compat-gen/src/generate.rs b/vortex-test/compat-gen/src/generate.rs index a888a41bb5c..e4a066afc9a 100644 --- a/vortex-test/compat-gen/src/generate.rs +++ b/vortex-test/compat-gen/src/generate.rs @@ -47,7 +47,7 @@ pub fn write_fixtures( } std::fs::create_dir_all(output_dir) - .map_err(|e| vortex_err!("failed to create output dir: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to create output dir: {e}"))?; eprintln!("generating {} fixtures...", fixtures.len()); @@ -57,7 +57,7 @@ pub fn write_fixtures( for entry in entries { let path = output_dir.join(&entry.name); let file_bytes = std::fs::read(&path) - .map_err(|e| vortex_err!("failed to read back {}: {e}", path.display()))?; + .map_err(|e| vortex_err!(Io: "failed to read back {}: {e}", path.display()))?; let sha256 = format!("{:x}", HexDisplay(&Sha256::digest(&file_bytes))); eprintln!(" wrote {}", entry.name); infos.push(FixtureInfo { @@ -75,9 +75,9 @@ pub fn write_fixtures( pub fn write_manifest(output_dir: &Path, infos: Vec) -> VortexResult<()> { let fixtures_json = FixturesJson { fixtures: infos }; let json = serde_json::to_string_pretty(&fixtures_json) - .map_err(|e| vortex_err!("failed to serialize fixtures.json: {e}"))?; + .map_err(|e| vortex_err!(Serde: "failed to serialize fixtures.json: {e}"))?; std::fs::write(output_dir.join("fixtures.json"), format!("{json}\n")) - .map_err(|e| vortex_err!("failed to write fixtures.json: {e}"))?; + .map_err(|e| vortex_err!(Io: "failed to write fixtures.json: {e}"))?; eprintln!(" wrote fixtures.json"); eprintln!( diff --git a/vortex-tui/src/browse/ui/segments.rs b/vortex-tui/src/browse/ui/segments.rs index a271b1195b1..922af882821 100644 --- a/vortex-tui/src/browse/ui/segments.rs +++ b/vortex-tui/src/browse/ui/segments.rs @@ -119,7 +119,7 @@ pub fn segments_ui(app_state: &mut AppState, area: Rect, buf: &mut Buffer) { ); app_state.segment_grid_state.segment_tree = Some( to_display_segment_tree(segment_tree) - .map_err(|e| vortex_err!("Fail to compute segment tree {e}")) + .map_err(|e| vortex_err!(Other: "Fail to compute segment tree {e}")) .vortex_expect("operation should succeed in TUI"), ); } @@ -134,7 +134,7 @@ pub fn segments_ui(app_state: &mut AppState, area: Rect, buf: &mut Buffer) { height: AvailableSpace::Definite(area.height as f32), }; tree.compute_layout(*root_node, viewport_size) - .map_err(|e| vortex_err!("Fail to compute layout {e}")) + .map_err(|e| vortex_err!(Other: "Fail to compute layout {e}")) .vortex_expect("operation should succeed in TUI"); app_state.frame_size = area.as_size(); diff --git a/vortex-tui/src/inspect.rs b/vortex-tui/src/inspect.rs index 038d57e4559..ae7c4984300 100644 --- a/vortex-tui/src/inspect.rs +++ b/vortex-tui/src/inspect.rs @@ -343,12 +343,12 @@ struct VortexInspector<'a> { impl<'a> VortexInspector<'a> { fn new(session: &'a VortexSession, path: PathBuf) -> VortexResult { - let mut file = - File::open(&path).map_err(|e| vortex_err!("Failed to open file {:?}: {}", path, e))?; + let mut file = File::open(&path) + .map_err(|e| vortex_err!(Io: "Failed to open file {:?}: {}", path, e))?; let file_size = file .seek(SeekFrom::End(0)) - .map_err(|e| vortex_err!("Failed to get file size: {}", e))?; + .map_err(|e| vortex_err!(Io: "Failed to get file size: {}", e))?; Ok(Self { session, @@ -361,7 +361,7 @@ impl<'a> VortexInspector<'a> { fn read_eof(&mut self) -> VortexResult { if self.file_size < EOF_SIZE as u64 { vortex_bail!( - "File too small ({} bytes) to contain EOF marker (requires {} bytes)", + InvalidArgument: "File too small ({} bytes) to contain EOF marker (requires {} bytes)", self.file_size, EOF_SIZE ); @@ -370,10 +370,10 @@ impl<'a> VortexInspector<'a> { let mut eof_bytes = [0u8; EOF_SIZE]; self.file .seek(SeekFrom::End(-(EOF_SIZE as i64))) - .map_err(|e| vortex_err!("Failed to seek to EOF: {}", e))?; + .map_err(|e| vortex_err!(Io: "Failed to seek to EOF: {}", e))?; self.file .read_exact(&mut eof_bytes) - .map_err(|e| vortex_err!("Failed to read EOF bytes: {}", e))?; + .map_err(|e| vortex_err!(Io: "Failed to read EOF bytes: {}", e))?; let version = u16::from_le_bytes([eof_bytes[0], eof_bytes[1]]); let postscript_size = u16::from_le_bytes([eof_bytes[2], eof_bytes[3]]); @@ -393,14 +393,14 @@ impl<'a> VortexInspector<'a> { let mut postscript_bytes = vec![0u8; postscript_size as usize]; self.file .seek(SeekFrom::Start(postscript_offset)) - .map_err(|e| vortex_err!("Failed to seek to postscript: {}", e))?; + .map_err(|e| vortex_err!(Io: "Failed to seek to postscript: {}", e))?; self.file .read_exact(&mut postscript_bytes) - .map_err(|e| vortex_err!("Failed to read postscript: {}", e))?; + .map_err(|e| vortex_err!(Io: "Failed to read postscript: {}", e))?; let postscript_buffer = ByteBuffer::from(postscript_bytes); let fb_postscript = root::(&postscript_buffer) - .map_err(|e| vortex_err!("Failed to parse postscript flatbuffer: {}", e))?; + .map_err(|e| vortex_err!(Serde: "Failed to parse postscript flatbuffer: {}", e))?; let segment_info = |s: fb::PostscriptSegment<'_>| -> VortexResult { Ok(SegmentInfo { @@ -416,7 +416,7 @@ impl<'a> VortexInspector<'a> { .layout() .map(segment_info) .transpose()? - .ok_or_else(|| vortex_err!("Postscript missing layout segment"))?; + .ok_or_else(|| vortex_err!(NotFound: "Postscript missing layout segment"))?; let statistics = fb_postscript.statistics().map(segment_info).transpose()?; @@ -424,7 +424,7 @@ impl<'a> VortexInspector<'a> { .footer() .map(segment_info) .transpose()? - .ok_or_else(|| vortex_err!("Postscript missing footer segment"))?; + .ok_or_else(|| vortex_err!(Serde: "Postscript missing footer segment"))?; Ok(PostscriptInfo { dtype, diff --git a/vortex-tui/src/query.rs b/vortex-tui/src/query.rs index fa789bef4dc..05ed4b1706f 100644 --- a/vortex-tui/src/query.rs +++ b/vortex-tui/src/query.rs @@ -54,11 +54,11 @@ pub async fn exec_query(session: &VortexSession, args: QueryArgs) -> VortexResul let file_path = args .file .to_str() - .ok_or_else(|| vortex_err!("Path is not valid UTF-8"))?; + .ok_or_else(|| vortex_err!(InvalidArgument: "Path is not valid UTF-8"))?; let batches: Vec = execute_vortex_query(session, file_path, &args.sql) .await - .map_err(|e| vortex_err!("{e}"))?; + .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; // Build schema info from the result let schema = if let Some(batch) = batches.first() { @@ -82,7 +82,7 @@ pub async fn exec_query(session: &VortexSession, args: QueryArgs) -> VortexResul }; let json_output = serde_json::to_string_pretty(&output) - .map_err(|e| vortex_err!("Failed to serialize JSON: {e}"))?; + .map_err(|e| vortex_err!(Serde: "Failed to serialize JSON: {e}"))?; println!("{json_output}"); Ok(()) diff --git a/vortex-tui/src/segments.rs b/vortex-tui/src/segments.rs index e8ca3d94ab7..4baace28356 100644 --- a/vortex-tui/src/segments.rs +++ b/vortex-tui/src/segments.rs @@ -106,7 +106,7 @@ pub async fn exec_segments(session: &VortexSession, args: SegmentsArgs) -> Vorte let output = SegmentsOutput { columns }; let json_output = serde_json::to_string_pretty(&output) - .map_err(|e| vortex::error::vortex_err!("Failed to serialize JSON: {e}"))?; + .map_err(|e| vortex::error::vortex_err!(Serde: "Failed to serialize JSON: {e}"))?; println!("{json_output}"); Ok(()) diff --git a/vortex-tui/src/tree.rs b/vortex-tui/src/tree.rs index 64d0af2552a..06e991d5b7f 100644 --- a/vortex-tui/src/tree.rs +++ b/vortex-tui/src/tree.rs @@ -115,7 +115,7 @@ async fn exec_layout_tree( if json { let tree = layout_to_json(Arc::clone(footer.layout()))?; let json_output = serde_json::to_string_pretty(&tree) - .map_err(|e| vortex::error::vortex_err!("Failed to serialize JSON: {e}"))?; + .map_err(|e| vortex::error::vortex_err!(Serde: "Failed to serialize JSON: {e}"))?; println!("{json_output}"); } else if verbose { // In verbose mode, fetch segments to display buffer sizes. diff --git a/vortex/benches/common_encoding_tree_throughput.rs b/vortex/benches/common_encoding_tree_throughput.rs index 0d523c133e0..559bb1bc628 100644 --- a/vortex/benches/common_encoding_tree_throughput.rs +++ b/vortex/benches/common_encoding_tree_throughput.rs @@ -110,7 +110,9 @@ mod setup { fn global_reference(array: &FoRArray) -> Scalar { match array.references() { FoRReferences::Global(reference) => reference.clone(), - FoRReferences::Blocked(_) => vortex_panic!("FoR::encode uses a global reference"), + FoRReferences::Blocked(_) => { + vortex_panic!(AssertionFailed: "FoR::encode uses a global reference") + } } } diff --git a/vortex/benches/pipeline.rs b/vortex/benches/pipeline.rs index a53dba2e430..35be3862dd8 100644 --- a/vortex/benches/pipeline.rs +++ b/vortex/benches/pipeline.rs @@ -783,7 +783,7 @@ fn compare_outputs(function_name: &str, expected: &[f32], actual: &[f32], expect ); } vortex_panic!( - "{}: Output mismatch at index {}: expected={}, actual={}", + AssertionFailed: "{}: Output mismatch at index {}: expected={}, actual={}", function_name, i, expected_slice[i], diff --git a/vortex/src/editions/mod.rs b/vortex/src/editions/mod.rs index 464cce2197b..36a2927ec21 100644 --- a/vortex/src/editions/mod.rs +++ b/vortex/src/editions/mod.rs @@ -44,7 +44,6 @@ pub use vortex_edition::declarations::core::CORE_2026_08_3; pub use vortex_edition::declarations::preview; pub use vortex_edition::declarations::preview::PREVIEW_2026_08_0; use vortex_error::VortexExpect; -use vortex_error::vortex_err; use vortex_session::VortexSession; /// The `core` edition enabled for writing by the default Vortex session. @@ -60,13 +59,11 @@ pub fn register_default_editions(session: &VortexSession) { session .editions() .declare_family(family) - .map_err(|e| vortex_err!("{e}")) .vortex_expect("edition families are valid"); } for declaration in EDITION_DECLARATIONS { session .register_edition(declaration) - .map_err(|e| vortex_err!("{e}")) .vortex_expect("edition declarations are valid"); } } @@ -78,6 +75,5 @@ pub fn register_default_editions(session: &VortexSession) { pub fn enable_default_editions(session: &VortexSession) { session .enable_edition(DEFAULT_CORE_EDITION) - .map_err(|e| vortex_err!("{e}")) .vortex_expect("default core edition is registered"); } diff --git a/vortex/src/editions/tests.rs b/vortex/src/editions/tests.rs index c116f73796f..b4b37483429 100644 --- a/vortex/src/editions/tests.rs +++ b/vortex/src/editions/tests.rs @@ -413,7 +413,7 @@ async fn disabling_editions_allows_uneditioned_components() -> VortexResult<()> .await .err() .ok_or_else(|| { - vortex_err!("writer with no enabled editions accepted an extension dtype") + vortex_err!(AssertionFailed: "writer with no enabled editions accepted an extension dtype") })?; assert!( error @@ -556,10 +556,9 @@ async fn writer_restricts_layouts_to_the_enabled_editions() -> VortexResult<()> // Dropping one of them fails the write at the layout it may not emit. let session = session_declaring(&members[1..])?; - let error = write_with(&session, array) - .await - .err() - .ok_or_else(|| vortex_err!("write emitted layout {} outside its edition", written[0]))?; + let error = write_with(&session, array).await.err().ok_or_else( + || vortex_err!(AssertionFailed: "write emitted layout {} outside its edition", written[0]), + )?; assert!( error.to_string().contains(&format!( "Layout encoding {} not permitted by ctx", @@ -652,7 +651,7 @@ async fn explicit_btrblocks_strategy_is_not_reconfigured() -> VortexResult<()> { ) .await .err() - .ok_or_else(|| vortex_err!("explicit BtrBlocks strategy was unexpectedly reconfigured"))?; + .ok_or_else(|| vortex_err!(AssertionFailed: "explicit BtrBlocks strategy was unexpectedly reconfigured"))?; assert!( error .to_string() @@ -683,7 +682,9 @@ async fn serialization_context_rejects_unsupported_compressor_output() -> Vortex ) .await .err() - .ok_or_else(|| vortex_err!("Sequence unexpectedly had a permitted wire variant"))?; + .ok_or_else( + || vortex_err!(AssertionFailed: "Sequence unexpectedly had a permitted wire variant"), + )?; assert!( error .to_string() From 00d0a8b180272543c0c77ed3d40c9dc9e768f739 Mon Sep 17 00:00:00 2001 From: Robert Kruszewski Date: Tue, 6 Oct 2026 15:29:18 +0000 Subject: [PATCH 2/3] Put VortexError's payload behind one Arc VortexError was 56 bytes, so every VortexResult was too, whatever it carried. A result that large is returned through memory: the caller reserves a stack slot, passes its address, and reads the outcome back. That is the path for nearly every call in the codebase, almost all of which succeed: 3158 functions return VortexResult<()> and 684 return VortexResult. The kind, message, source and backtrace now live in one shared allocation, and VortexError is a single pointer: VortexResult for T before after () 56 8 bool, usize, ArrayRef 56 16 Option, Vec 56 24 Results of 16 bytes or less come back in registers on x86-64 and aarch64. Const assertions pin the error and VortexResult<()> to one word. Constructing an error costs no more than before. It already allocated every time, for the Arc around its backtrace; the backtrace now sits inline in the payload, so that allocation is the payload's. Wrapping a foreign error drops from three allocations to two, because its source is now boxed once instead of boxed and then copied into an Arc. Cloning stays a reference-count bump. with_context writes into the payload when it holds the only reference, which is the usual case while an error propagates. On an error that has been cloned, it builds a new payload that points back at the shared one for its source and backtrace, so the other clones are unchanged and nothing is lost. Signed-off-by: Robert Kruszewski Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01S7EtMqoZ91rrCCh9vS2yTm --- vortex-error/src/lib.rs | 107 ++++++++++++++++++++++++++----------- vortex-error/tests/kind.rs | 28 ++++++++++ 2 files changed, 104 insertions(+), 31 deletions(-) diff --git a/vortex-error/src/lib.rs b/vortex-error/src/lib.rs index ec9047f5418..7b087c8d277 100644 --- a/vortex-error/src/lib.rs +++ b/vortex-error/src/lib.rs @@ -132,26 +132,42 @@ impl VortexErrorKind { /// /// An error is a [`VortexErrorKind`], a message, an optional underlying error, and a backtrace /// captured at construction. Cloning is cheap: the payload is shared, never copied. +/// +/// The payload sits behind one pointer, so a `VortexResult` costs the same as `T` plus at +/// most a word on the success path. Most results fit in two registers and are returned in them, +/// rather than through a stack slot the caller must reserve and read back. Constructing an error +/// is no more expensive for it: the payload's allocation is the one the backtrace needed anyway. #[derive(Clone)] -pub struct VortexError { +pub struct VortexError(Arc); + +const _: () = assert!(size_of::() == size_of::()); +const _: () = assert!(size_of::>() == size_of::()); + +struct ErrorInner { kind: VortexErrorKind, - /// `None` defers the message to `source`, keeping the `?` conversion path allocation-free. + /// `None` defers the message to the source, keeping the `?` conversion path allocation-free. message: Option, - source: Option>, - backtrace: Arc, + origin: Origin, } -const _: () = assert!(size_of::() <= 56); +/// Where an error's source and backtrace come from. +enum Origin { + /// Captured when this error was created. + Own { + source: Option>, + backtrace: Backtrace, + }, + /// Shared with the error this one adds context to. + /// + /// Context is normally added in place. This is only for an error that has been cloned, whose + /// payload the other clones still see. + Context(VortexError), +} impl VortexError { /// Creates an error of the given kind carrying `message`. pub fn new>(kind: VortexErrorKind, message: T) -> Self { - Self { - kind, - message: Some(message.into()), - source: None, - backtrace: Arc::new(Backtrace::capture()), - } + Self::from_parts(kind, Some(message.into()), None) } /// Wraps an underlying error as a Vortex error of the given kind. @@ -162,12 +178,7 @@ impl VortexError { where E: Into>, { - Self { - kind, - message: None, - source: Some(Arc::from(source.into())), - backtrace: Arc::new(Backtrace::capture()), - } + Self::from_parts(kind, None, Some(source.into())) } /// Wraps an underlying error that does not fit any more specific [`VortexErrorKind`]. @@ -178,9 +189,24 @@ impl VortexError { Self::wrap(VortexErrorKind::Other, source) } + fn from_parts( + kind: VortexErrorKind, + message: Option, + source: Option>, + ) -> Self { + Self(Arc::new(ErrorInner { + kind, + message, + origin: Origin::Own { + source, + backtrace: Backtrace::capture(), + }, + })) + } + /// The classification of this error. pub fn kind(&self) -> VortexErrorKind { - self.kind + self.0.kind } /// Adds additional context to an error, preserving its kind, source and backtrace. @@ -188,33 +214,53 @@ impl VortexError { let msg: ErrString = msg.into(); // Build the combined string directly: `msg` has already been through the // `VORTEX_PANIC_ON_ERR` check and must not trip it a second time. - self.message = Some(ErrString(Cow::Owned(format!( - "{msg}:\n {}", - self.message_body() - )))); - self + let message = ErrString(Cow::Owned(format!("{msg}:\n {}", self.message_body()))); + if let Some(inner) = Arc::get_mut(&mut self.0) { + inner.message = Some(message); + return self; + } + Self(Arc::new(ErrorInner { + kind: self.kind(), + message: Some(message), + origin: Origin::Context(self), + })) } /// The error message, falling back to the underlying error when none was provided. fn message_body(&self) -> Cow<'_, str> { - match (&self.message, &self.source) { + match (&self.0.message, self.source_ref()) { (Some(message), _) => Cow::Borrowed(message.as_ref()), (None, Some(source)) => Cow::Owned(source.to_string()), (None, None) => Cow::Borrowed(""), } } + + fn source_ref(&self) -> Option<&(dyn Error + Send + Sync + 'static)> { + match &self.0.origin { + Origin::Own { source, .. } => source.as_deref(), + Origin::Context(error) => error.source_ref(), + } + } + + fn backtrace(&self) -> &Backtrace { + match &self.0.origin { + Origin::Own { backtrace, .. } => backtrace, + Origin::Context(error) => error.backtrace(), + } + } } impl Display for VortexError { fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { - f.write_str(self.kind.prefix())?; - match (&self.message, &self.source) { + f.write_str(self.kind().prefix())?; + match (&self.0.message, self.source_ref()) { (Some(message), _) => Display::fmt(message, f)?, (None, Some(source)) => Display::fmt(source, f)?, (None, None) => {} } - if self.backtrace.status() == BacktraceStatus::Captured { - write!(f, "\nBacktrace:\n{}", self.backtrace)?; + let backtrace = self.backtrace(); + if backtrace.status() == BacktraceStatus::Captured { + write!(f, "\nBacktrace:\n{backtrace}")?; } Ok(()) } @@ -228,9 +274,8 @@ impl Debug for VortexError { impl Error for VortexError { fn source(&self) -> Option<&(dyn Error + 'static)> { - self.source - .as_ref() - .map(|source| source.as_ref() as &(dyn Error + 'static)) + self.source_ref() + .map(|source| source as &(dyn Error + 'static)) } } diff --git a/vortex-error/tests/kind.rs b/vortex-error/tests/kind.rs index e50a8833b13..99f17776191 100644 --- a/vortex-error/tests/kind.rs +++ b/vortex-error/tests/kind.rs @@ -141,6 +141,34 @@ fn test_clone_and_shared_round_trip() { assert_eq!(borrowed.to_string(), owned.to_string()); } +#[test] +fn test_context_on_a_clone_leaves_the_other_clone_alone() { + let err = VortexError::from(io::Error::other("disk on fire")); + let clone = err.clone(); + + // The payload is shared, so this context cannot be written into it in place. + let with_context = clone.with_context("while reading"); + + let original = err.to_string(); + assert!( + original.starts_with("IO error: disk on fire") && !original.contains("while reading"), + "{original}" + ); + let display = with_context.to_string(); + assert!( + display.starts_with("IO error: while reading:\n disk on fire"), + "{display}" + ); + assert_eq!(with_context.kind(), VortexErrorKind::Io); + assert!( + with_context + .source() + .and_then(|source| source.downcast_ref::()) + .is_some(), + "context on a shared error must still expose the underlying error" + ); +} + #[test] fn test_arrow_error_is_classified_by_variant() { use arrow_schema::ArrowError; From 3115e2ca3d9d0263a393088cc1d8e1258b980959 Mon Sep 17 00:00:00 2001 From: Robert Kruszewski Date: Fri, 23 Oct 2026 14:24:17 +0000 Subject: [PATCH 3/3] Remove error kinds from VortexError A VortexError is now a message, an optional source and a backtrace. The VortexErrorKind classification is gone, and with it kind(), the kind prefix in the displayed message and the classification of foreign errors in the From impls, which now keep the foreign error as the source. The error macros take a plain format string again. The Context: and External: forms remain, since they are not kinds. Every call site drops its kind tag, and vortex_ensure_eq! loses its kind-only form. Tests that asserted on a kind now assert on the guard's message. The Python bindings raise RuntimeError for every Vortex error, as before kinds existed. The C API keeps VX_ERROR_CODE_OTHER for Vortex errors and VX_ERROR_CODE_PANIC for panics, at their existing values, and the C++ ErrorCode mirrors it. Signed-off-by: Robert Kruszewski Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01S7EtMqoZ91rrCCh9vS2yTm --- STYLE.md | 17 +- encodings/alp/src/alp/array.rs | 26 +- encodings/alp/src/alp/compress.rs | 4 +- encodings/alp/src/alp/compute/compare.rs | 4 +- encodings/alp/src/alp/ops.rs | 2 +- encodings/alp/src/alp/plugin.rs | 24 +- encodings/alp/src/alp_rd/array.rs | 35 +-- encodings/alp/src/alp_rd/mod.rs | 2 +- encodings/bytebool/src/array.rs | 18 +- encodings/bytebool/src/compute.rs | 10 +- encodings/datetime-parts/src/array.rs | 28 +- encodings/datetime-parts/src/canonical.rs | 6 +- encodings/datetime-parts/src/compress.rs | 2 +- encodings/datetime-parts/src/compute/take.rs | 8 +- encodings/datetime-parts/src/ops.rs | 6 +- encodings/datetime-parts/src/timestamp.rs | 4 +- .../decimal-byte-parts/benches/common/mod.rs | 2 +- .../benches/dbp_assemble.rs | 6 +- .../decimal-byte-parts/benches/dbp_split.rs | 2 +- .../src/decimal_byte_parts/array.rs | 28 +- .../src/decimal_byte_parts/assemble.rs | 10 +- .../src/decimal_byte_parts/plugin/mod.rs | 4 +- .../src/decimal_byte_parts/plugin/v1.rs | 12 +- .../src/decimal_byte_parts/plugin/v2.rs | 15 +- encodings/fastlanes/benches/for_decode.rs | 2 +- .../array/bitpack_compress/blocked.rs | 65 +++-- .../array/bitpack_compress/global.rs | 29 +- .../bitpacking/array/bitpack_compress/mod.rs | 4 +- .../array/bitpack_decompress/blocked.rs | 6 +- .../array/bitpack_decompress/global.rs | 2 +- .../fastlanes/src/bitpacking/array/mod.rs | 54 ++-- .../fastlanes/src/bitpacking/array/tests.rs | 2 +- .../src/bitpacking/array/unpack_iter.rs | 6 +- .../fastlanes/src/bitpacking/compute/take.rs | 10 +- .../fastlanes/src/bitpacking/plugin/mod.rs | 12 +- .../fastlanes/src/bitpacking/plugin/tests.rs | 38 +-- .../fastlanes/src/bitpacking/plugin/v1.rs | 8 +- .../fastlanes/src/bitpacking/plugin/v2.rs | 6 +- .../fastlanes/src/bitpacking/vtable/mod.rs | 10 +- encodings/fastlanes/src/delta/array/mod.rs | 2 +- encodings/fastlanes/src/delta/compute/cast.rs | 6 +- encodings/fastlanes/src/delta/tests.rs | 2 +- encodings/fastlanes/src/delta/vtable/mod.rs | 33 ++- .../fastlanes/src/delta/vtable/validity.rs | 16 +- .../fastlanes/src/for_/array/for_compress.rs | 2 +- .../src/for_/array/for_decompress.rs | 2 +- encodings/fastlanes/src/for_/array/mod.rs | 6 +- encodings/fastlanes/src/for_/plugin/mod.rs | 8 +- encodings/fastlanes/src/for_/plugin/tests.rs | 4 +- encodings/fastlanes/src/for_/plugin/v1.rs | 4 +- encodings/fastlanes/src/for_/plugin/v2.rs | 6 +- encodings/fastlanes/src/for_/tests.rs | 4 +- encodings/fastlanes/src/for_/vtable/mod.rs | 28 +- .../fastlanes/src/for_/vtable/operations.rs | 6 +- encodings/fastlanes/src/rle/array/mod.rs | 2 +- .../fastlanes/src/rle/array/rle_decompress.rs | 10 +- encodings/fastlanes/src/rle/probe.rs | 14 +- encodings/fastlanes/src/rle/vtable/mod.rs | 20 +- encodings/fsst/src/array.rs | 67 +++-- encodings/fsst/src/canonical.rs | 18 +- encodings/fsst/src/compress.rs | 4 +- encodings/fsst/src/compute/compare.rs | 2 +- encodings/fsst/src/dfa/flat_contains.rs | 2 +- encodings/fsst/src/dfa/prefix.rs | 2 +- encodings/fsst/src/slice.rs | 2 +- encodings/onpair/src/array.rs | 49 ++-- encodings/onpair/src/canonical.rs | 14 +- encodings/onpair/src/compute/compare.rs | 4 +- encodings/onpair/src/decode.rs | 14 +- encodings/onpair/src/ops.rs | 10 +- encodings/onpair/src/tests.rs | 8 +- encodings/parquet-variant/src/array.rs | 26 +- encodings/parquet-variant/src/arrow.rs | 20 +- .../src/json_to_variant_tests.rs | 18 +- encodings/parquet-variant/src/kernel.rs | 57 ++-- encodings/parquet-variant/src/operations.rs | 15 +- encodings/parquet-variant/src/vtable.rs | 53 ++-- encodings/pco/src/array.rs | 50 ++-- encodings/runend/src/array.rs | 18 +- encodings/runend/src/compute/take.rs | 2 +- encodings/runend/src/iter.rs | 6 +- encodings/runend/src/probe.rs | 6 +- encodings/sequence/src/array.rs | 40 +-- encodings/sequence/src/compute/min_max.rs | 9 +- encodings/sequence/src/compute/take.rs | 4 +- encodings/sequence/src/model_tests.rs | 2 +- encodings/sparse/src/canonical.rs | 14 +- encodings/sparse/src/compute/sum.rs | 4 +- encodings/sparse/src/lib.rs | 24 +- encodings/uuid/src/arrow.rs | 2 +- encodings/uuid/src/metadata.rs | 2 +- encodings/uuid/src/vtable.rs | 45 +-- encodings/zigzag/src/array.rs | 19 +- encodings/zigzag/src/compress.rs | 4 +- encodings/zstd/src/array.rs | 76 +++-- encodings/zstd/src/lib.rs | 6 +- encodings/zstd/src/zstd_buffers.rs | 32 +-- fuzz/fuzz_targets/array_ops.rs | 2 +- fuzz/fuzz_targets/compress_gpu.rs | 2 +- fuzz/fuzz_targets/compress_roundtrip.rs | 2 +- fuzz/fuzz_targets/fsst_like.rs | 2 +- fuzz/fuzz_targets/row_encode.rs | 2 +- fuzz/src/array/compare.rs | 4 +- fuzz/src/array/fill_null.rs | 2 +- fuzz/src/array/mask.rs | 2 +- fuzz/src/array/mod.rs | 16 +- fuzz/src/array/scalar_at.rs | 2 +- fuzz/src/array/search_sorted.rs | 4 +- fuzz/src/array/sum/mod.rs | 4 +- fuzz/src/array/sum/tests.rs | 4 +- fuzz/src/fsst_like.rs | 2 +- fuzz/src/gpu/mod.rs | 2 +- lang/cpp/include/vortex/array.hpp | 2 +- lang/cpp/include/vortex/error.hpp | 12 +- lang/cpp/include/vortex/estimate.hpp | 2 +- lang/cpp/include/vortex/scalar.hpp | 35 ++- lang/cpp/src/array.cpp | 17 +- lang/cpp/src/dtype.cpp | 11 +- lang/cpp/src/expression.cpp | 4 +- lang/cpp/src/scalar.cpp | 2 +- lang/cpp/src/writer.cpp | 4 +- lang/cpp/tests/array.cpp | 4 +- vortex-array/benches/row_fn_bool_retry.rs | 2 +- vortex-array/benches/row_fn_output.rs | 4 +- vortex-array/src/aggregate_fn/accumulator.rs | 18 +- .../src/aggregate_fn/accumulator_grouped.rs | 10 +- vortex-array/src/aggregate_fn/combined.rs | 20 +- .../aggregate_fn/fns/all_non_distinct/mod.rs | 12 +- .../src/aggregate_fn/fns/bounded_max/mod.rs | 10 +- .../src/aggregate_fn/fns/bounded_min/mod.rs | 4 +- .../src/aggregate_fn/fns/count/mod.rs | 2 +- .../src/aggregate_fn/fns/first/mod.rs | 2 +- .../src/aggregate_fn/fns/is_constant/mod.rs | 6 +- .../src/aggregate_fn/fns/is_sorted/mod.rs | 2 +- vortex-array/src/aggregate_fn/fns/last/mod.rs | 2 +- vortex-array/src/aggregate_fn/fns/mean/mod.rs | 4 +- .../src/aggregate_fn/fns/min_max/mod.rs | 6 +- .../aggregate_fn/fns/min_max/varbinview.rs | 2 +- .../src/aggregate_fn/fns/nan_count/mod.rs | 2 +- vortex-array/src/aggregate_fn/fns/sum/bool.rs | 2 +- .../src/aggregate_fn/fns/sum/constant.rs | 27 +- .../src/aggregate_fn/fns/sum/decimal.rs | 2 +- vortex-array/src/aggregate_fn/fns/sum/mod.rs | 10 +- .../src/aggregate_fn/fns/sum/primitive.rs | 28 +- .../src/aggregate_fn/fns/sum_v2/mod.rs | 24 +- .../fns/uncompressed_size_in_bytes/bool.rs | 2 +- .../fns/uncompressed_size_in_bytes/decimal.rs | 10 +- .../fixed_size_list.rs | 2 +- .../uncompressed_size_in_bytes/list_view.rs | 10 +- .../fns/uncompressed_size_in_bytes/mod.rs | 30 +- .../uncompressed_size_in_bytes/primitive.rs | 13 +- .../fns/uncompressed_size_in_bytes/struct_.rs | 4 +- .../fns/uncompressed_size_in_bytes/union.rs | 2 +- .../uncompressed_size_in_bytes/varbinview.rs | 24 +- vortex-array/src/aggregate_fn/foreign.rs | 14 +- vortex-array/src/aggregate_fn/proto.rs | 15 +- .../src/aggregate_fn/storage_pushdown.rs | 4 +- vortex-array/src/aggregate_fn/vtable.rs | 6 +- vortex-array/src/array/erased.rs | 33 ++- vortex-array/src/array/foreign.rs | 2 +- vortex-array/src/array/mod.rs | 20 +- vortex-array/src/array/plugin.rs | 4 +- vortex-array/src/array/probe/array.rs | 16 +- vortex-array/src/array/probe/repeated.rs | 14 +- vortex-array/src/array/vtable/mod.rs | 8 +- vortex-array/src/array/vtable/operations.rs | 2 +- vortex-array/src/arrays/bool/array.rs | 10 +- .../src/arrays/bool/compute/boolean.rs | 2 +- .../src/arrays/bool/compute/fill_null.rs | 2 +- vortex-array/src/arrays/bool/compute/mask.rs | 4 +- vortex-array/src/arrays/bool/compute/take.rs | 11 +- vortex-array/src/arrays/bool/test_harness.rs | 2 +- vortex-array/src/arrays/bool/vtable/mod.rs | 16 +- vortex-array/src/arrays/chunked/array.rs | 8 +- .../src/arrays/chunked/compute/take.rs | 37 ++- .../src/arrays/chunked/vtable/canonical.rs | 12 +- vortex-array/src/arrays/chunked/vtable/mod.rs | 26 +- .../src/arrays/chunked/vtable/operations.rs | 2 +- .../constant/compute/uncompressed_size.rs | 4 +- .../src/arrays/constant/vtable/canonical.rs | 10 +- .../src/arrays/constant/vtable/mod.rs | 8 +- vortex-array/src/arrays/datetime/mod.rs | 6 +- vortex-array/src/arrays/decimal/array.rs | 8 +- .../src/arrays/decimal/compute/cast.rs | 10 +- .../src/arrays/decimal/compute/rules.rs | 6 +- vortex-array/src/arrays/decimal/utils.rs | 4 +- vortex-array/src/arrays/decimal/vtable/mod.rs | 12 +- vortex-array/src/arrays/dict/array.rs | 12 +- vortex-array/src/arrays/dict/vtable/mod.rs | 10 +- .../src/arrays/dict/vtable/operations.rs | 4 +- vortex-array/src/arrays/extension/array.rs | 2 +- .../src/arrays/extension/vtable/mod.rs | 16 +- .../src/arrays/extension/vtable/operations.rs | 2 +- vortex-array/src/arrays/filter/array.rs | 2 +- .../src/arrays/filter/execute/take.rs | 2 +- .../src/arrays/filter/execute/take/rank.rs | 14 +- vortex-array/src/arrays/filter/vtable.rs | 14 +- .../src/arrays/fixed_size_list/array.rs | 6 +- .../arrays/fixed_size_list/compute/take.rs | 45 ++- .../src/arrays/fixed_size_list/vtable/mod.rs | 22 +- vortex-array/src/arrays/fixed_width/array.rs | 4 +- .../src/arrays/fixed_width/take/mod.rs | 4 +- .../src/arrays/fixed_width/take/records.rs | 2 +- .../src/arrays/fixed_width/take/slices.rs | 29 +- vortex-array/src/arrays/fixed_width/vtable.rs | 6 +- .../src/arrays/interleave/execute/bool.rs | 6 +- .../src/arrays/interleave/execute/mod.rs | 2 +- .../arrays/interleave/execute/primitive.rs | 6 +- vortex-array/src/arrays/interleave/mod.rs | 24 +- vortex-array/src/arrays/list/array.rs | 24 +- .../src/arrays/list/compute/filter.rs | 14 +- vortex-array/src/arrays/list/compute/take.rs | 39 +-- vortex-array/src/arrays/list/vtable/mod.rs | 16 +- vortex-array/src/arrays/listview/array.rs | 38 +-- vortex-array/src/arrays/listview/rebuild.rs | 6 +- .../src/arrays/listview/vtable/mod.rs | 18 +- vortex-array/src/arrays/map/array.rs | 6 +- vortex-array/src/arrays/map/compute/cast.rs | 2 +- vortex-array/src/arrays/map/compute/mod.rs | 2 +- vortex-array/src/arrays/map/vtable/mod.rs | 18 +- vortex-array/src/arrays/masked/array.rs | 6 +- vortex-array/src/arrays/masked/vtable/mod.rs | 14 +- .../src/arrays/masked/vtable/operations.rs | 2 +- vortex-array/src/arrays/null/compute/cast.rs | 2 +- vortex-array/src/arrays/null/compute/take.rs | 7 +- vortex-array/src/arrays/null/mod.rs | 10 +- vortex-array/src/arrays/patched/array.rs | 18 +- .../src/arrays/patched/compute/compare.rs | 8 +- vortex-array/src/arrays/patched/vtable/mod.rs | 4 +- .../src/arrays/piecewise_sequence/mod.rs | 28 +- .../src/arrays/piecewise_sequence/vtable.rs | 40 ++- .../src/arrays/primitive/array/cast.rs | 2 +- .../src/arrays/primitive/array/conversion.rs | 2 +- .../src/arrays/primitive/array/mod.rs | 7 +- .../src/arrays/primitive/compute/cast.rs | 29 +- .../src/arrays/primitive/compute/zip.rs | 2 +- .../src/arrays/primitive/vtable/mod.rs | 14 +- vortex-array/src/arrays/scalar_fn/array.rs | 8 +- vortex-array/src/arrays/scalar_fn/plugin.rs | 2 +- vortex-array/src/arrays/scalar_fn/rules.rs | 6 +- .../src/arrays/scalar_fn/vtable/mod.rs | 14 +- .../src/arrays/scalar_fn/vtable/validity.rs | 4 +- vortex-array/src/arrays/slice/array.rs | 2 +- vortex-array/src/arrays/slice/vtable.rs | 16 +- vortex-array/src/arrays/struct_/array.rs | 12 +- .../src/arrays/struct_/compute/cast.rs | 2 +- .../src/arrays/struct_/compute/rules.rs | 2 +- vortex-array/src/arrays/struct_/vtable/mod.rs | 28 +- .../src/arrays/struct_/vtable/operations.rs | 2 +- vortex-array/src/arrays/union/array.rs | 10 +- vortex-array/src/arrays/union/tests/mod.rs | 2 +- vortex-array/src/arrays/union/tests/take.rs | 2 +- vortex-array/src/arrays/union/vtable/mod.rs | 22 +- .../src/arrays/union/vtable/operations.rs | 4 +- .../src/arrays/union/vtable/validate.rs | 12 +- vortex-array/src/arrays/validation_tests.rs | 43 ++- vortex-array/src/arrays/varbin/array.rs | 26 +- vortex-array/src/arrays/varbin/builder.rs | 26 +- .../src/arrays/varbin/compute/compare.rs | 2 +- .../src/arrays/varbin/compute/filter.rs | 28 +- .../src/arrays/varbin/compute/take.rs | 73 ++--- vortex-array/src/arrays/varbin/vtable/mod.rs | 18 +- vortex-array/src/arrays/varbinview/array.rs | 22 +- .../arrays/varbinview/compute/fill_null.rs | 4 +- .../src/arrays/varbinview/compute/take.rs | 13 +- .../src/arrays/varbinview/compute/zip.rs | 2 +- vortex-array/src/arrays/varbinview/tests.rs | 2 +- .../src/arrays/varbinview/vtable/mod.rs | 24 +- vortex-array/src/arrays/variant/mod.rs | 18 +- vortex-array/src/arrays/variant/vtable/mod.rs | 22 +- vortex-array/src/builders/bool.rs | 2 +- vortex-array/src/builders/child.rs | 2 +- vortex-array/src/builders/decimal.rs | 6 +- vortex-array/src/builders/dict/bytes.rs | 8 +- vortex-array/src/builders/dict/mod.rs | 4 +- vortex-array/src/builders/dict/primitive.rs | 10 +- vortex-array/src/builders/extension.rs | 2 +- vortex-array/src/builders/fixed_size_list.rs | 16 +- .../src/builders/lazy_null_builder.rs | 2 +- vortex-array/src/builders/list.rs | 8 +- vortex-array/src/builders/listview.rs | 10 +- vortex-array/src/builders/map.rs | 6 +- vortex-array/src/builders/mod.rs | 4 +- vortex-array/src/builders/null.rs | 2 +- vortex-array/src/builders/primitive.rs | 2 +- vortex-array/src/builders/struct_.rs | 8 +- vortex-array/src/builders/tests.rs | 2 +- vortex-array/src/builders/validity.rs | 2 +- vortex-array/src/builders/varbinview.rs | 4 +- vortex-array/src/canonical.rs | 58 ++-- .../src/compute/conformance/binary_numeric.rs | 4 +- vortex-array/src/compute/conformance/cast.rs | 4 +- .../src/compute/conformance/consistency.rs | 4 +- vortex-array/src/dtype/decimal/mod.rs | 10 +- vortex-array/src/dtype/decimal/precision.rs | 8 +- vortex-array/src/dtype/decimal/types.rs | 2 +- vortex-array/src/dtype/dtype_impl.rs | 10 +- vortex-array/src/dtype/extension/erased.rs | 2 +- vortex-array/src/dtype/field_mask.rs | 4 +- vortex-array/src/dtype/map.rs | 2 +- vortex-array/src/dtype/ptype.rs | 4 +- vortex-array/src/dtype/serde/flatbuffers.rs | 90 +++--- vortex-array/src/dtype/serde/proto.rs | 36 ++- vortex-array/src/dtype/struct_.rs | 10 +- vortex-array/src/dtype/union.rs | 14 +- vortex-array/src/executor.rs | 16 +- vortex-array/src/expr/bound_expression.rs | 4 +- vortex-array/src/expr/expression.rs | 10 +- vortex-array/src/expr/exprs.rs | 6 +- vortex-array/src/expr/lambda/mod.rs | 10 +- vortex-array/src/expr/lambda/tests.rs | 4 +- vortex-array/src/expr/optimize.rs | 9 +- vortex-array/src/expr/proto.rs | 6 +- vortex-array/src/expr/traversal/fold.rs | 4 +- vortex-array/src/extension/datetime/date.rs | 16 +- vortex-array/src/extension/datetime/time.rs | 28 +- .../src/extension/datetime/timestamp.rs | 17 +- vortex-array/src/extension/datetime/unit.rs | 2 +- .../src/extension/tests/divisible_int.rs | 14 +- vortex-array/src/mask.rs | 2 +- vortex-array/src/mask_future.rs | 2 +- vortex-array/src/metadata.rs | 2 +- vortex-array/src/normalize.rs | 2 +- vortex-array/src/optimizer/mod.rs | 2 +- vortex-array/src/optimizer/rules.rs | 4 +- vortex-array/src/patches.rs | 67 +++-- vortex-array/src/scalar/cast.rs | 14 +- vortex-array/src/scalar/constructor.rs | 16 +- vortex-array/src/scalar/convert/decimal.rs | 22 +- .../src/scalar/convert/from_scalar.rs | 98 +++---- vortex-array/src/scalar/convert/primitive.rs | 18 +- vortex-array/src/scalar/downcast.rs | 32 +-- vortex-array/src/scalar/proto.rs | 95 +++---- vortex-array/src/scalar/scalar_impl.rs | 6 +- vortex-array/src/scalar/scalar_value.rs | 2 +- vortex-array/src/scalar/tests/casting.rs | 8 +- vortex-array/src/scalar/truncation.rs | 4 +- vortex-array/src/scalar/typed_view/binary.rs | 2 +- vortex-array/src/scalar/typed_view/bool.rs | 2 +- .../scalar/typed_view/decimal/arithmetic.rs | 7 +- .../src/scalar/typed_view/decimal/dvalue.rs | 8 +- .../scalar/typed_view/decimal/integer_cast.rs | 2 +- .../src/scalar/typed_view/decimal/scalar.rs | 4 +- .../src/scalar/typed_view/decimal/tests.rs | 10 +- .../src/scalar/typed_view/extension/mod.rs | 4 +- .../src/scalar/typed_view/extension/tests.rs | 4 +- vortex-array/src/scalar/typed_view/list.rs | 12 +- vortex-array/src/scalar/typed_view/map.rs | 12 +- .../typed_view/primitive/numeric_operator.rs | 2 +- .../src/scalar/typed_view/primitive/pvalue.rs | 53 ++-- .../src/scalar/typed_view/primitive/scalar.rs | 10 +- vortex-array/src/scalar/typed_view/struct_.rs | 14 +- vortex-array/src/scalar/typed_view/union.rs | 4 +- vortex-array/src/scalar/typed_view/utf8.rs | 2 +- vortex-array/src/scalar/typed_view/variant.rs | 2 +- vortex-array/src/scalar/validate.rs | 46 +-- vortex-array/src/scalar_fn/erased.rs | 2 +- vortex-array/src/scalar_fn/fns/between/mod.rs | 6 +- .../src/scalar_fn/fns/binary/boolean.rs | 16 +- .../scalar_fn/fns/binary/compare/boolean.rs | 6 +- .../src/scalar_fn/fns/binary/compare/bytes.rs | 4 +- .../scalar_fn/fns/binary/compare/decimal.rs | 8 +- .../src/scalar_fn/fns/binary/compare/mod.rs | 10 +- .../scalar_fn/fns/binary/compare/nested.rs | 4 +- .../scalar_fn/fns/binary/compare/primitive.rs | 2 +- vortex-array/src/scalar_fn/fns/binary/mod.rs | 6 +- .../scalar_fn/fns/binary/numeric/decimal.rs | 11 +- .../src/scalar_fn/fns/binary/numeric/mod.rs | 6 +- .../src/scalar_fn/fns/binary/numeric/row.rs | 9 +- vortex-array/src/scalar_fn/fns/byte_length.rs | 6 +- vortex-array/src/scalar_fn/fns/case_when.rs | 14 +- vortex-array/src/scalar_fn/fns/cast/mod.rs | 20 +- vortex-array/src/scalar_fn/fns/dynamic.rs | 2 +- vortex-array/src/scalar_fn/fns/ext_storage.rs | 4 +- .../src/scalar_fn/fns/fill_null/kernel.rs | 2 +- .../src/scalar_fn/fns/fill_null/mod.rs | 26 +- vortex-array/src/scalar_fn/fns/get_item.rs | 4 +- vortex-array/src/scalar_fn/fns/is_nan.rs | 2 +- vortex-array/src/scalar_fn/fns/like/mod.rs | 9 +- .../src/scalar_fn/fns/like/pattern.rs | 2 +- .../src/scalar_fn/fns/list_contains/mod.rs | 12 +- .../fns/list_contains/prepared/data.rs | 12 +- vortex-array/src/scalar_fn/fns/list_length.rs | 4 +- vortex-array/src/scalar_fn/fns/list_sum.rs | 10 +- vortex-array/src/scalar_fn/fns/literal.rs | 2 +- vortex-array/src/scalar_fn/fns/mask/kernel.rs | 4 +- vortex-array/src/scalar_fn/fns/mask/mod.rs | 2 +- vortex-array/src/scalar_fn/fns/merge.rs | 18 +- vortex-array/src/scalar_fn/fns/not/mod.rs | 2 +- vortex-array/src/scalar_fn/fns/operators.rs | 6 +- vortex-array/src/scalar_fn/fns/pack.rs | 2 +- .../src/scalar_fn/fns/replace_time_zone.rs | 20 +- vortex-array/src/scalar_fn/fns/select.rs | 12 +- vortex-array/src/scalar_fn/fns/stat.rs | 2 +- .../src/scalar_fn/fns/variant_get/mod.rs | 22 +- vortex-array/src/scalar_fn/fns/zip/mod.rs | 4 +- vortex-array/src/scalar_fn/foreign.rs | 2 +- .../src/scalar_fn/internal/row_count.rs | 6 +- vortex-array/src/scalar_fn/typed.rs | 2 +- .../src/scalar_fn/unstable/row/batch/args.rs | 2 +- .../unstable/row/batch/execute/output.rs | 6 +- .../scalar_fn/unstable/row/batch/planning.rs | 2 +- .../src/scalar_fn/unstable/row/batch/tests.rs | 22 +- .../scalar_fn/unstable/row/execute/owned.rs | 16 +- .../unstable/row/execute/packed_bool.rs | 6 +- .../scalar_fn/unstable/row/execute/retry.rs | 4 +- .../scalar_fn/unstable/row/execute/sink.rs | 16 +- .../scalar_fn/unstable/row/execute/tests.rs | 8 +- .../src/scalar_fn/unstable/row/row_fn.rs | 2 +- .../unstable/row/types/element/bool.rs | 6 +- .../unstable/row/types/element/primitive.rs | 8 +- .../row/types/element/tuple/element_tuple.rs | 4 +- .../unstable/row/types/element/tuple/tests.rs | 4 +- .../unstable/row/types/element/utf8.rs | 8 +- .../row/types/sink/fixed_size_list.rs | 1 - .../scalar_fn/unstable/row/visitor/check.rs | 4 +- .../scalar_fn/unstable/row/visitor/plan.rs | 12 +- .../unstable/row/visitor/row_visitor.rs | 6 +- .../src/scalar_fn/unstable/row/vtable.rs | 6 +- vortex-array/src/scalar_fn/vtable.rs | 4 +- vortex-array/src/serde.rs | 57 ++-- vortex-array/src/session/mod.rs | 4 +- vortex-array/src/stats/flatbuffers.rs | 6 +- vortex-array/src/stats/stats_set.rs | 6 +- vortex-array/src/test_harness/trace/mod.rs | 2 +- vortex-array/src/test_harness/trace/tests.rs | 32 +-- vortex-array/src/validity.rs | 18 +- vortex-arrow/src/convert.rs | 42 +-- vortex-arrow/src/datum.rs | 2 +- vortex-arrow/src/dtype.rs | 24 +- vortex-arrow/src/executor/bool.rs | 2 +- vortex-arrow/src/executor/byte.rs | 10 +- vortex-arrow/src/executor/decimal.rs | 32 +-- vortex-arrow/src/executor/dictionary.rs | 4 +- vortex-arrow/src/executor/fixed_size_list.rs | 6 +- vortex-arrow/src/executor/list.rs | 6 +- vortex-arrow/src/executor/list_view.rs | 6 +- vortex-arrow/src/executor/map.rs | 4 +- vortex-arrow/src/executor/mod.rs | 4 +- vortex-arrow/src/executor/null.rs | 2 +- vortex-arrow/src/executor/run_end.rs | 21 +- vortex-arrow/src/executor/struct_.rs | 4 +- vortex-arrow/src/executor/temporal.rs | 8 +- vortex-arrow/src/run_end_import.rs | 2 +- vortex-arrow/src/scalar.rs | 30 +- vortex-arrow/src/session.rs | 24 +- vortex-bench/src/conversions.rs | 5 +- vortex-bench/src/datasets/mod.rs | 2 +- vortex-bench/src/lib.rs | 10 +- vortex-bench/src/measurements.rs | 14 +- vortex-bench/src/public_bi.rs | 15 +- vortex-bench/src/runner.rs | 8 +- vortex-bench/src/statpopgen/builder.rs | 4 +- vortex-bench/src/statpopgen/vcf_conversion.rs | 46 +-- vortex-bench/src/vector_dataset/convert.rs | 37 ++- vortex-btrblocks/src/schemes/float/alprd.rs | 2 +- .../src/schemes/integer/sequence.rs | 4 +- vortex-btrblocks/tests/decimal_config.rs | 8 +- vortex-buffer/src/alignment.rs | 12 +- vortex-buffer/src/allocation.rs | 2 +- vortex-buffer/src/arrow.rs | 4 +- vortex-buffer/src/buffer.rs | 32 +-- vortex-buffer/src/buffer_mut.rs | 29 +- vortex-buffer/src/const_.rs | 2 +- vortex-buffer/src/string.rs | 4 +- vortex-cloud/src/registry/tests.rs | 7 +- vortex-compressor/src/compressor/cascade.rs | 3 +- .../src/compressor/constant/tests.rs | 4 +- .../src/compressor/structural.rs | 2 +- vortex-compressor/src/compressor/tests.rs | 4 +- vortex-compressor/src/stats/float.rs | 4 +- vortex-compressor/src/stats/varbinview.rs | 2 +- vortex-cuda/benches/dynamic_dispatch_cuda.rs | 26 +- vortex-cuda/benches/filter_cuda.rs | 12 +- vortex-cuda/benches/zstd_cuda.rs | 12 +- vortex-cuda/ffi/src/lib.rs | 40 +-- vortex-cuda/src/arrow/canonical.rs | 92 +++--- vortex-cuda/src/arrow/dictionary_tests.rs | 8 +- vortex-cuda/src/arrow/list_view.rs | 40 +-- vortex-cuda/src/arrow/mod.rs | 48 ++-- vortex-cuda/src/arrow/offsets.rs | 10 +- vortex-cuda/src/canonical.rs | 2 +- vortex-cuda/src/cub.rs | 14 +- vortex-cuda/src/device_buffer.rs | 51 ++-- vortex-cuda/src/dynamic_dispatch/mod.rs | 22 +- .../src/dynamic_dispatch/plan_builder.rs | 28 +- vortex-cuda/src/executor.rs | 16 +- vortex-cuda/src/file.rs | 4 +- vortex-cuda/src/hybrid_dispatch/mod.rs | 8 +- vortex-cuda/src/kernel/arrays/constant.rs | 14 +- vortex-cuda/src/kernel/arrays/dict.rs | 4 +- vortex-cuda/src/kernel/arrays/list.rs | 4 +- vortex-cuda/src/kernel/arrays/masked.rs | 4 +- vortex-cuda/src/kernel/encodings/alp.rs | 4 +- vortex-cuda/src/kernel/encodings/bitpacked.rs | 10 +- .../src/kernel/encodings/date_time_parts.rs | 8 +- .../kernel/encodings/decimal_byte_parts.rs | 4 +- vortex-cuda/src/kernel/encodings/delta.rs | 8 +- vortex-cuda/src/kernel/encodings/for_.rs | 9 +- vortex-cuda/src/kernel/encodings/fsst.rs | 5 +- vortex-cuda/src/kernel/encodings/onpair.rs | 34 +-- vortex-cuda/src/kernel/encodings/runend.rs | 12 +- vortex-cuda/src/kernel/encodings/sequence.rs | 6 +- vortex-cuda/src/kernel/encodings/zigzag.rs | 10 +- vortex-cuda/src/kernel/encodings/zstd.rs | 11 +- .../src/kernel/encodings/zstd_buffers.rs | 10 +- vortex-cuda/src/kernel/filter/mod.rs | 14 +- vortex-cuda/src/kernel/mod.rs | 18 +- vortex-cuda/src/kernel/patches/mod.rs | 2 +- vortex-cuda/src/kernel/patches/types.rs | 2 +- vortex-cuda/src/kernel/slice/mod.rs | 4 +- vortex-cuda/src/layout.rs | 12 +- vortex-cuda/src/pinned.rs | 67 ++--- vortex-cuda/src/pooled_read_at.rs | 11 +- vortex-cuda/src/pooled_read_at/file.rs | 12 +- vortex-cuda/src/pooled_read_at/file/direct.rs | 22 +- vortex-cuda/src/pooled_read_at/file/tests.rs | 6 +- vortex-cuda/src/session.rs | 4 +- vortex-cuda/src/stream.rs | 16 +- vortex-cuda/src/stream_pool.rs | 14 +- vortex-datafusion/examples/vortex_table.rs | 2 +- vortex-datafusion/src/convert/scalars.rs | 31 +- vortex-datafusion/src/convert/stats/tests.rs | 2 +- vortex-datafusion/src/persistent/format.rs | 8 +- vortex-datafusion/src/v2/source.rs | 2 +- vortex-duckdb/src/convert/dtype.rs | 31 +- vortex-duckdb/src/convert/expr.rs | 10 +- vortex-duckdb/src/convert/scalar.rs | 41 ++- vortex-duckdb/src/convert/table_filter.rs | 10 +- vortex-duckdb/src/convert/vector.rs | 8 +- vortex-duckdb/src/copy.rs | 8 +- vortex-duckdb/src/duckdb/connection.rs | 6 +- vortex-duckdb/src/duckdb/data_chunk.rs | 4 +- vortex-duckdb/src/duckdb/database.rs | 14 +- vortex-duckdb/src/duckdb/function.rs | 4 +- vortex-duckdb/src/duckdb/logical_type.rs | 18 +- vortex-duckdb/src/duckdb/macro_.rs | 12 +- vortex-duckdb/src/duckdb/query_result.rs | 4 +- vortex-duckdb/src/duckdb/table_filter.rs | 2 +- vortex-duckdb/src/duckdb/value.rs | 14 +- vortex-duckdb/src/duckdb/vector.rs | 4 +- vortex-duckdb/src/exporter/canonical.rs | 6 +- vortex-duckdb/src/exporter/chunked.rs | 2 +- vortex-duckdb/src/exporter/decimal.rs | 2 +- vortex-duckdb/src/exporter/extension.rs | 2 +- vortex-duckdb/src/exporter/mod.rs | 4 +- vortex-duckdb/src/exporter/uuid.rs | 2 +- vortex-duckdb/src/ffi.rs | 6 +- vortex-duckdb/src/projection.rs | 6 +- vortex-duckdb/src/table_function.rs | 2 +- vortex-edition/src/lib.rs | 16 +- vortex-edition/src/session.rs | 18 +- vortex-edition/src/test_harness.rs | 2 +- vortex-edition/src/tests.rs | 6 +- vortex-error/src/lib.rs | 267 +++--------------- vortex-error/tests/ensure.rs | 48 +--- vortex-error/tests/error.rs | 117 ++++++++ vortex-error/tests/fmt.rs | 12 +- vortex-error/tests/kind.rs | 217 -------------- .../src/analysis/referenced_field_paths.rs | 2 +- vortex-expr/src/stats/rewrite.rs | 2 +- vortex-expr/src/transform/bound_partition.rs | 6 +- vortex-ffi/cinclude/vortex.h | 38 +-- vortex-ffi/examples/hello_vortex.rs | 4 +- vortex-ffi/src/array.rs | 28 +- vortex-ffi/src/data_source.rs | 2 +- vortex-ffi/src/dtype.rs | 10 +- vortex-ffi/src/error.rs | 65 +---- vortex-ffi/src/lib.rs | 4 +- vortex-ffi/src/scalar.rs | 14 +- vortex-ffi/src/scan.rs | 10 +- vortex-ffi/src/session.rs | 2 +- vortex-ffi/src/sink.rs | 6 +- vortex-ffi/src/string.rs | 5 +- vortex-ffi/src/struct_array.rs | 2 +- vortex-file/src/footer/deserializer.rs | 26 +- vortex-file/src/footer/field_sizes.rs | 2 +- vortex-file/src/footer/mod.rs | 6 +- vortex-file/src/footer/postscript.rs | 12 +- vortex-file/src/footer/serializer.rs | 6 +- vortex-file/src/multi/mod.rs | 8 +- vortex-file/src/multi/uri.rs | 8 +- vortex-file/src/open.rs | 6 +- vortex-file/src/read/driver.rs | 2 +- vortex-file/src/read/request.rs | 6 +- vortex-file/src/segments/source.rs | 29 +- vortex-file/src/segments/writer.rs | 4 +- vortex-file/src/writer.rs | 14 +- vortex-io/src/filesystem/glob.rs | 13 +- vortex-io/src/object_store/read_at.rs | 4 +- vortex-io/src/read_at.rs | 2 +- vortex-io/src/request/mod.rs | 6 +- vortex-io/src/request/source.rs | 10 +- vortex-io/src/request/source/tests.rs | 2 +- vortex-io/src/runtime/blocking_pool.rs | 18 +- vortex-io/src/runtime/handle.rs | 2 +- vortex-io/src/runtime/single.rs | 6 +- vortex-io/src/runtime/tokio.rs | 4 +- vortex-ipc/src/iterator.rs | 8 +- vortex-ipc/src/messages/decoder.rs | 8 +- vortex-ipc/src/messages/encoder.rs | 4 +- vortex-ipc/src/messages/reader_async.rs | 2 +- vortex-ipc/src/messages/reader_buf.rs | 2 +- vortex-ipc/src/messages/reader_sync.rs | 4 +- vortex-ipc/src/stream.rs | 12 +- vortex-jni/src/data_source.rs | 14 +- vortex-jni/src/errors.rs | 2 +- vortex-jni/src/expression.rs | 89 +++--- vortex-jni/src/file.rs | 10 +- vortex-jni/src/io/mod.rs | 2 +- vortex-jni/src/io/read_at.rs | 21 +- vortex-jni/src/io/write.rs | 4 +- vortex-jni/src/object_store.rs | 9 +- vortex-jni/src/runtime.rs | 2 +- vortex-jni/src/scan.rs | 18 +- vortex-jni/src/writer.rs | 42 ++- vortex-json/src/dtype.rs | 6 +- vortex-json/src/json_to_variant.rs | 10 +- vortex-layout/examples/reverse_index/main.rs | 8 +- vortex-layout/src/arrays/shared/vtable.rs | 10 +- vortex-layout/src/children.rs | 12 +- vortex-layout/src/layouts/chunked/mod.rs | 4 +- vortex-layout/src/layouts/chunked/reader.rs | 4 +- vortex-layout/src/layouts/dict/mod.rs | 8 +- vortex-layout/src/layouts/dict/writer.rs | 6 +- vortex-layout/src/layouts/file_stats.rs | 2 +- vortex-layout/src/layouts/flat/mod.rs | 8 +- vortex-layout/src/layouts/flat/writer.rs | 2 +- vortex-layout/src/layouts/foreign/mod.rs | 2 +- vortex-layout/src/layouts/indexed/mod.rs | 30 +- .../src/layouts/indexed/test_harness.rs | 10 +- vortex-layout/src/layouts/indexed/tests.rs | 44 ++- vortex-layout/src/layouts/indexed/writer.rs | 8 +- vortex-layout/src/layouts/list/mod.rs | 21 +- vortex-layout/src/layouts/list/writer.rs | 4 +- vortex-layout/src/layouts/repartition.rs | 2 +- vortex-layout/src/layouts/row_idx/expr.rs | 2 +- vortex-layout/src/layouts/struct_/mod.rs | 12 +- vortex-layout/src/layouts/struct_/reader.rs | 16 +- vortex-layout/src/layouts/struct_/writer.rs | 6 +- .../aggregates/bloom_filter/canonical/bool.rs | 4 +- .../aggregates/bloom_filter/canonical/mod.rs | 2 +- .../zoned/aggregates/bloom_filter/mod.rs | 19 +- .../bloom_filter/partial/aggregate.rs | 2 +- .../aggregates/bloom_filter/partial/mod.rs | 2 +- .../aggregates/bloom_filter/partial/scalar.rs | 2 +- .../aggregates/bloom_filter/partial/serde.rs | 4 +- .../aggregates/bloom_filter/scalar_fn.rs | 21 +- vortex-layout/src/layouts/zoned/builder.rs | 2 +- vortex-layout/src/layouts/zoned/mod.rs | 26 +- vortex-layout/src/layouts/zoned/reader.rs | 4 +- vortex-layout/src/layouts/zoned/schema.rs | 6 +- vortex-layout/src/layouts/zoned/writer.rs | 2 +- vortex-layout/src/layouts/zoned/zone_map.rs | 8 +- vortex-layout/src/plan/physical/children.rs | 11 +- vortex-layout/src/plan/physical/lower.rs | 12 +- vortex-layout/src/plan/physical/mod.rs | 2 +- .../src/plan/physical/operators/concat.rs | 8 +- .../src/plan/physical/operators/filter.rs | 2 +- .../src/plan/physical/operators/mod.rs | 6 +- .../src/plan/physical/operators/pack.rs | 16 +- .../src/plan/physical/operators/scan.rs | 2 +- .../src/plan/physical/optimizer/rules.rs | 8 +- .../src/plan/physical/pipeline/scan.rs | 31 +- .../physical/pipeline/scheduling_tests.rs | 16 +- .../src/plan/physical/pipeline/synthetic.rs | 2 +- .../src/plan/physical/pipeline/tests.rs | 10 +- .../src/plan/physical/plans/concat.rs | 14 +- vortex-layout/src/plan/physical/plans/eval.rs | 6 +- .../src/plan/physical/plans/filter.rs | 4 +- .../src/plan/physical/plans/legacy_stats.rs | 4 +- .../src/plan/physical/plans/list_pack.rs | 26 +- vortex-layout/src/plan/physical/plans/pack.rs | 53 ++-- .../src/plan/physical/plans/row_idx.rs | 16 +- .../src/plan/physical/plans/share.rs | 4 +- vortex-layout/src/plan/physical/plans/take.rs | 14 +- .../src/plan/physical/plans/zoned.rs | 18 +- vortex-layout/src/plan/physical/selection.rs | 2 +- vortex-layout/src/plan/physical/tests.rs | 128 ++++----- vortex-layout/src/plan/physical/typed.rs | 6 +- vortex-layout/src/plan/physical/vtable.rs | 2 +- vortex-layout/src/reader.rs | 6 +- vortex-layout/src/scan/execution/adaptor.rs | 8 +- .../src/scan/execution/projection.rs | 2 +- vortex-layout/src/scan/filter.rs | 4 +- vortex-layout/src/scan/layout.rs | 2 +- vortex-layout/src/scan/multi.rs | 4 +- vortex-layout/src/scan/repeated_scan.rs | 4 +- vortex-layout/src/scan/scan_builder.rs | 29 +- vortex-layout/src/scan/split_by.rs | 8 +- vortex-layout/src/scan/test.rs | 10 +- vortex-layout/src/scan/v2/io.rs | 12 +- vortex-layout/src/scan/v2/tests.rs | 6 +- vortex-layout/src/segments/test.rs | 2 +- vortex-layout/src/serde.rs | 19 +- vortex-layout/src/test.rs | 2 +- vortex-mask/src/bitops.rs | 10 +- vortex-mask/src/lib.rs | 4 +- vortex-python-cuda/src/lib.rs | 23 +- vortex-python/src/arrays/py/vtable.rs | 18 +- vortex-python/src/arrays/range_to_sequence.rs | 6 +- vortex-python/src/dtype/decimal.rs | 4 +- vortex-python/src/dtype/primitive.rs | 2 +- vortex-python/src/dtype/struct_.rs | 4 +- vortex-python/src/error.rs | 28 +- vortex-python/src/iter/python.rs | 2 +- vortex-python/src/object_store/resolve.rs | 6 +- vortex-python/src/python_repr.rs | 2 +- vortex-python/src/readable.rs | 6 +- vortex-python/src/scalar/into_py.rs | 2 +- vortex-python/src/scalar/struct_.rs | 2 +- vortex-python/test/test_file_arrow_indices.py | 2 +- vortex-row/src/codec.rs | 49 ++-- vortex-row/src/encode.rs | 6 +- vortex-row/src/encoder.rs | 8 +- vortex-row/src/options.rs | 4 +- vortex-row/src/size.rs | 9 +- vortex-scan/src/lib.rs | 2 +- vortex-scan/src/planning/driver/mod.rs | 22 +- vortex-scan/src/planning/next.rs | 2 +- vortex-scan/src/planning/tests/scripted.rs | 10 +- vortex-scan/src/selection.rs | 2 +- vortex-scan/src/strict_sorted_buffer.rs | 2 +- vortex-session/src/session.rs | 2 +- vortex-spatial/src/aggregate_fn/aabb.rs | 2 +- vortex-spatial/src/extension/coordinate.rs | 10 +- vortex-spatial/src/extension/linestring.rs | 81 +++--- vortex-spatial/src/extension/mod.rs | 32 +-- .../src/extension/multilinestring.rs | 87 +++--- vortex-spatial/src/extension/multipoint.rs | 69 +++-- vortex-spatial/src/extension/multipolygon.rs | 90 +++--- vortex-spatial/src/extension/point.rs | 14 +- vortex-spatial/src/extension/polygon.rs | 90 +++--- vortex-spatial/src/extension/rect.rs | 19 +- vortex-spatial/src/extension/wkb.rs | 16 +- vortex-spatial/src/scalar_fn/collect.rs | 15 +- vortex-spatial/src/scalar_fn/contains.rs | 4 +- vortex-spatial/src/scalar_fn/convex_hull.rs | 8 +- vortex-spatial/src/scalar_fn/envelope.rs | 10 +- vortex-spatial/src/scalar_fn/intersects.rs | 4 +- vortex-spatial/src/scalar_fn/length.rs | 13 +- vortex-spatial/src/scalar_fn/make_line.rs | 14 +- vortex-spatial/src/scalar_fn/row.rs | 4 +- vortex-spatial/src/test_harness.rs | 2 +- vortex-spatial/src/tests/point.rs | 4 +- vortex-spatial/src/tests/rect.rs | 6 +- vortex-spatial/src/tests/wkb.rs | 2 +- vortex-tensor/src/scalar_fns/l2_norm.rs | 4 +- vortex-tensor/src/scalar_fns/l2_normalize.rs | 7 +- vortex-tensor/src/scalar_fns/row.rs | 20 +- .../src/types/fixed_shape_tensor/matcher.rs | 2 +- .../src/types/fixed_shape_tensor/metadata.rs | 8 +- .../src/types/fixed_shape_tensor/proto.rs | 3 +- .../src/types/fixed_shape_tensor/vtable.rs | 8 +- vortex-tensor/src/types/vector/matcher.rs | 2 +- vortex-tensor/src/types/vector/mod.rs | 6 +- vortex-tensor/src/utils.rs | 24 +- vortex-test/compat-gen/src/adapter.rs | 8 +- vortex-test/compat-gen/src/check.rs | 11 +- .../fixtures/arrays/datasets/clickbench.rs | 41 ++- vortex-test/compat-gen/src/fixtures/mod.rs | 2 +- vortex-test/compat-gen/src/generate.rs | 8 +- vortex-tui/src/browse/ui/segments.rs | 4 +- vortex-tui/src/inspect.rs | 22 +- vortex-tui/src/query.rs | 6 +- vortex-tui/src/segments.rs | 2 +- vortex-tui/src/tree.rs | 2 +- .../common_encoding_tree_throughput.rs | 2 +- vortex/benches/pipeline.rs | 2 +- vortex/src/editions/tests.rs | 15 +- 770 files changed, 4658 insertions(+), 5201 deletions(-) create mode 100644 vortex-error/tests/error.rs delete mode 100644 vortex-error/tests/kind.rs diff --git a/STYLE.md b/STYLE.md index 05ef59a5b61..a6ba99171ae 100644 --- a/STYLE.md +++ b/STYLE.md @@ -54,20 +54,9 @@ - `vortex_panic!` for handling invariant violations - `vortex_ensure!` and `vortex_ensure_eq!` for checking conditions. Prefer `vortex_ensure_eq!(a, b)` with no message: the error already shows both expressions and values. - Add a message only for context the expressions lack, and never repeat the values in it. With no - message the error is `AssertionFailed`; when the check is on the caller's input rather than an - internal invariant, name the kind alone, as in `vortex_ensure_eq!(a, b, InvalidArgument)`. -- Every message names its `VortexErrorKind`, as in `vortex_bail!(InvalidArgument: "...")`; the - macros reject a message without one. Choose the kind by what went wrong, the way Python picks an - exception class: `InvalidArgument` (`ValueError`) for a value the callee rejects, - `MismatchedTypes` (`TypeError`) for the wrong dtype, `OutOfBounds` (`IndexError`) for a position - past the end, `NotFound` (`KeyError`) for a name that resolves to nothing, `Overflow` - (`OverflowError`) for a value that does not fit its target, `NotImplemented`, `Serde` for an - unreadable wire or file format, `Io` for a failed system or driver call, `AssertionFailed` for a - broken internal invariant, and `Other` only when nothing else fits. Never classify by where the - failure happened. -- Add context to an existing error with `.with_context()`, which keeps its kind; do not format it - into a new `vortex_err!`, which discards the kind. + Add a message only for context the expressions lack, and never repeat the values in it. +- Add context to an existing error with `.with_context()`, which keeps its source and backtrace; + do not format it into a new `vortex_err!`, which discards them. - Include backtraces for better debugging - Use `VortexExpect` trait when unwrapping is appropriate with proper error context. diff --git a/encodings/alp/src/alp/array.rs b/encodings/alp/src/alp/array.rs index 075841b2ecb..8cc368830ae 100644 --- a/encodings/alp/src/alp/array.rs +++ b/encodings/alp/src/alp/array.rs @@ -98,7 +98,7 @@ impl VTable for ALP { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ALPArray buffer index {idx} out of bounds") + vortex_panic!("ALPArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -144,7 +144,7 @@ impl VTable for ALP { let encoded_ptype = match &dtype { DType::Primitive(PType::F32, n) => DType::Primitive(PType::I32, *n), DType::Primitive(PType::F64, n) => DType::Primitive(PType::I64, *n), - d => vortex_bail!(MismatchedTypes: "expected type: f32 or f64 but instead got {}", d), + d => vortex_bail!("expected type: f32 or f64 but instead got {}", d), }; let encoded = children.get(0, &encoded_ptype, len)?; @@ -275,7 +275,7 @@ impl ALPData { encoded.dtype(), DType::Primitive(PType::I32 | PType::I64, _) ), - MismatchedTypes: "ALP encoded ints have invalid DType {}", + "ALP encoded ints have invalid DType {}", encoded.dtype(), ); @@ -284,15 +284,15 @@ impl ALPData { let Exponents { e, f } = exponents; match encoded.dtype().as_ptype() { PType::I32 => { - vortex_ensure!(exponents.e <= f32::MAX_EXPONENT, InvalidArgument: "e out of bounds: {e}"); - vortex_ensure!(exponents.f <= f32::MAX_EXPONENT, InvalidArgument: "f out of bounds: {f}"); + vortex_ensure!(exponents.e <= f32::MAX_EXPONENT, "e out of bounds: {e}"); + vortex_ensure!(exponents.f <= f32::MAX_EXPONENT, "f out of bounds: {f}"); if let Some(patches) = patches { Self::validate_patches::(patches, encoded)?; } } PType::I64 => { - vortex_ensure!(e <= f64::MAX_EXPONENT, InvalidArgument: "e out of bounds: {e}"); - vortex_ensure!(f <= f64::MAX_EXPONENT, InvalidArgument: "f out of bounds: {f}"); + vortex_ensure!(e <= f64::MAX_EXPONENT, "e out of bounds: {e}"); + vortex_ensure!(f <= f64::MAX_EXPONENT, "f out of bounds: {f}"); if let Some(patches) = patches { Self::validate_patches::(patches, encoded)?; @@ -303,7 +303,7 @@ impl ALPData { // Validate patches if let Some(patches) = patches { - vortex_ensure_eq!(patches.array_len(), encoded.len(), InvalidArgument); + vortex_ensure_eq!(patches.array_len(), encoded.len()); // Verify that the patches DType are of the proper DType. } @@ -320,7 +320,7 @@ impl ALPData { Ok(DType::Primitive(PType::F64, *nullability)) } _ => { - vortex_bail!(MismatchedTypes: "ALP encoded ints have invalid DType {}", encoded.dtype(),) + vortex_bail!("ALP encoded ints have invalid DType {}", encoded.dtype(),) } } } @@ -330,10 +330,10 @@ impl ALPData { patches: &Patches, encoded: &ArrayRef, ) -> VortexResult<()> { - vortex_ensure_eq!(patches.array_len(), encoded.len(), InvalidArgument); + vortex_ensure_eq!(patches.array_len(), encoded.len()); let expected_type = DType::Primitive(T::PTYPE, encoded.dtype().nullability()); - vortex_ensure_eq!(patches.dtype(), &expected_type, MismatchedTypes); + vortex_ensure_eq!(patches.dtype(), &expected_type); Ok(()) } @@ -447,11 +447,11 @@ fn validate_parts( ) -> VortexResult<()> { let logical_dtype = ALPData::logical_dtype(encoded)?; ALPData::validate_components(encoded, exponents, patches.as_ref())?; - vortex_ensure_eq!(encoded.len(), len, InvalidArgument: "ALP encoded len must match outer len"); + vortex_ensure_eq!(encoded.len(), len, "ALP encoded len must match outer len"); vortex_ensure_eq!( &logical_dtype, dtype, - MismatchedTypes: "ALP dtype does not match encoded logical dtype" + "ALP dtype does not match encoded logical dtype" ); Ok(()) } diff --git a/encodings/alp/src/alp/compress.rs b/encodings/alp/src/alp/compress.rs index 5d510159ed7..024c95f82e3 100644 --- a/encodings/alp/src/alp/compress.rs +++ b/encodings/alp/src/alp/compress.rs @@ -39,7 +39,7 @@ macro_rules! match_each_alp_float_ptype { type $enc = f64; $body } - _ => vortex_panic!(MismatchedTypes: "ALP can only encode f32 and f64, got {}", ptype), + _ => vortex_panic!("ALP can only encode f32 and f64, got {}", ptype), } }}; } @@ -52,7 +52,7 @@ pub fn alp_encode( let (exponents, encoded, patches) = match parray.ptype() { PType::F32 => alp_encode_components_typed::(parray, exponents, ctx)?, PType::F64 => alp_encode_components_typed::(parray, exponents, ctx)?, - _ => vortex_bail!(MismatchedTypes: "ALP can only encode f32 and f64"), + _ => vortex_bail!("ALP can only encode f32 and f64"), }; // SAFETY: alp_encode_components_typed must return well-formed components diff --git a/encodings/alp/src/alp/compute/compare.rs b/encodings/alp/src/alp/compute/compare.rs index 9921cf731c2..457aacee172 100644 --- a/encodings/alp/src/alp/compute/compare.rs +++ b/encodings/alp/src/alp/compute/compare.rs @@ -45,7 +45,7 @@ impl CompareKernel for ALP { if let Some(const_scalar) = rhs.as_constant() { let pscalar = const_scalar.as_primitive_opt().ok_or_else(|| { vortex_err!( - InvalidArgument: "ALP Compare RHS had the wrong type {}, expected {}", + "ALP Compare RHS had the wrong type {}, expected {}", const_scalar, const_scalar.dtype() ) @@ -55,7 +55,7 @@ impl CompareKernel for ALP { match pscalar.typed_value::() { Some(value) => return alp_scalar_compare(lhs, value, operator), None => vortex_bail!( - InvalidArgument: "Failed to convert scalar {:?} to ALP type {:?}", + "Failed to convert scalar {:?} to ALP type {:?}", pscalar, pscalar.ptype() ), diff --git a/encodings/alp/src/alp/ops.rs b/encodings/alp/src/alp/ops.rs index b374a052ff4..db6f89ecf91 100644 --- a/encodings/alp/src/alp/ops.rs +++ b/encodings/alp/src/alp/ops.rs @@ -36,7 +36,7 @@ impl OperationsVTable for ALP { let encoded_val = state .slot(ALPSlots::ENCODED)? - .ok_or_else(|| vortex_err!(InvalidArgument: "ALP encoded slot is missing"))? + .ok_or_else(|| vortex_err!("ALP encoded slot is missing"))? .execute_scalar(index, ctx)?; Ok(match_each_alp_float_ptype!(array.dtype().as_ptype(), |T| { diff --git a/encodings/alp/src/alp/plugin.rs b/encodings/alp/src/alp/plugin.rs index 738bec6f919..b72893efb32 100644 --- a/encodings/alp/src/alp/plugin.rs +++ b/encodings/alp/src/alp/plugin.rs @@ -55,7 +55,7 @@ impl ArrayPlugin for ALPPatchedPlugin { vortex_ensure_eq!( parts.serialized_id, self.id(), - Serde: "ALP plugin does not recognize serialized ID" + "ALP plugin does not recognize serialized ID" ); let alp_array = Array::::try_from_parts(ArrayVTable::deserialize( &ALP, @@ -66,7 +66,7 @@ impl ArrayPlugin for ALPPatchedPlugin { parts.children, session, )?) - .map_err(|_| vortex_err!(Serde: "ALP plugin should only deserialize vortex.alp"))?; + .map_err(|_| vortex_err!("ALP plugin should only deserialize vortex.alp"))?; // Check if there are interior patches to externalize. let Some(patches) = alp_array.patches() else { @@ -164,13 +164,15 @@ mod tests { assert_arrays_eq!(deserialized, parray, &mut SESSION.create_execution_ctx()); - let patched: PatchedArray = deserialized.try_downcast().map_err( - |a| vortex_err!(MismatchedTypes: "Expected Patched, got {}", a.encoding_id()), - )?; + let patched: PatchedArray = deserialized + .try_downcast() + .map_err(|a| vortex_err!("Expected Patched, got {}", a.encoding_id()))?; - let inner_alp: ALPArray = patched.inner().clone().try_downcast().map_err( - |a| vortex_err!(MismatchedTypes: "Expected inner ALP, got {}", a.encoding_id()), - )?; + let inner_alp: ALPArray = patched + .inner() + .clone() + .try_downcast() + .map_err(|a| vortex_err!("Expected inner ALP, got {}", a.encoding_id()))?; assert!( inner_alp.patches().is_none(), @@ -216,9 +218,9 @@ mod tests { assert_arrays_eq!(deserialized, parray, &mut SESSION.create_execution_ctx()); - let result = deserialized.try_downcast::().map_err( - |a| vortex_err!(Serde: "Expected deserialized ALP, got {}", a.encoding_id()), - )?; + let result = deserialized + .try_downcast::() + .map_err(|a| vortex_err!("Expected deserialized ALP, got {}", a.encoding_id()))?; assert!(result.patches().is_none(), "Result should not have patches"); diff --git a/encodings/alp/src/alp_rd/array.rs b/encodings/alp/src/alp_rd/array.rs index fe5c0b8d340..71a450585a6 100644 --- a/encodings/alp/src/alp_rd/array.rs +++ b/encodings/alp/src/alp_rd/array.rs @@ -122,7 +122,7 @@ impl VTable for ALPRD { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ALPRDArray buffer index {idx} out of bounds") + vortex_panic!("ALPRDArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -174,7 +174,7 @@ impl VTable for ALPRD { let metadata = ALPRDMetadata::decode(metadata)?; if children.len() < 2 { vortex_bail!( - InvalidArgument: "Expected at least 2 children for ALPRD encoding, found {}", + "Expected at least 2 children for ALPRD encoding, found {}", children.len() ); } @@ -185,9 +185,8 @@ impl VTable for ALPRD { [0..metadata.dict_len as usize] .iter() .map(|&i| { - u16::try_from(i).map_err( - |_| vortex_err!(Overflow: "left_parts_dictionary code {i} does not fit in u16"), - ) + u16::try_from(i) + .map_err(|_| vortex_err!("left_parts_dictionary code {i} does not fit in u16")) }) .try_collect()?; @@ -198,7 +197,7 @@ impl VTable for ALPRD { DType::Primitive(PType::F64, _) => { DType::Primitive(PType::U64, Nullability::NonNullable) } - _ => vortex_bail!(MismatchedTypes: "Expected f32 or f64 dtype, got {:?}", dtype), + _ => vortex_bail!("Expected f32 or f64 dtype, got {:?}", dtype), }; let right_parts = children.get(1, &right_parts_dtype, len)?; @@ -224,7 +223,7 @@ impl VTable for ALPRD { left_parts_dictionary, u8::try_from(metadata.right_bit_width).map_err(|_| { vortex_err!( - Overflow: "right_bit_width {} out of u8 range", + "right_bit_width {} out of u8 range", metadata.right_bit_width ) })?, @@ -478,18 +477,18 @@ fn validate_parts( left_parts_patches: Option<&Patches>, ) -> VortexResult<()> { if !dtype.is_float() { - vortex_bail!(InvalidArgument: "ALPRDArray given invalid DType ({dtype})"); + vortex_bail!("ALPRDArray given invalid DType ({dtype})"); } - vortex_ensure_eq!(left_parts.len(), len, InvalidArgument); - vortex_ensure_eq!(right_parts.len(), len, InvalidArgument); + vortex_ensure_eq!(left_parts.len(), len); + vortex_ensure_eq!(right_parts.len(), len); if !left_parts.dtype().is_unsigned_int() { - vortex_bail!(InvalidArgument: "left_parts dtype must be uint"); + vortex_bail!("left_parts dtype must be uint"); } if dtype.is_nullable() != left_parts.dtype().is_nullable() { vortex_bail!( - InvalidArgument: "ALPRDArray dtype nullability ({}) must match left_parts dtype nullability ({})", + "ALPRDArray dtype nullability ({}) must match left_parts dtype nullability ({})", dtype, left_parts.dtype() ); @@ -498,16 +497,12 @@ fn validate_parts( let expected_right_parts_dtype = match dtype { DType::Primitive(PType::F32, _) => DType::Primitive(PType::U32, Nullability::NonNullable), DType::Primitive(PType::F64, _) => DType::Primitive(PType::U64, Nullability::NonNullable), - _ => vortex_bail!(MismatchedTypes: "Expected f32 or f64 dtype, got {:?}", dtype), + _ => vortex_bail!("Expected f32 or f64 dtype, got {:?}", dtype), }; - vortex_ensure_eq!( - right_parts.dtype(), - &expected_right_parts_dtype, - MismatchedTypes - ); + vortex_ensure_eq!(right_parts.dtype(), &expected_right_parts_dtype); if let Some(patches) = left_parts_patches { - vortex_ensure_eq!(patches.array_len(), len, InvalidArgument); + vortex_ensure_eq!(patches.array_len(), len); // Left-parts exceptions are always all-valid and are stored as the non-nullable left-parts // dtype. Requiring that exact dtype (rather than ignoring nullability) means each // construction path must produce correct patches, removing the need to normalize them. @@ -516,7 +511,7 @@ fn validate_parts( vortex_ensure_eq!( patches.dtype(), &expected, - MismatchedTypes: "patches dtype must be the non-nullable left_parts dtype" + "patches dtype must be the non-nullable left_parts dtype" ); } diff --git a/encodings/alp/src/alp_rd/mod.rs b/encodings/alp/src/alp_rd/mod.rs index ec663339f38..8b0cd8f2f39 100644 --- a/encodings/alp/src/alp_rd/mod.rs +++ b/encodings/alp/src/alp_rd/mod.rs @@ -150,7 +150,7 @@ where T::UINT: NativePType, { if left_parts.len() != right_parts.len() { - vortex_panic!(AssertionFailed: "alp_rd_decode: left_parts.len != right_parts.len"); + vortex_panic!("alp_rd_decode: left_parts.len != right_parts.len"); } if let Some(patches) = left_parts_patches { diff --git a/encodings/bytebool/src/array.rs b/encodings/bytebool/src/array.rs index 14a052fbe6e..9413cbaa8b4 100644 --- a/encodings/bytebool/src/array.rs +++ b/encodings/bytebool/src/array.rs @@ -85,14 +85,14 @@ impl VTable for ByteBool { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.buffer().clone(), - _ => vortex_panic!(OutOfBounds: "ByteBoolArray buffer index {idx} out of bounds"), + _ => vortex_panic!("ByteBoolArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("values".to_string()), - _ => vortex_panic!(OutOfBounds: "ByteBoolArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!("ByteBoolArray buffer_name index {idx} out of bounds"), } } @@ -101,7 +101,7 @@ impl VTable for ByteBool { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 1); let data = ByteBoolData::new(buffers[0].clone()); Ok(ArrayParts::new( self.clone(), @@ -130,7 +130,7 @@ impl VTable for ByteBool { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "ByteBoolArray expects empty metadata, got {} bytes", + "ByteBoolArray expects empty metadata, got {} bytes", metadata.len() ); } @@ -140,11 +140,11 @@ impl VTable for ByteBool { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "Expected 0 or 1 child, got {}", children.len()); + vortex_bail!("Expected 0 or 1 child, got {}", children.len()); }; if buffers.len() != 1 { - vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); + vortex_bail!("Expected 1 buffer, got {}", buffers.len()); } let buffer = buffers[0].clone(); @@ -261,10 +261,10 @@ impl ByteBoolData { len: usize, ) -> VortexResult<()> { let expected_dtype = DType::Bool(validity.nullability()); - vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes); - vortex_ensure_eq!(buffer.len(), len, InvalidArgument); + vortex_ensure_eq!(dtype, &expected_dtype); + vortex_ensure_eq!(buffer.len(), len); if let Some(vlen) = validity.maybe_len() { - vortex_ensure_eq!(vlen, len, InvalidArgument); + vortex_ensure_eq!(vlen, len); } Ok(()) } diff --git a/encodings/bytebool/src/compute.rs b/encodings/bytebool/src/compute.rs index 9b8fb0ce979..6a92a039ec8 100644 --- a/encodings/bytebool/src/compute.rs +++ b/encodings/bytebool/src/compute.rs @@ -129,7 +129,7 @@ impl BooleanKernel for ByteBool { let rhs = rhs .scalar() .as_bool_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))?; + .ok_or_else(|| vortex_err!("expected boolean scalar"))?; return kleene_boolean_buffer_scalar( lhs_values, lhs.validity()?, @@ -280,9 +280,7 @@ mod tests { let and_result = ::boolean(lhs.as_view(), &rhs, Operator::And, &mut ctx)? - .ok_or_else( - || vortex_err!(AssertionFailed: "ByteBool should handle ByteBool boolean AND"), - )?; + .ok_or_else(|| vortex_err!("ByteBool should handle ByteBool boolean AND"))?; assert_arrays_eq!( and_result, BoolArray::from_iter([Some(false), None, None, Some(false), None]), @@ -291,9 +289,7 @@ mod tests { let or_result = ::boolean(lhs.as_view(), &rhs, Operator::Or, &mut ctx)? - .ok_or_else( - || vortex_err!(AssertionFailed: "ByteBool should handle ByteBool boolean OR"), - )?; + .ok_or_else(|| vortex_err!("ByteBool should handle ByteBool boolean OR"))?; assert_arrays_eq!( or_result, BoolArray::from_iter([None, Some(true), Some(true), Some(false), None]), diff --git a/encodings/datetime-parts/src/array.rs b/encodings/datetime-parts/src/array.rs index 429bd602e8c..8511073ba9d 100644 --- a/encodings/datetime-parts/src/array.rs +++ b/encodings/datetime-parts/src/array.rs @@ -74,17 +74,17 @@ pub struct DateTimePartsMetadata { impl DateTimePartsMetadata { pub fn get_days_ptype(&self) -> VortexResult { PType::try_from(self.days_ptype) - .map_err(|_| vortex_err!(InvalidArgument: "Invalid PType {}", self.days_ptype)) + .map_err(|_| vortex_err!("Invalid PType {}", self.days_ptype)) } pub fn get_seconds_ptype(&self) -> VortexResult { PType::try_from(self.seconds_ptype) - .map_err(|_| vortex_err!(InvalidArgument: "Invalid PType {}", self.seconds_ptype)) + .map_err(|_| vortex_err!("Invalid PType {}", self.seconds_ptype)) } pub fn get_subseconds_ptype(&self) -> VortexResult { PType::try_from(self.subseconds_ptype) - .map_err(|_| vortex_err!(InvalidArgument: "Invalid PType {}", self.subseconds_ptype)) + .map_err(|_| vortex_err!("Invalid PType {}", self.subseconds_ptype)) } } @@ -115,11 +115,11 @@ impl VTable for DateTimeParts { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "DateTimePartsArray buffer index {idx} out of bounds") + vortex_panic!("DateTimePartsArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "DateTimePartsArray buffer_name index {idx} out of bounds") + vortex_panic!("DateTimePartsArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -156,7 +156,7 @@ impl VTable for DateTimeParts { let metadata = DateTimePartsMetadata::decode(metadata)?; if children.len() != 3 { vortex_bail!( - InvalidArgument: "Expected 3 children for datetime-parts encoding, found {}", + "Expected 3 children for datetime-parts encoding, found {}", children.len() ) } @@ -313,25 +313,31 @@ impl DateTimePartsData { subseconds: &ArrayRef, len: usize, ) -> VortexResult<()> { - vortex_ensure_eq!(days.len(), len, InvalidArgument); + vortex_ensure_eq!(days.len(), len); if !days.dtype().is_int() || (dtype.is_nullable() != days.dtype().is_nullable()) { vortex_bail!( - MismatchedTypes: "Expected integer with nullability {}, got {}", + "Expected integer with nullability {}, got {}", dtype.is_nullable(), days.dtype() ); } if !seconds.dtype().is_int() || seconds.dtype().is_nullable() { - vortex_bail!(MismatchedTypes: "expected type: non-nullable integer but instead got {}", seconds.dtype()); + vortex_bail!( + "expected type: non-nullable integer but instead got {}", + seconds.dtype() + ); } if !subseconds.dtype().is_int() || subseconds.dtype().is_nullable() { - vortex_bail!(MismatchedTypes: "expected type: non-nullable integer but instead got {}", subseconds.dtype()); + vortex_bail!( + "expected type: non-nullable integer but instead got {}", + subseconds.dtype() + ); } if len != seconds.len() || len != subseconds.len() { vortex_bail!( - MismatchedTypes: "Mismatched lengths {} {} {}", + "Mismatched lengths {} {} {}", days.len(), seconds.len(), subseconds.len() diff --git a/encodings/datetime-parts/src/canonical.rs b/encodings/datetime-parts/src/canonical.rs index 2f854ffa6a2..b613bd229cd 100644 --- a/encodings/datetime-parts/src/canonical.rs +++ b/encodings/datetime-parts/src/canonical.rs @@ -41,11 +41,11 @@ pub fn decode_to_temporal( ctx: &mut ExecutionCtx, ) -> VortexResult { let DType::Extension(ext) = dtype else { - vortex_panic!(MismatchedTypes: "expected dtype to be DType::Extension variant") + vortex_panic!("expected dtype to be DType::Extension variant") }; let Some(options) = ext.metadata_opt::() else { - vortex_panic!(Serde: "must decode TemporalMetadata from extension metadata"); + vortex_panic!("must decode TemporalMetadata from extension metadata"); }; let divisor = match options.unit { @@ -53,7 +53,7 @@ pub fn decode_to_temporal( TimeUnit::Microseconds => 1_000_000, TimeUnit::Milliseconds => 1_000, TimeUnit::Seconds => 1, - TimeUnit::Days => vortex_panic!(InvalidArgument: "cannot decode into TimeUnit::D"), + TimeUnit::Days => vortex_panic!("cannot decode into TimeUnit::D"), }; let days = parts.days.as_::(); diff --git a/encodings/datetime-parts/src/compress.rs b/encodings/datetime-parts/src/compress.rs index 8c5b7410368..d84f4b6be91 100644 --- a/encodings/datetime-parts/src/compress.rs +++ b/encodings/datetime-parts/src/compress.rs @@ -34,7 +34,7 @@ pub struct TemporalParts { pub fn split_temporal(array: TemporalArray, ctx: &mut ExecutionCtx) -> VortexResult { let time_unit = array.temporal_metadata().time_unit(); if matches!(time_unit, TimeUnit::Days) { - vortex_bail!(NotImplemented: "Cannot handle day-level data"); + vortex_bail!("Cannot handle day-level data"); } let temporal_values = array diff --git a/encodings/datetime-parts/src/compute/take.rs b/encodings/datetime-parts/src/compute/take.rs index 23deaa616da..7ca56f55b97 100644 --- a/encodings/datetime-parts/src/compute/take.rs +++ b/encodings/datetime-parts/src/compute/take.rs @@ -49,16 +49,16 @@ fn take_datetime_parts( // If they became nullable due to nullable indices, we need to fill nulls. // But first, we need to check that the types are consistent. if !taken_days.dtype().is_nullable() { - vortex_panic!(MismatchedTypes: "Mismatched types: days is not nullable, seconds is nullable"); + vortex_panic!("Mismatched types: days is not nullable, seconds is nullable"); } if !taken_seconds.dtype().is_nullable() { - vortex_panic!(MismatchedTypes: "Mismatched types: seconds is not nullable, days is nullable"); + vortex_panic!("Mismatched types: seconds is not nullable, days is nullable"); } if !taken_subseconds.dtype().is_nullable() { - vortex_panic!(MismatchedTypes: "Mismatched types: subseconds is not nullable, days & seconds are nullable"); + vortex_panic!("Mismatched types: subseconds is not nullable, days & seconds are nullable"); } if !indices.dtype().is_nullable() { - vortex_panic!(MismatchedTypes: "Mismatched types: indices are not nullable, days & seconds are nullable"); + vortex_panic!("Mismatched types: indices are not nullable, days & seconds are nullable"); } let seconds_fill = array diff --git a/encodings/datetime-parts/src/ops.rs b/encodings/datetime-parts/src/ops.rs index ad1aa48606e..b75b4378b27 100644 --- a/encodings/datetime-parts/src/ops.rs +++ b/encodings/datetime-parts/src/ops.rs @@ -29,13 +29,13 @@ impl OperationsVTable for DateTimeParts { let array = state.array(); let DType::Extension(ext) = array.dtype().clone() else { vortex_panic!( - MismatchedTypes: "DateTimePartsArray must have extension dtype, found {}", + "DateTimePartsArray must have extension dtype, found {}", array.dtype() ); }; let Some(options) = ext.metadata_opt::() else { - vortex_panic!(Serde: "must decode TemporalMetadata from extension metadata"); + vortex_panic!("must decode TemporalMetadata from extension metadata"); }; if !state.is_valid(index, ctx)? { @@ -87,7 +87,7 @@ fn part_at( ) -> VortexResult { Ok(state .slot(slot)? - .ok_or_else(|| vortex_err!(InvalidArgument: "DateTimeParts {name} slot is missing"))? + .ok_or_else(|| vortex_err!("DateTimeParts {name} slot is missing"))? .execute_scalar(index, ctx)? .as_primitive() .as_::() diff --git a/encodings/datetime-parts/src/timestamp.rs b/encodings/datetime-parts/src/timestamp.rs index 07a9888fb21..a9e9bcc3322 100644 --- a/encodings/datetime-parts/src/timestamp.rs +++ b/encodings/datetime-parts/src/timestamp.rs @@ -37,7 +37,7 @@ pub fn split(timestamp: i64, time_unit: TimeUnit) -> VortexResult split_with_divisor::<1_000_000>(timestamp), TimeUnit::Milliseconds => split_with_divisor::<1_000>(timestamp), TimeUnit::Seconds => split_with_divisor::<1>(timestamp), - TimeUnit::Days => vortex_bail!(NotImplemented: "Cannot handle day-level data"), + TimeUnit::Days => vortex_bail!("Cannot handle day-level data"), }) } @@ -71,7 +71,7 @@ pub fn combine(ts_parts: TimestampParts, time_unit: TimeUnit) -> i64 { TimeUnit::Microseconds => 1_000_000, TimeUnit::Milliseconds => 1_000, TimeUnit::Seconds => 1, - TimeUnit::Days => vortex_panic!(NotImplemented: "Cannot handle day-level data"), + TimeUnit::Days => vortex_panic!("Cannot handle day-level data"), }; ts_parts.days as i64 * SECONDS_PER_DAY * divisor diff --git a/encodings/decimal-byte-parts/benches/common/mod.rs b/encodings/decimal-byte-parts/benches/common/mod.rs index dc8044702d4..197c518b722 100644 --- a/encodings/decimal-byte-parts/benches/common/mod.rs +++ b/encodings/decimal-byte-parts/benches/common/mod.rs @@ -85,7 +85,7 @@ pub(super) mod arrays { DecimalType::I256 => { DecimalArray::new(i256_values(len), DecimalDType::new(76, 2), validity) } - _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), } } } diff --git a/encodings/decimal-byte-parts/benches/dbp_assemble.rs b/encodings/decimal-byte-parts/benches/dbp_assemble.rs index ee2dcf1cdc8..33ab5efbf2a 100644 --- a/encodings/decimal-byte-parts/benches/dbp_assemble.rs +++ b/encodings/decimal-byte-parts/benches/dbp_assemble.rs @@ -62,7 +62,7 @@ fn dbp_assemble_kernel(bencher: Bencher, (values_type, len): (DecimalType, usize ) }); } - _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), } } @@ -96,7 +96,7 @@ fn dbp_assemble_kernel_narrow_msp(bencher: Bencher, (values_type, len): (Decimal ) }); } - _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), } } @@ -154,7 +154,7 @@ mod arrays { buffer![u32::MAX; len].into_array(), ], ), - _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), }; bench_parts( bencher, diff --git a/encodings/decimal-byte-parts/benches/dbp_split.rs b/encodings/decimal-byte-parts/benches/dbp_split.rs index 3bdf5dddd23..933eb31a519 100644 --- a/encodings/decimal-byte-parts/benches/dbp_split.rs +++ b/encodings/decimal-byte-parts/benches/dbp_split.rs @@ -68,7 +68,7 @@ fn bench_split(bencher: Bencher, values_type: DecimalType, len: usize, validity: ) }); } - _ => vortex_panic!(NotImplemented: "unsupported benchmark storage type: {values_type}"), + _ => vortex_panic!("unsupported benchmark storage type: {values_type}"), } } diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs index 212306d8a69..7b60b349023 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/array.rs @@ -95,26 +95,26 @@ impl DecimalBytePartsData { len: usize, ) -> VortexResult<()> { if !msp.dtype().is_signed_int() { - vortex_bail!(InvalidArgument: "msp must be a signed integer array") + vortex_bail!("msp must be a signed integer array") } let expected_dtype = DType::Decimal(decimal_dtype, msp.dtype().nullability()); - vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes); - vortex_ensure_eq!(msp.len(), len, InvalidArgument); + vortex_ensure_eq!(dtype, &expected_dtype); + vortex_ensure_eq!(msp.len(), len); let lower_part_count = lower_parts.len(); vortex_ensure!( lower_part_count <= MAX_LOWER_PARTS, - InvalidArgument: "at most {MAX_LOWER_PARTS} lower parts are supported, got {lower_part_count}" + "at most {MAX_LOWER_PARTS} lower parts are supported, got {lower_part_count}" ); for (idx, part) in lower_parts.enumerate() { vortex_ensure!( part.dtype().is_unsigned_int() && !part.dtype().is_nullable(), - MismatchedTypes: "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", + "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", part.dtype() ); - vortex_ensure_eq!(part.len(), len, InvalidArgument: "lower part {idx} length mismatch"); + vortex_ensure_eq!(part.len(), len, "lower part {idx} length mismatch"); } Ok(()) } @@ -211,18 +211,18 @@ impl VTable for DecimalByteParts { slots: &[Option], ) -> VortexResult<()> { let Some(decimal_dtype) = dtype.as_decimal_opt() else { - vortex_bail!(MismatchedTypes: "expected decimal dtype, got {}", dtype) + vortex_bail!("expected decimal dtype, got {}", dtype) }; let min_slots = DecimalBytePartsSlots::FIXED_COUNT; let max_slots = min_slots + MAX_LOWER_PARTS; vortex_ensure!( (min_slots..=max_slots).contains(&slots.len()), - InvalidArgument: "expected {min_slots}..={max_slots} slots, got {}", + "expected {min_slots}..={max_slots} slots, got {}", slots.len() ); for (idx, slot) in slots.iter().enumerate() { - vortex_ensure!(slot.is_some(), InvalidArgument: "missing required slot {idx}"); + vortex_ensure!(slot.is_some(), "missing required slot {idx}"); } let slots = DecimalBytePartsSlotsView::from_slots(slots); @@ -240,11 +240,11 @@ impl VTable for DecimalByteParts { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "DecimalBytePartsArray buffer index {idx} out of bounds") + vortex_panic!("DecimalBytePartsArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "DecimalBytePartsArray buffer_name index {idx} out of bounds") + vortex_panic!("DecimalBytePartsArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -259,7 +259,7 @@ impl VTable for DecimalByteParts { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!(Serde: "DecimalByteParts serialization requires DecimalBytePartsPlugin") + vortex_bail!("DecimalByteParts serialization requires DecimalBytePartsPlugin") } fn deserialize( @@ -271,7 +271,7 @@ impl VTable for DecimalByteParts { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "DecimalByteParts deserialization requires DecimalBytePartsPlugin") + vortex_bail!("DecimalByteParts deserialization requires DecimalBytePartsPlugin") } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { @@ -392,7 +392,7 @@ impl OperationsVTable for DecimalByteParts { DecimalValue::I256(assemble_wide_decimal_value(msp, [*first, *second, *third])) } _ => vortex_bail!( - InvalidArgument: "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", + "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", lower_parts.len() ), }; diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs index 54982f7b252..1cdf27c15bd 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/assemble.rs @@ -52,7 +52,7 @@ pub fn assemble_decimal( ) -> VortexResult { vortex_ensure!( msp.dtype().is_signed_int(), - MismatchedTypes: "MSP must have a signed integer dtype" + "MSP must have a signed integer dtype" ); let validity = msp.validity()?; @@ -63,17 +63,17 @@ pub fn assemble_decimal( vortex_ensure!( lower_parts.len() <= MAX_LOWER_PARTS, - InvalidArgument: "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", + "at most {MAX_LOWER_PARTS} lower parts are supported, got {}", lower_parts.len() ); let len = msp.len(); for (idx, part) in lower_parts.iter().enumerate() { vortex_ensure!( part.dtype().is_unsigned_int() && !part.dtype().is_nullable(), - MismatchedTypes: "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", + "lower part {idx} must have a non-nullable unsigned integer dtype, got {}", part.dtype() ); - vortex_ensure_eq!(part.len(), len, InvalidArgument: "lower part {idx} length mismatch"); + vortex_ensure_eq!(part.len(), len, "lower part {idx} length mismatch"); } assemble_wide_decimal_from_arrays(msp, lower_parts, validity, decimal_dtype, exec_ctx) @@ -155,7 +155,7 @@ fn assemble_wide_decimal_from_arrays( ) .into_array(), _ => { - vortex_bail!(InvalidArgument: "expected between one and {MAX_LOWER_PARTS} lower parts") + vortex_bail!("expected between one and {MAX_LOWER_PARTS} lower parts") } } })) diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs index e5e243546ce..3896cd51c96 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/mod.rs @@ -66,7 +66,7 @@ impl ArrayPlugin for DecimalBytePartsPlugin { ) -> VortexResult> { let view = array.as_opt::().ok_or_else(|| { vortex_err!( - Serde: "DecimalByteParts plugin cannot serialize {}", + "DecimalByteParts plugin cannot serialize {}", array.encoding_id() ) })?; @@ -89,7 +89,7 @@ impl ArrayPlugin for DecimalBytePartsPlugin { v2::deserialize(parts)? } else { vortex_bail!( - Serde: "DecimalByteParts plugin does not recognize serialized ID {}", + "DecimalByteParts plugin does not recognize serialized ID {}", parts.serialized_id ) }; diff --git a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs index 9bca0ca88c7..99f3614e2a4 100644 --- a/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs +++ b/encodings/decimal-byte-parts/src/decimal_byte_parts/plugin/v1.rs @@ -35,7 +35,7 @@ pub(super) fn serialize( ) -> VortexResult { vortex_ensure!( array.lower_parts().is_empty(), - Serde: "v1 must not carry lower parts" + "v1 must not carry lower parts" ); let msp = array.msp(); let metadata = DecimalBytePartsMetadata { @@ -55,23 +55,23 @@ pub(super) fn deserialize(parts: ArrayDeserialization<'_>) -> VortexResult) -> VortexResult>(len: usize, child: Child) -> Array } }; let FoRReferences::Blocked(references) = for_array.references() else { - vortex_panic!(AssertionFailed: "every chunk has its own reference"); + vortex_panic!("every chunk has its own reference"); }; FoR::try_new_chunked(packed.into_array(), references.clone(), 0) .unwrap() diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs index 77e503d70ea..7aa088f3bac 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/blocked.rs @@ -94,7 +94,7 @@ pub fn bitpack_encode_blocked( let num_blocks = array.len().div_ceil(FL_CHUNK_SIZE); vortex_ensure!( bit_widths.len() == num_blocks, - InvalidArgument: "Expected {num_blocks} bit widths, got {}", + "Expected {num_blocks} bit widths, got {}", bit_widths.len() ); validate_bit_widths(bit_widths, array.ptype())?; @@ -133,13 +133,13 @@ fn validate_bit_widths(bit_widths: &[u8], ptype: PType) -> VortexResult<()> { let bit_width = usize::from(bit_width); vortex_ensure!( bit_width <= max_bit_width, - InvalidArgument: "Bit widths must be at most {max_bit_width} for {ptype}" + "Bit widths must be at most {max_bit_width} for {ptype}" ); has_packed_block |= bit_width < max_bit_width; } vortex_ensure!( bit_widths.is_empty() || has_packed_block, - InvalidArgument: "Cannot pack: all blocks use the native bit width {max_bit_width}" + "Cannot pack: all blocks use the native bit width {max_bit_width}" ); Ok(()) } @@ -343,7 +343,6 @@ mod tests { use vortex_array::assert_arrays_eq; use vortex_array::validity::Validity; use vortex_buffer::Buffer; - use vortex_error::VortexErrorKind; use vortex_error::vortex_bail; use vortex_error::vortex_err; use vortex_session::VortexSession; @@ -366,7 +365,7 @@ mod tests { ctx: &mut ExecutionCtx, ) -> VortexResult { let BitWidthsView::Blocked(offsets) = array.bit_widths() else { - vortex_bail!(AssertionFailed: "expected block offsets"); + vortex_bail!("expected block offsets"); }; offsets.clone().execute::(ctx) } @@ -445,7 +444,7 @@ mod tests { let patches = array .patches() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; + .ok_or_else(|| vortex_err!("expected patches"))?; assert_arrays_eq!( patches.indices().clone(), PrimitiveArray::from_iter([10u16, 20, 1029]), @@ -459,7 +458,7 @@ mod tests { let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? + .ok_or_else(|| vortex_err!("expected chunk offsets"))? .clone(); assert_arrays_eq!( chunk_offsets, @@ -482,7 +481,7 @@ mod tests { assert_eq!(array.packed().len(), 0); let patches = array .patches() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; + .ok_or_else(|| vortex_err!("expected patches"))?; assert_eq!(patches.num_patches(), 10); Ok(()) } @@ -496,7 +495,7 @@ mod tests { )?; let BitWidthsView::Blocked(offsets) = array.bit_widths() else { - vortex_bail!(AssertionFailed: "expected block offsets"); + vortex_bail!("expected block offsets"); }; assert!(offsets.is::()); assert_arrays_eq!( @@ -542,37 +541,43 @@ mod tests { } #[rstest] - #[case::negative(PrimitiveArray::from_iter(-5i64..5))] - #[case::float(PrimitiveArray::from_iter([1.0f32, 2.0]))] - fn encode_blocked_rejects_invalid_values(#[case] array: PrimitiveArray) { + #[case::negative( + PrimitiveArray::from_iter(-5i64..5), + "cannot bitpack array containing negative integers" + )] + #[case::float(PrimitiveArray::from_iter([1.0f32, 2.0]), "cannot bitpack f32 array")] + fn encode_blocked_rejects_invalid_values( + #[case] array: PrimitiveArray, + #[case] expected: &str, + ) { let mut ctx = SESSION.create_execution_ctx(); - assert_eq!( - bitpack_blocked_to_best_bit_widths(&array, &mut ctx) - .unwrap_err() - .kind(), - VortexErrorKind::InvalidArgument - ); - assert_eq!( - BitPackedData::encode_blocked(&array.into_array(), &[1], &mut ctx) - .unwrap_err() - .kind(), - VortexErrorKind::InvalidArgument - ); + let err = bitpack_blocked_to_best_bit_widths(&array, &mut ctx) + .unwrap_err() + .to_string(); + assert!(err.contains(expected), "{err}"); + let err = BitPackedData::encode_blocked(&array.into_array(), &[1], &mut ctx) + .unwrap_err() + .to_string(); + assert!(err.contains(expected), "{err}"); } #[rstest] - #[case::too_few(vec![3])] - #[case::too_many(vec![3, 3, 3])] - #[case::wider_than_type(vec![3, 33])] - fn encode_blocked_rejects_invalid_bit_widths(#[case] bit_widths: Vec) { + #[case::too_few(vec![3], "Expected 2 bit widths, got 1")] + #[case::too_many(vec![3, 3, 3], "Expected 2 bit widths, got 3")] + #[case::wider_than_type(vec![3, 33], "Bit widths must be at most 32 for u32")] + fn encode_blocked_rejects_invalid_bit_widths( + #[case] bit_widths: Vec, + #[case] expected: &str, + ) { let array = PrimitiveArray::from_iter((0..2048u32).map(|i| i % 8)); let err = BitPackedData::encode_blocked( &array.into_array(), &bit_widths, &mut SESSION.create_execution_ctx(), ) - .unwrap_err(); - assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); + .unwrap_err() + .to_string(); + assert!(err.contains(expected), "{err}"); } #[test] diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs index b3058f1122e..a20a0d027de 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/global.rs @@ -58,7 +58,7 @@ pub fn bitpack_encode( if bit_width >= array.ptype().bit_width() as u8 { // Nothing we can do vortex_bail!( - InvalidArgument: "Cannot pack - specified bit width {bit_width} >= {}", + "Cannot pack - specified bit width {bit_width} >= {}", array.ptype().bit_width() ) } @@ -353,7 +353,7 @@ pub fn find_best_bit_width(ptype: PType, bit_width_freq: &[usize]) -> VortexResu )] fn best_bit_width(bit_width_freq: &[usize], bytes_per_exception: usize) -> VortexResult { if bit_width_freq.len() > u8::MAX as usize { - vortex_bail!(Overflow: "Too many bit widths"); + vortex_bail!("Too many bit widths"); } let len: usize = bit_width_freq.iter().sum(); @@ -434,7 +434,6 @@ mod test { use vortex_array::builders::ArrayBuilder; use vortex_array::builders::PrimitiveBuilder; use vortex_buffer::Buffer; - use vortex_error::VortexErrorKind; use vortex_error::vortex_err; use vortex_session::VortexSession; @@ -493,8 +492,12 @@ mod test { assert!(array.ptype().is_signed_int()); let err = BitPackedData::encode(&array.into_array(), 1024u32.ilog2() as u8, &mut ctx) - .unwrap_err(); - assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); + .unwrap_err() + .to_string(); + assert!( + err.contains("cannot bitpack array containing negative integers"), + "{err}" + ); } #[test] @@ -536,11 +539,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; + .ok_or_else(|| vortex_err!("expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? + .ok_or_else(|| vortex_err!("expected chunk offsets"))? .clone(); // chunk 0 (0-1023): patches at 100, 200 -> starts at patch index 0 @@ -571,11 +574,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; + .ok_or_else(|| vortex_err!("expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? + .ok_or_else(|| vortex_err!("expected chunk offsets"))? .clone(); assert_arrays_eq!( @@ -602,11 +605,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; + .ok_or_else(|| vortex_err!("expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? + .ok_or_else(|| vortex_err!("expected chunk offsets"))? .clone(); // chunk 0 (0-1023): patches at 100, 200 -> starts at patch index 0 @@ -638,11 +641,11 @@ mod test { let patches = bitpacked .patches() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected patches"))?; + .ok_or_else(|| vortex_err!("expected patches"))?; let chunk_offsets = patches .chunk_offsets() .as_ref() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected chunk offsets"))? + .ok_or_else(|| vortex_err!("expected chunk offsets"))? .clone(); // Single chunk starting at patch index 0. diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/mod.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/mod.rs index b60bf1e6513..70a3cde910b 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_compress/mod.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_compress/mod.rs @@ -33,7 +33,7 @@ fn ensure_non_negative_integers( ) -> VortexResult<()> { vortex_ensure!( array.ptype().is_int(), - InvalidArgument: "cannot bitpack {} array", + "cannot bitpack {} array", array.ptype() ); if array.ptype().is_signed_int() { @@ -41,7 +41,7 @@ fn ensure_non_negative_integers( array.statistics().compute_min::

(ctx).unwrap_or_default() < 0 }); if has_negative_values { - vortex_bail!(InvalidArgument: "cannot bitpack array containing negative integers") + vortex_bail!("cannot bitpack array containing negative integers") } } Ok(()) diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs index 792ee5aa1f3..6dcb3177928 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/blocked.rs @@ -118,7 +118,7 @@ pub(crate) fn execute_block_offsets( let num_blocks = (array.len() + usize::from(array.offset())).div_ceil(FL_CHUNK_SIZE); vortex_ensure!( offsets.len() == num_blocks + 1, - InvalidArgument: "Expected {} block boundaries, got {}", + "Expected {} block boundaries, got {}", num_blocks + 1, offsets.len() ); @@ -221,7 +221,7 @@ pub fn unpack_single_blocked( let block = index_in_encoded / FL_CHUNK_SIZE; vortex_ensure!( block + 1 < offsets.len(), - OutOfBounds: "BitPacked index {index} has no block boundaries" + "BitPacked index {index} has no block boundaries" ); let (base, start, end) = if let Some(primitive) = offsets.as_opt::() && primitive.buffer_handle().is_on_host() @@ -457,7 +457,7 @@ mod tests { &mut ctx, )?; let BitWidthsView::Blocked(block_offsets) = array.bit_widths() else { - vortex_bail!(AssertionFailed: "expected block offsets"); + vortex_bail!("expected block offsets"); }; let array = BitPacked::try_new_with_block_offsets( array.packed().clone(), diff --git a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs index 685b3eaf80e..3cdf080edec 100644 --- a/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs +++ b/encodings/fastlanes/src/bitpacking/array/bitpack_decompress/global.rs @@ -168,7 +168,7 @@ pub(crate) fn apply_patches_to_uninit_range, index: usize) -> VortexResult { let BitWidthsView::Global(bit_width) = array.bit_widths() else { - vortex_bail!(NotImplemented: "BitPacked array has per-block bit widths"); + vortex_bail!("BitPacked array has per-block bit widths"); }; let bit_width = bit_width as usize; let ptype = array.dtype().as_ptype(); diff --git a/encodings/fastlanes/src/bitpacking/array/mod.rs b/encodings/fastlanes/src/bitpacking/array/mod.rs index 08c7cefb526..685ff42298e 100644 --- a/encodings/fastlanes/src/bitpacking/array/mod.rs +++ b/encodings/fastlanes/src/bitpacking/array/mod.rs @@ -84,12 +84,12 @@ pub(crate) fn validate_block_offsets( ) -> VortexResult<()> { vortex_ensure!( offsets.dtype().is_unsigned_int() && !offsets.dtype().is_nullable(), - MismatchedTypes: "Expected non-nullable unsigned integer block offsets, got {}", + "Expected non-nullable unsigned integer block offsets, got {}", offsets.dtype() ); vortex_ensure!( offsets.len() == num_blocks + 1, - InvalidArgument: "Expected {} block boundaries, got {}", + "Expected {} block boundaries, got {}", num_blocks + 1, offsets.len() ); @@ -132,7 +132,7 @@ where }; vortex_ensure!( span == packed_len as u64, - InvalidArgument: "Block offsets span {span} bytes, but the packed buffer has {packed_len}" + "Block offsets span {span} bytes, but the packed buffer has {packed_len}" ); Ok(()) } @@ -151,22 +151,22 @@ fn block_range( ) -> VortexResult> { vortex_ensure!( base <= start, - InvalidArgument: "Block boundary {start} is below the first boundary {base}" + "Block boundary {start} is below the first boundary {base}" ); vortex_ensure!( start <= end, - InvalidArgument: "Block boundaries {start} and {end} are decreasing" + "Block boundaries {start} and {end} are decreasing" ); vortex_ensure!( end - base <= packed_len as u64, - InvalidArgument: "Block boundaries {start} and {end} are outside the packed buffer (base {base})" + "Block boundaries {start} and {end} are outside the packed buffer (base {base})" ); let size = end - start; vortex_ensure!( (start - base).is_multiple_of(128) && size.is_multiple_of(128) && size / 128 <= max_bit_width, - InvalidArgument: "Block boundaries {start} and {end} do not hold a supported bit width (at most {max_bit_width} bits)" + "Block boundaries {start} and {end} do not hold a supported bit width (at most {max_bit_width} bits)" ); // Both differences are at most `packed_len`, so they fit in `usize`. Ok((start - base) as usize..(end - base) as usize) @@ -288,10 +288,10 @@ impl BitPackedData { bit_width: u8, offset: u16, ) -> VortexResult { - vortex_ensure!(bit_width <= 64, InvalidArgument: "Unsupported bit width {bit_width}"); + vortex_ensure!(bit_width <= 64, "Unsupported bit width {bit_width}"); vortex_ensure!( offset < 1024, - InvalidArgument: "Offset must be less than the full block i.e., 1024, got {offset}" + "Offset must be less than the full block i.e., 1024, got {offset}" ); Ok(Self { @@ -310,7 +310,7 @@ impl BitPackedData { ) -> VortexResult { vortex_ensure!( offset < 1024, - InvalidArgument: "Offset must be less than the full block i.e., 1024, got {offset}" + "Offset must be less than the full block i.e., 1024, got {offset}" ); Ok(Self { @@ -332,7 +332,7 @@ impl BitPackedData { ) -> VortexResult<()> { vortex_ensure!( ptype.is_int(), - MismatchedTypes: "expected type: integer but instead got {}", + "expected type: integer but instead got {}", ptype ); @@ -340,7 +340,7 @@ impl BitPackedData { vortex_ensure_eq!( validity_len, length, - InvalidArgument: "BitPackedArray validity length must match array length" + "BitPackedArray validity length must match array length" ); } @@ -353,11 +353,11 @@ impl BitPackedData { if let Some(bit_width) = bit_width { vortex_ensure!( usize::from(bit_width) <= ptype.bit_width(), - InvalidArgument: "Unsupported bit width {bit_width} for {ptype}" + "Unsupported bit width {bit_width} for {ptype}" ); let expected_packed_len = (length + offset as usize).div_ceil(1024) * (128 * bit_width as usize); - vortex_ensure_eq!(packed.len(), expected_packed_len, InvalidArgument); + vortex_ensure_eq!(packed.len(), expected_packed_len); } Ok(()) @@ -367,7 +367,7 @@ impl BitPackedData { // Ensure that array and patches have same ptype vortex_ensure!( patches.dtype().eq_ignore_nullability(ptype.into()), - MismatchedTypes: "Patches DType {} does not match BitPackedArray dtype {}", + "Patches DType {} does not match BitPackedArray dtype {}", patches.dtype().as_nonnullable(), ptype ); @@ -375,7 +375,7 @@ impl BitPackedData { vortex_ensure_eq!( patches.array_len(), len, - InvalidArgument: "BitPackedArray patches length mismatch" + "BitPackedArray patches length mismatch" ); Ok(()) @@ -441,10 +441,12 @@ impl BitPackedData { bit_width: u8, ctx: &mut ExecutionCtx, ) -> VortexResult { - let parray: PrimitiveArray = array - .clone() - .try_downcast::() - .map_err(|a| vortex_err!(InvalidArgument: "Bitpacking can only encode primitive arrays, got {}", a.encoding_id()))?; + let parray: PrimitiveArray = array.clone().try_downcast::().map_err(|a| { + vortex_err!( + "Bitpacking can only encode primitive arrays, got {}", + a.encoding_id() + ) + })?; bitpack_encode(&parray, bit_width, None, ctx) } @@ -464,10 +466,12 @@ impl BitPackedData { bit_widths: &[u8], ctx: &mut ExecutionCtx, ) -> VortexResult { - let parray: PrimitiveArray = array - .clone() - .try_downcast::() - .map_err(|a| vortex_err!(InvalidArgument: "Bitpacking can only encode primitive arrays, got {}", a.encoding_id()))?; + let parray: PrimitiveArray = array.clone().try_downcast::().map_err(|a| { + vortex_err!( + "Bitpacking can only encode primitive arrays, got {}", + a.encoding_id() + ) + })?; bitpack_encode_blocked(&parray, bit_widths, None, ctx) } } @@ -486,7 +490,7 @@ pub trait BitPackedArrayExt: BitPackedArraySlotsExt { (Some(bit_width), None) => BitWidthsView::Global(bit_width), (None, Some(block_offsets)) => BitWidthsView::Blocked(block_offsets), _ => vortex_panic!( - AssertionFailed: "BitPacked must have exactly one of a global bit width and block offsets" + "BitPacked must have exactly one of a global bit width and block offsets" ), } } diff --git a/encodings/fastlanes/src/bitpacking/array/tests.rs b/encodings/fastlanes/src/bitpacking/array/tests.rs index 2a9d28ba8cb..94a29adff73 100644 --- a/encodings/fastlanes/src/bitpacking/array/tests.rs +++ b/encodings/fastlanes/src/bitpacking/array/tests.rs @@ -374,7 +374,7 @@ fn into_parts_preserves_block_offsets(#[case] offsets: ArrayRef) -> VortexResult )?; let parts = BitPacked::into_parts(array); let BitWidths::Blocked(block_offsets) = parts.bit_widths else { - vortex_bail!(AssertionFailed: "expected block offsets"); + vortex_bail!("expected block offsets"); }; assert!(ArrayRef::ptr_eq(&offsets, &block_offsets)); let rebuilt = BitPacked::try_new_with_block_offsets( diff --git a/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs b/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs index e5e8f095ac7..e6993e83a62 100644 --- a/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs +++ b/encodings/fastlanes/src/bitpacking/array/unpack_iter.rs @@ -110,7 +110,7 @@ impl<'a, T: BitPacked> BitUnpackedChunks<'a, T> { scratch: &'a mut [MaybeUninit; CHUNK_SIZE], ) -> VortexResult { let Some(bit_width) = array.global_bit_width else { - vortex_bail!(NotImplemented: "BitPacked array has per-block bit widths"); + vortex_bail!("BitPacked array has per-block bit widths"); }; Self::try_new_with_strategy( BitPackingStrategy, @@ -350,11 +350,11 @@ fn validate_packed( ) -> VortexResult<(usize, usize)> { vortex_ensure!( offset < CHUNK_SIZE, - InvalidArgument: "Invalid bit-packed offset {offset}, expected < {CHUNK_SIZE}" + "Invalid bit-packed offset {offset}, expected < {CHUNK_SIZE}" ); let elems_per_chunk = 128 * bit_width / size_of::(); let num_chunks = (offset + len).div_ceil(CHUNK_SIZE); - vortex_ensure_eq!(packed_len, num_chunks * elems_per_chunk, InvalidArgument); + vortex_ensure_eq!(packed_len, num_chunks * elems_per_chunk); Ok((num_chunks, (offset + len) % CHUNK_SIZE)) } diff --git a/encodings/fastlanes/src/bitpacking/compute/take.rs b/encodings/fastlanes/src/bitpacking/compute/take.rs index 2ba7fdd33f6..345cbef80da 100644 --- a/encodings/fastlanes/src/bitpacking/compute/take.rs +++ b/encodings/fastlanes/src/bitpacking/compute/take.rs @@ -184,14 +184,14 @@ fn collect_ranges( let length = usize::try_from(length)?; let end = start .checked_add(length) - .ok_or_else(|| vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"))?; + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; vortex_ensure!( end <= array_len, - OutOfBounds: "PiecewiseSequenceArray range exceeds array length" + "PiecewiseSequenceArray range exceeds array length" ); - total_len = total_len.checked_add(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + total_len = total_len + .checked_add(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; ranges.push(start..end); } vortex_ensure_eq!(total_len, output_len); diff --git a/encodings/fastlanes/src/bitpacking/plugin/mod.rs b/encodings/fastlanes/src/bitpacking/plugin/mod.rs index 648282d6f13..31b1f06ec90 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/mod.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/mod.rs @@ -73,9 +73,9 @@ impl ArrayPlugin for BitPackedPlugin { array: &ArrayRef, _session: &VortexSession, ) -> VortexResult> { - let view = array.as_opt::().ok_or_else( - || vortex_err!(Serde: "BitPacked plugin cannot serialize {}", array.encoding_id()), - )?; + let view = array.as_opt::().ok_or_else(|| { + vortex_err!("BitPacked plugin cannot serialize {}", array.encoding_id()) + })?; let serialization = match view.bit_widths() { BitWidthsView::Global(bit_width) => v1::serialize(array, view, bit_width)?, BitWidthsView::Blocked(block_offsets) => v2::serialize(array, view, block_offsets)?, @@ -94,7 +94,7 @@ impl ArrayPlugin for BitPackedPlugin { v2::deserialize(parts, session) } else { vortex_bail!( - Serde: "BitPacked plugin does not recognize serialized ID {}", + "BitPacked plugin does not recognize serialized ID {}", parts.serialized_id ) } @@ -134,14 +134,14 @@ impl ArrayPlugin for BitPackedPatchedPlugin { ) -> VortexResult { vortex_ensure!( self.serialized_ids().contains(&parts.serialized_id), - Serde: "BitPacked plugin does not recognize serialized ID {}", + "BitPacked plugin does not recognize serialized ID {}", parts.serialized_id, ); let bitpacked: BitPackedArray = BitPackedPlugin .deserialize(parts, session)? .try_downcast() .map_err(|_| { - vortex_err!(Serde: "BitPacked plugin should only deserialize fastlanes.bitpacked") + vortex_err!("BitPacked plugin should only deserialize fastlanes.bitpacked") })?; // Create a new BitPackedArray without the interior patches installed. diff --git a/encodings/fastlanes/src/bitpacking/plugin/tests.rs b/encodings/fastlanes/src/bitpacking/plugin/tests.rs index d42840cd6a0..127695c6d26 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/tests.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/tests.rs @@ -92,11 +92,13 @@ fn test_decode_bitpacked_patches() -> VortexResult<()> { let patched: PatchedArray = deserialized .try_downcast() - .map_err(|a| vortex_err!(MismatchedTypes: "Expected Patched, got {}", a.encoding_id()))?; + .map_err(|a| vortex_err!("Expected Patched, got {}", a.encoding_id()))?; - let inner_bitpacked: BitPackedArray = patched.inner().clone().try_downcast().map_err( - |a| vortex_err!(MismatchedTypes: "Expected inner BitPacked, got {}", a.encoding_id()), - )?; + let inner_bitpacked: BitPackedArray = patched + .inner() + .clone() + .try_downcast() + .map_err(|a| vortex_err!("Expected inner BitPacked, got {}", a.encoding_id()))?; assert!( inner_bitpacked.patches().is_none(), @@ -143,9 +145,9 @@ fn bitpacked_without_patches_stays_bitpacked() -> VortexResult<()> { assert_arrays_eq!(deserialized, parray, &mut ctx); - let result = deserialized.try_downcast::().map_err( - |a| vortex_err!(Serde: "Expected deserialize BitPacked, got {}", a.encoding_id()), - )?; + let result = deserialized + .try_downcast::() + .map_err(|a| vortex_err!("Expected deserialize BitPacked, got {}", a.encoding_id()))?; assert!(result.patches().is_none(), "Result should not have patches"); @@ -226,7 +228,7 @@ fn serde_roundtrip( let view = array.as_::(); let serialization = PLUGIN_SESSION .array_serialize(&array)? - .ok_or_else(|| vortex_err!(AssertionFailed: "BitPacked must serialize"))?; + .ok_or_else(|| vortex_err!("BitPacked must serialize"))?; assert_eq!(serialization.serialized_id, bitpacked_v1_id()); let metadata = BitPackedMetadata::decode(serialization.metadata.as_slice())?; assert_eq!(metadata.bit_width, u32::from(bit_width)); @@ -273,11 +275,11 @@ fn v2_roundtrip( None => bitpack_blocked_to_best_bit_widths(&values, &mut ctx)?, }; let BitWidthsView::Blocked(block_offsets) = array.bit_widths() else { - vortex_bail!(AssertionFailed: "expected block offsets"); + vortex_bail!("expected block offsets"); }; let serialization = PLUGIN_SESSION .array_serialize(array.as_array())? - .ok_or_else(|| vortex_err!(AssertionFailed: "BitPacked must serialize"))?; + .ok_or_else(|| vortex_err!("BitPacked must serialize"))?; assert_eq!(serialization.serialized_id, bitpacked_v2_id()); let metadata = BitPackedV2Metadata::decode(serialization.metadata.as_slice())?; assert_eq!(metadata.offset, 0); @@ -300,7 +302,7 @@ fn v2_roundtrip_offset_and_nonzero_base() -> VortexResult<()> { let values = drifting(); let encoded = bitpack_blocked_to_best_bit_widths(&values, &mut ctx)?; let BitWidthsView::Blocked(block_offsets) = encoded.bit_widths() else { - vortex_bail!(AssertionFailed: "expected block offsets"); + vortex_bail!("expected block offsets"); }; let block_offsets = block_offsets .cast(DType::Primitive(PType::U64, Nullability::NonNullable))? @@ -320,7 +322,7 @@ fn v2_roundtrip_offset_and_nonzero_base() -> VortexResult<()> { let serialization = PLUGIN_SESSION .array_serialize(&array)? - .ok_or_else(|| vortex_err!(AssertionFailed: "BitPacked must serialize"))?; + .ok_or_else(|| vortex_err!("BitPacked must serialize"))?; assert_eq!( BitPackedV2Metadata::decode(serialization.metadata.as_slice())?.offset, 17 @@ -340,7 +342,7 @@ fn v2_rejects_malformed_parts() -> VortexResult<()> { &mut PLUGIN_SESSION.create_execution_ctx(), )?; let BitWidthsView::Blocked(block_offsets) = array.bit_widths() else { - vortex_bail!(AssertionFailed: "expected block offsets"); + vortex_bail!("expected block offsets"); }; let metadata = BitPackedV2Metadata { offset: 0, @@ -410,10 +412,12 @@ fn test_decode_blocked_bitpacked_patches() -> VortexResult<()> { let patched: PatchedArray = deserialized .try_downcast() - .map_err(|a| vortex_err!(MismatchedTypes: "Expected Patched, got {}", a.encoding_id()))?; - let inner_bitpacked: BitPackedArray = patched.inner().clone().try_downcast().map_err( - |a| vortex_err!(MismatchedTypes: "Expected inner BitPacked, got {}", a.encoding_id()), - )?; + .map_err(|a| vortex_err!("Expected Patched, got {}", a.encoding_id()))?; + let inner_bitpacked: BitPackedArray = patched + .inner() + .clone() + .try_downcast() + .map_err(|a| vortex_err!("Expected inner BitPacked, got {}", a.encoding_id()))?; assert!(inner_bitpacked.patches().is_none()); assert!(!inner_bitpacked.bit_widths().is_global()); assert_arrays_eq!(patched, values, &mut ctx); diff --git a/encodings/fastlanes/src/bitpacking/plugin/v1.rs b/encodings/fastlanes/src/bitpacking/plugin/v1.rs index 2ed8229e2cb..78da347f2c5 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/v1.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/v1.rs @@ -75,7 +75,7 @@ pub(super) fn deserialize( let metadata = BitPackedMetadata::decode(metadata)?; if buffers.len() != 1 { - vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); + vortex_bail!("Expected 1 buffer, got {}", buffers.len()); } let packed = buffers[0].clone(); @@ -87,7 +87,7 @@ pub(super) fn deserialize( Ok(Validity::Array(validity)) } else { vortex_bail!( - InvalidArgument: "Expected {} or {} children, got {}", + "Expected {} or {} children, got {}", child_idx, child_idx + 1, children.len() @@ -136,13 +136,13 @@ pub(super) fn deserialize( patches, u8::try_from(metadata.bit_width).map_err(|_| { vortex_err!( - Overflow: "BitPackedMetadata bit_width {} does not fit in u8", + "BitPackedMetadata bit_width {} does not fit in u8", metadata.bit_width ) })?, u16::try_from(metadata.offset).map_err(|_| { vortex_err!( - Overflow: "BitPackedMetadata offset {} does not fit in u16", + "BitPackedMetadata offset {} does not fit in u16", metadata.offset ) })?, diff --git a/encodings/fastlanes/src/bitpacking/plugin/v2.rs b/encodings/fastlanes/src/bitpacking/plugin/v2.rs index 46702fd8273..388e4b1241f 100644 --- a/encodings/fastlanes/src/bitpacking/plugin/v2.rs +++ b/encodings/fastlanes/src/bitpacking/plugin/v2.rs @@ -86,12 +86,12 @@ pub(super) fn deserialize( let metadata = BitPackedV2Metadata::decode(metadata)?; vortex_ensure!( buffers.len() == 1, - InvalidArgument: "Expected 1 buffer, got {}", + "Expected 1 buffer, got {}", buffers.len() ); vortex_ensure!( usize::try_from(metadata.offset).is_ok_and(|offset| offset < FL_CHUNK_SIZE), - InvalidArgument: "BitPacked offset must be less than {FL_CHUNK_SIZE}, got {}", + "BitPacked offset must be less than {FL_CHUNK_SIZE}, got {}", metadata.offset ); let offset = u16::try_from(metadata.offset)?; @@ -108,7 +108,7 @@ pub(super) fn deserialize( Validity::Array(children.get(num_patch_children, &Validity::DTYPE, len)?) } else { vortex_bail!( - InvalidArgument: "Expected {} or {} children, got {}", + "Expected {} or {} children, got {}", num_patch_children + 1, num_patch_children + 2, children.len() diff --git a/encodings/fastlanes/src/bitpacking/vtable/mod.rs b/encodings/fastlanes/src/bitpacking/vtable/mod.rs index 72493720543..e92b1d040a2 100644 --- a/encodings/fastlanes/src/bitpacking/vtable/mod.rs +++ b/encodings/fastlanes/src/bitpacking/vtable/mod.rs @@ -113,7 +113,7 @@ impl VTable for BitPacked { data.packed.len(), )?, _ => { - vortex_bail!(InvalidArgument: "BitPacked needs exactly one of a global bit width and block offsets") + vortex_bail!("BitPacked needs exactly one of a global bit width and block offsets") } } @@ -138,7 +138,7 @@ impl VTable for BitPacked { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.packed().clone(), - _ => vortex_panic!(OutOfBounds: "BitPackedArray buffer index {idx} out of bounds"), + _ => vortex_panic!("BitPackedArray buffer index {idx} out of bounds"), } } @@ -154,7 +154,7 @@ impl VTable for BitPacked { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 1); let mut data = array.data().clone(); data.packed = buffers[0].clone(); Ok(ArrayParts::new( @@ -170,7 +170,7 @@ impl VTable for BitPacked { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!(Serde: "BitPacked serialization requires BitPackedPlugin") + vortex_bail!("BitPacked serialization requires BitPackedPlugin") } fn deserialize( @@ -182,7 +182,7 @@ impl VTable for BitPacked { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "BitPacked deserialization requires BitPackedPlugin") + vortex_bail!("BitPacked deserialization requires BitPackedPlugin") } fn append_to_builder( diff --git a/encodings/fastlanes/src/delta/array/mod.rs b/encodings/fastlanes/src/delta/array/mod.rs index 09377d81288..271a74d5343 100644 --- a/encodings/fastlanes/src/delta/array/mod.rs +++ b/encodings/fastlanes/src/delta/array/mod.rs @@ -109,7 +109,7 @@ impl> DeltaArrayExt for T {} impl DeltaData { pub fn try_new(offset: usize) -> VortexResult { - vortex_ensure!(offset < 1024, InvalidArgument: "offset must be less than 1024: {offset}"); + vortex_ensure!(offset < 1024, "offset must be less than 1024: {offset}"); Ok(Self { offset }) } } diff --git a/encodings/fastlanes/src/delta/compute/cast.rs b/encodings/fastlanes/src/delta/compute/cast.rs index d24d97fa017..4342fd883bd 100644 --- a/encodings/fastlanes/src/delta/compute/cast.rs +++ b/encodings/fastlanes/src/delta/compute/cast.rs @@ -135,9 +135,9 @@ mod tests { casted.dtype(), &DType::Primitive(PType::U32, Nullability::Nullable) ); - let reduced = casted.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "expected nullability cast to preserve Delta"), - )?; + let reduced = casted + .as_opt::() + .ok_or_else(|| vortex_err!("expected nullability cast to preserve Delta"))?; assert!(!reduced.deltas().dtype().is_nullable()); assert!(!reduced.bases().dtype().is_nullable()); assert_arrays_eq!( diff --git a/encodings/fastlanes/src/delta/tests.rs b/encodings/fastlanes/src/delta/tests.rs index 563aeea92be..37bc80e8e00 100644 --- a/encodings/fastlanes/src/delta/tests.rs +++ b/encodings/fastlanes/src/delta/tests.rs @@ -135,7 +135,7 @@ fn delta_null_patterns(#[case] pattern: usize) -> VortexResult<()> { )?; let restored_delta = restored .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "expected deserialized Delta"))?; + .ok_or_else(|| vortex_err!("expected deserialized Delta"))?; assert!(!restored_delta.deltas().dtype().is_nullable()); assert_arrays_eq!(restored, source, &mut ctx); } diff --git a/encodings/fastlanes/src/delta/vtable/mod.rs b/encodings/fastlanes/src/delta/vtable/mod.rs index 32eb7d11b5c..cdd4cef18c4 100644 --- a/encodings/fastlanes/src/delta/vtable/mod.rs +++ b/encodings/fastlanes/src/delta/vtable/mod.rs @@ -105,7 +105,7 @@ impl VTable for Delta { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "DeltaArray buffer index {idx} out of bounds") + vortex_panic!("DeltaArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -156,24 +156,23 @@ impl VTable for Delta { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - InvalidArgument: "DeltaArray expects 0 buffers, got {}", + "DeltaArray expects 0 buffers, got {}", buffers.len() ); vortex_ensure!( children.len() == 2 || children.len() == 3, - InvalidArgument: "DeltaArray expects 2 or 3 children, got {}", + "DeltaArray expects 2 or 3 children, got {}", children.len() ); let metadata = DeltaMetadata::decode(metadata)?; let ptype = PType::try_from(dtype)?; let lanes = lane_count(ptype); - let deltas_len = usize::try_from(metadata.deltas_len).map_err( - |_| vortex_err!(Overflow: "deltas_len {} overflowed usize", metadata.deltas_len), - )?; + let deltas_len = usize::try_from(metadata.deltas_len) + .map_err(|_| vortex_err!("deltas_len {} overflowed usize", metadata.deltas_len))?; vortex_ensure!( deltas_len.is_multiple_of(FL_CHUNK_SIZE), - Serde: "deltas length must be a multiple of {FL_CHUNK_SIZE}" + "deltas length must be a multiple of {FL_CHUNK_SIZE}" ); let bases_len = deltas_len / FL_CHUNK_SIZE * lanes; @@ -258,42 +257,42 @@ fn validate_parts( ) -> VortexResult<()> { vortex_ensure!( offset <= deltas.len() && len <= deltas.len() - offset, - InvalidArgument: "offset + len, {offset} + {len}, must be less than or equal to the size of deltas: {}", + "offset + len, {offset} + {len}, must be less than or equal to the size of deltas: {}", deltas.len() ); vortex_ensure!( !bases.dtype().is_nullable() && !deltas.dtype().is_nullable(), - MismatchedTypes: "DeltaArray: bases and deltas must be nonnullable" + "DeltaArray: bases and deltas must be nonnullable" ); vortex_ensure!( bases.dtype() == deltas.dtype(), - MismatchedTypes: "DeltaArray: bases and deltas must have the same dtype, got {} and {}", + "DeltaArray: bases and deltas must have the same dtype, got {} and {}", bases.dtype(), deltas.dtype() ); vortex_ensure!( bases.dtype().is_int(), - MismatchedTypes: "DeltaArray: dtype must be an integer, got {}", + "DeltaArray: dtype must be an integer, got {}", bases.dtype() ); let expected_dtype = bases.dtype().with_nullability(dtype.nullability()); - vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes: "DeltaArray dtype mismatch"); + vortex_ensure_eq!(dtype, &expected_dtype, "DeltaArray dtype mismatch"); if let Some(validity) = validity_child { vortex_ensure!( dtype.is_nullable(), - MismatchedTypes: "DeltaArray: validity requires a nullable dtype" + "DeltaArray: validity requires a nullable dtype" ); vortex_ensure_eq!( validity.dtype(), &Validity::DTYPE, - MismatchedTypes: "DeltaArray: validity must be nonnullable bool" + "DeltaArray: validity must be nonnullable bool" ); vortex_ensure_eq!( validity.len(), len, - InvalidArgument: "DeltaArray: validity length must equal logical length" + "DeltaArray: validity length must equal logical length" ); } @@ -301,12 +300,12 @@ fn validate_parts( vortex_ensure!( deltas.len().is_multiple_of(1024), - InvalidArgument: "deltas length ({}) must be a multiple of 1024", + "deltas length ({}) must be a multiple of 1024", deltas.len(), ); vortex_ensure!( bases.len() == deltas.len() / FL_CHUNK_SIZE * lanes, - InvalidArgument: "bases length ({}) must equal the number of chunks times LANES ({lanes})", + "bases length ({}) must equal the number of chunks times LANES ({lanes})", bases.len(), ); Ok(()) diff --git a/encodings/fastlanes/src/delta/vtable/validity.rs b/encodings/fastlanes/src/delta/vtable/validity.rs index b56b14ec35c..3133e07cdf2 100644 --- a/encodings/fastlanes/src/delta/vtable/validity.rs +++ b/encodings/fastlanes/src/delta/vtable/validity.rs @@ -87,7 +87,7 @@ mod tests { let sliced = delta.slice(range.clone())?; let Validity::Array(validity) = sliced.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(range.clone()), &mut ctx); assert_arrays_eq!(sliced, primitive.slice(range)?, &mut ctx); @@ -102,7 +102,7 @@ mod tests { let sliced = delta.slice(100..2400)?.slice(900..1500)?; let Validity::Array(validity) = sliced.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(1000..1600), &mut ctx); assert_arrays_eq!(sliced, primitive.slice(1000..1600)?, &mut ctx); @@ -118,7 +118,7 @@ mod tests { let (bases, deltas) = delta_compress(&primitive, &mut ctx)?; let Validity::Array(validity) = primitive.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; let lazy_validity = SliceArray::try_new(validity, 0..primitive.len())?.into_array(); let delta = Delta::try_new( @@ -130,7 +130,7 @@ mod tests { )?; let Validity::Array(validity) = delta.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; assert_arrays_eq!( validity, @@ -148,7 +148,7 @@ mod tests { let (bases, deltas) = delta_compress(&primitive, &mut ctx)?; let Validity::Array(validity) = primitive.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; let bits = validity.execute::(&mut ctx)?.into_bit_buffer(); let unaligned = BoolArray::new(misalign_bits(bits), Validity::NonNullable).into_array(); @@ -161,14 +161,14 @@ mod tests { )?; let Validity::Array(validity) = delta.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(0..LEN), &mut ctx); assert_arrays_eq!(delta, primitive, &mut ctx); let sliced = delta.slice(1000..1050)?; let Validity::Array(sliced_validity) = sliced.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; assert_arrays_eq!(sliced_validity, expected_validity(1000..1050), &mut ctx); Ok(()) @@ -185,7 +185,7 @@ mod tests { let delta = Delta::try_from_primitive_array(&primitive, &mut ctx)?; let Validity::Array(validity) = delta.validity()? else { - vortex_bail!(MismatchedTypes: "expected array-backed validity") + vortex_bail!("expected array-backed validity") }; assert_arrays_eq!(validity, expected_validity(0..len as usize), &mut ctx); assert_arrays_eq!(delta, primitive, &mut ctx); diff --git a/encodings/fastlanes/src/for_/array/for_compress.rs b/encodings/fastlanes/src/for_/array/for_compress.rs index a8f26f2fdc5..cd854bab5fa 100644 --- a/encodings/fastlanes/src/for_/array/for_compress.rs +++ b/encodings/fastlanes/src/for_/array/for_compress.rs @@ -39,7 +39,7 @@ impl FoRData { let min = array_ref .statistics() .compute_stat(Stat::Min, ctx)? - .ok_or_else(|| vortex_err!(NotFound: "Min stat not found"))?; + .ok_or_else(|| vortex_err!("Min stat not found"))?; let encoded = match_each_integer_ptype!(array.ptype(), |T| { encode_primitive::(array, T::try_from(&min)?, ctx)?.into_array() diff --git a/encodings/fastlanes/src/for_/array/for_decompress.rs b/encodings/fastlanes/src/for_/array/for_decompress.rs index 7a41f0457a3..30aed5808b9 100644 --- a/encodings/fastlanes/src/for_/array/for_decompress.rs +++ b/encodings/fastlanes/src/for_/array/for_decompress.rs @@ -86,7 +86,7 @@ fn fused_decompress_typed< ctx: &mut ExecutionCtx, ) -> VortexResult { let FoRReferences::Global(reference) = for_.references() else { - vortex_bail!(NotImplemented: "fused FoR decompression requires a global reference"); + vortex_bail!("fused FoR decompression requires a global reference"); }; let ref_ = reference .as_primitive() diff --git a/encodings/fastlanes/src/for_/array/mod.rs b/encodings/fastlanes/src/for_/array/mod.rs index f2f30fadbf2..d7edb2de513 100644 --- a/encodings/fastlanes/src/for_/array/mod.rs +++ b/encodings/fastlanes/src/for_/array/mod.rs @@ -68,7 +68,7 @@ pub trait FoRArrayExt: FoRArraySlotsExt { (Some(reference), None) => FoRReferences::Global(reference), (None, Some(references)) => FoRReferences::Blocked(references), _ => { - vortex_panic!(AssertionFailed: "FoR array must have either a global or blocked references") + vortex_panic!("FoR array must have either a global or blocked references") } } } @@ -100,11 +100,11 @@ impl FoRData { pub(crate) fn try_new(offset: u16, global_reference: Option) -> VortexResult { vortex_ensure!( usize::from(offset) < FL_CHUNK_SIZE, - InvalidArgument: "FoR offset must be less than {FL_CHUNK_SIZE}, got {offset}" + "FoR offset must be less than {FL_CHUNK_SIZE}, got {offset}" ); vortex_ensure!( offset == 0 || global_reference.is_none(), - InvalidArgument: "FoR with a global reference must have offset 0, got {offset}" + "FoR with a global reference must have offset 0, got {offset}" ); Ok(Self { offset, diff --git a/encodings/fastlanes/src/for_/plugin/mod.rs b/encodings/fastlanes/src/for_/plugin/mod.rs index 7ab1d13cadc..a5478428072 100644 --- a/encodings/fastlanes/src/for_/plugin/mod.rs +++ b/encodings/fastlanes/src/for_/plugin/mod.rs @@ -61,9 +61,9 @@ impl ArrayPlugin for FoRPlugin { array: &ArrayRef, _session: &VortexSession, ) -> VortexResult> { - let view = array.as_opt::().ok_or_else( - || vortex_err!(Serde: "FoR plugin cannot serialize {}", array.encoding_id()), - )?; + let view = array + .as_opt::() + .ok_or_else(|| vortex_err!("FoR plugin cannot serialize {}", array.encoding_id()))?; Ok(Some(match view.references() { FoRReferences::Global(reference) => v1::serialize(view, reference), FoRReferences::Blocked(references) => v2::serialize(view, references), @@ -81,7 +81,7 @@ impl ArrayPlugin for FoRPlugin { v2::deserialize(parts) } else { vortex_bail!( - Serde: "FoR plugin does not recognize serialized ID {}", + "FoR plugin does not recognize serialized ID {}", parts.serialized_id ) } diff --git a/encodings/fastlanes/src/for_/plugin/tests.rs b/encodings/fastlanes/src/for_/plugin/tests.rs index 5d98fd5fcca..16278e070df 100644 --- a/encodings/fastlanes/src/for_/plugin/tests.rs +++ b/encodings/fastlanes/src/for_/plugin/tests.rs @@ -55,7 +55,7 @@ fn serde_roundtrip(#[case] array: VortexResult) -> VortexResult<()> { let array = array?; let serialization = SESSION .array_serialize(array.as_array())? - .ok_or_else(|| vortex_err!(AssertionFailed: "FoR must serialize"))?; + .ok_or_else(|| vortex_err!("FoR must serialize"))?; assert_eq!(serialization.serialized_id, for_v1_id()); assert_eq!( serialization.metadata, @@ -84,7 +84,7 @@ fn v2_roundtrip(#[case] range: std::ops::Range) -> VortexResult<()> { let array = chunked()?.into_array().slice(range.clone())?; let serialization = SESSION .array_serialize(&array)? - .ok_or_else(|| vortex_err!(AssertionFailed: "FoR must serialize"))?; + .ok_or_else(|| vortex_err!("FoR must serialize"))?; assert_eq!(serialization.serialized_id, for_v2_id()); assert_eq!( v2::FoRV2Metadata::decode(serialization.metadata.as_slice())?.offset, diff --git a/encodings/fastlanes/src/for_/plugin/v1.rs b/encodings/fastlanes/src/for_/plugin/v1.rs index 9dfdf7acb02..11a862cfc33 100644 --- a/encodings/fastlanes/src/for_/plugin/v1.rs +++ b/encodings/fastlanes/src/for_/plugin/v1.rs @@ -31,12 +31,12 @@ pub(super) fn deserialize( ) -> VortexResult { vortex_ensure!( parts.buffers.is_empty(), - InvalidArgument: "FoRArray expects 0 buffers, got {}", + "FoRArray expects 0 buffers, got {}", parts.buffers.len() ); if parts.children.len() != 1 { vortex_bail!( - InvalidArgument: "Expected 1 child for FoR encoding, found {}", + "Expected 1 child for FoR encoding, found {}", parts.children.len() ) } diff --git a/encodings/fastlanes/src/for_/plugin/v2.rs b/encodings/fastlanes/src/for_/plugin/v2.rs index c0d911eb54d..04cce287eab 100644 --- a/encodings/fastlanes/src/for_/plugin/v2.rs +++ b/encodings/fastlanes/src/for_/plugin/v2.rs @@ -43,19 +43,19 @@ pub(super) fn serialize(array: ArrayView<'_, FoR>, references: &ArrayRef) -> Arr pub(super) fn deserialize(parts: ArrayDeserialization<'_>) -> VortexResult { vortex_ensure!( parts.buffers.is_empty(), - InvalidArgument: "FoRArray expects 0 buffers, got {}", + "FoRArray expects 0 buffers, got {}", parts.buffers.len() ); vortex_ensure_eq!( parts.children.len(), 2, - Serde: "Expected 2 children for {}", + "Expected 2 children for {}", for_v2_id() ); let metadata = FoRV2Metadata::decode(parts.metadata)?; vortex_ensure!( usize::try_from(metadata.offset).is_ok_and(|offset| offset < FL_CHUNK_SIZE), - Serde: "FoR offset must be less than {FL_CHUNK_SIZE}, got {}", + "FoR offset must be less than {FL_CHUNK_SIZE}, got {}", metadata.offset ); let offset = u16::try_from(metadata.offset)?; diff --git a/encodings/fastlanes/src/for_/tests.rs b/encodings/fastlanes/src/for_/tests.rs index 8e6704e149d..63116924f5e 100644 --- a/encodings/fastlanes/src/for_/tests.rs +++ b/encodings/fastlanes/src/for_/tests.rs @@ -48,14 +48,14 @@ static SESSION: LazyLock = LazyLock::new(|| { pub(crate) fn global(array: &FoRArray) -> VortexResult { match array.references() { FoRReferences::Global(reference) => Ok(reference.clone()), - FoRReferences::Blocked(_) => vortex_bail!(AssertionFailed: "expected a global reference"), + FoRReferences::Blocked(_) => vortex_bail!("expected a global reference"), } } /// The blocked references of `array`. pub(crate) fn blocked(array: &FoRArray) -> VortexResult { match array.references() { - FoRReferences::Global(_) => vortex_bail!(AssertionFailed: "expected blocked references"), + FoRReferences::Global(_) => vortex_bail!("expected blocked references"), FoRReferences::Blocked(references) => Ok(references.clone()), } } diff --git a/encodings/fastlanes/src/for_/vtable/mod.rs b/encodings/fastlanes/src/for_/vtable/mod.rs index 1b3610c635a..ba2c353dec2 100644 --- a/encodings/fastlanes/src/for_/vtable/mod.rs +++ b/encodings/fastlanes/src/for_/vtable/mod.rs @@ -95,10 +95,10 @@ impl VTable for FoR { (Some(reference), None) => FoRReferences::Global(reference), (None, Some(references)) => FoRReferences::Blocked(references), (Some(_), Some(_)) => { - vortex_bail!(InvalidArgument: "FoR cannot have both a global reference and blocked references") + vortex_bail!("FoR cannot have both a global reference and blocked references") } (None, None) => { - vortex_bail!(InvalidArgument: "FoR needs either a global reference or blocked references") + vortex_bail!("FoR needs either a global reference or blocked references") } }; validate_parts(slots.encoded, references, data.offset, dtype, len) @@ -109,7 +109,7 @@ impl VTable for FoR { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "FoRArray buffer index {idx} out of bounds") + vortex_panic!("FoRArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -132,7 +132,7 @@ impl VTable for FoR { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!(Serde: "FoR serialization requires FoRPlugin") + vortex_bail!("FoR serialization requires FoRPlugin") } fn deserialize( @@ -144,7 +144,7 @@ impl VTable for FoR { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "FoR deserialization requires FoRPlugin") + vortex_bail!("FoR deserialization requires FoRPlugin") } fn reduce_parent( @@ -182,7 +182,7 @@ pub struct FoR; impl FoR { /// Construct a FoR array with one global reference. pub fn try_new(encoded: ArrayRef, reference: Scalar) -> VortexResult { - vortex_ensure!(!reference.is_null(), InvalidArgument: "Reference value cannot be null"); + vortex_ensure!(!reference.is_null(), "Reference value cannot be null"); let dtype = reference .dtype() .with_nullability(encoded.dtype().nullability()); @@ -204,7 +204,7 @@ impl FoR { vortex_ensure_eq!( references.len(), num_chunks(offset, encoded.len()), - InvalidArgument: "FoR expects one reference per chunk" + "FoR expects one reference per chunk" ); return Self::try_new(encoded, reference); } @@ -242,29 +242,29 @@ fn validate_parts( dtype: &DType, len: usize, ) -> VortexResult<()> { - vortex_ensure!(dtype.is_int(), MismatchedTypes: "FoR requires an integer dtype, got {dtype}"); - vortex_ensure_eq!(encoded.dtype(), dtype, MismatchedTypes: "FoR encoded dtype mismatch"); - vortex_ensure_eq!(encoded.len(), len, InvalidArgument: "FoR encoded length mismatch"); + vortex_ensure!(dtype.is_int(), "FoR requires an integer dtype, got {dtype}"); + vortex_ensure_eq!(encoded.dtype(), dtype, "FoR encoded dtype mismatch"); + vortex_ensure_eq!(encoded.len(), len, "FoR encoded length mismatch"); let references_dtype = dtype.as_nonnullable(); match references { FoRReferences::Global(reference) => { - vortex_ensure!(!reference.is_null(), InvalidArgument: "FoR global reference cannot be null"); + vortex_ensure!(!reference.is_null(), "FoR global reference cannot be null"); vortex_ensure_eq!( reference.dtype(), &references_dtype, - MismatchedTypes: "FoR global reference dtype mismatch" + "FoR global reference dtype mismatch" ); } FoRReferences::Blocked(references) => { vortex_ensure_eq!( references.dtype(), &references_dtype, - MismatchedTypes: "FoR references dtype mismatch" + "FoR references dtype mismatch" ); vortex_ensure_eq!( references.len(), num_chunks(offset, len), - InvalidArgument: "FoR expects one reference per chunk" + "FoR expects one reference per chunk" ); } } diff --git a/encodings/fastlanes/src/for_/vtable/operations.rs b/encodings/fastlanes/src/for_/vtable/operations.rs index d9f75d48ec2..afe60caf930 100644 --- a/encodings/fastlanes/src/for_/vtable/operations.rs +++ b/encodings/fastlanes/src/for_/vtable/operations.rs @@ -27,7 +27,7 @@ impl OperationsVTable for FoR { let array = state.array(); let encoded_pvalue = state .slot(FoRSlots::ENCODED)? - .ok_or_else(|| vortex_err!(InvalidArgument: "FoR encoded slot is missing"))? + .ok_or_else(|| vortex_err!("FoR encoded slot is missing"))? .execute_scalar(index, ctx)?; let encoded_pvalue = encoded_pvalue.as_primitive(); let reference = match array.references() { @@ -36,9 +36,7 @@ impl OperationsVTable for FoR { let chunk = (usize::from(array.offset()) + index) / FL_CHUNK_SIZE; state .slot(FoRSlots::BLOCKED_REFERENCES)? - .ok_or_else( - || vortex_err!(AssertionFailed: "FoR blocked references slot is missing"), - )? + .ok_or_else(|| vortex_err!("FoR blocked references slot is missing"))? .execute_scalar(chunk, ctx)? } }; diff --git a/encodings/fastlanes/src/rle/array/mod.rs b/encodings/fastlanes/src/rle/array/mod.rs index 0e19783314e..626d2fadd1d 100644 --- a/encodings/fastlanes/src/rle/array/mod.rs +++ b/encodings/fastlanes/src/rle/array/mod.rs @@ -60,7 +60,7 @@ impl RLEData { pub fn try_new(offset: usize) -> VortexResult { vortex_ensure!( offset < 1024, - InvalidArgument: "Offset must be smaller than 1024, got {}", + "Offset must be smaller than 1024, got {}", offset ); Ok(Self { offset }) diff --git a/encodings/fastlanes/src/rle/array/rle_decompress.rs b/encodings/fastlanes/src/rle/array/rle_decompress.rs index 065e53aea2d..0c841b7cba6 100644 --- a/encodings/fastlanes/src/rle/array/rle_decompress.rs +++ b/encodings/fastlanes/src/rle/array/rle_decompress.rs @@ -43,7 +43,7 @@ pub fn rle_decompress(array: &RLEArray, ctx: &mut ExecutionCtx) -> VortexResult< PType::U8 => rle_decode_typed::(array, &values_idx_offsets, ctx), PType::U16 => rle_decode_typed::(array, &values_idx_offsets, ctx), _ => vortex_panic!( - AssertionFailed: "Unsupported index type for RLE decoding: {}", + "Unsupported index type for RLE decoding: {}", array.indices().dtype().as_ptype() ), } @@ -68,12 +68,12 @@ where // offsets must be non-decreasing and span at most `values.len()` values. vortex_ensure!( values_idx_offsets.is_sorted(), - InvalidArgument: "RLE values_idx_offsets must be non-decreasing" + "RLE values_idx_offsets must be non-decreasing" ); if let (Some(&first), Some(&last)) = (values_idx_offsets.first(), values_idx_offsets.last()) { vortex_ensure!( last - first <= values.len() as u64, - InvalidArgument: "RLE values_idx_offsets span {} values but only {} are present", + "RLE values_idx_offsets span {} values but only {} are present", last - first, values.len() ); @@ -110,7 +110,7 @@ where .vortex_expect("There can be at most 1024 values in RLE chunk"); vortex_ensure!( num_chunk_values > 0, - InvalidArgument: "RLE chunk {chunk_idx} references no values" + "RLE chunk {chunk_idx} references no values" ); // SAFETY: `MaybeUninit` and `T` have the same layout. @@ -201,7 +201,7 @@ where .unwrap_or_default(); vortex_ensure!( max_index < num_chunk_values as usize, - OutOfBounds: "RLE index {max_index} out of bounds for chunk {chunk_idx} with {num_chunk_values} values" + "RLE index {max_index} out of bounds for chunk {chunk_idx} with {num_chunk_values} values" ); // SAFETY: just checked that every index in the chunk is below `num_chunk_values`, // which the caller's offset validation bounds by `chunk_values.len()`. diff --git a/encodings/fastlanes/src/rle/probe.rs b/encodings/fastlanes/src/rle/probe.rs index 3deca8ea2cd..8f80aa09228 100644 --- a/encodings/fastlanes/src/rle/probe.rs +++ b/encodings/fastlanes/src/rle/probe.rs @@ -31,7 +31,7 @@ pub(crate) fn scalar_at( let (mut retained, mut children) = state.split(); let code = children .slot(RLESlots::INDICES)? - .ok_or_else(|| vortex_err!(InvalidArgument: "RLE indices slot is missing"))? + .ok_or_else(|| vortex_err!("RLE indices slot is missing"))? .execute_scalar(logical_index, ctx)?; let Some(code) = code.as_primitive().as_::() else { return Ok(Scalar::null(array.dtype().clone())); @@ -47,7 +47,7 @@ pub(crate) fn scalar_at( let value = read_offset( children .slot(RLESlots::VALUES_IDX_OFFSETS)? - .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offsets slot is missing"))? + .ok_or_else(|| vortex_err!("RLE offsets slot is missing"))? .execute_scalar(0, ctx)?, )?; if let Some(state) = retained.as_mut() { @@ -59,18 +59,18 @@ pub(crate) fn scalar_at( read_offset( children .slot(RLESlots::VALUES_IDX_OFFSETS)? - .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offsets slot is missing"))? + .ok_or_else(|| vortex_err!("RLE offsets slot is missing"))? .execute_scalar(chunk, ctx)?, )? .checked_sub(base) - .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offsets precede the slice base"))? + .ok_or_else(|| vortex_err!("RLE offsets precede the slice base"))? }; let value_index = offset .checked_add(code) - .ok_or_else(|| vortex_err!(Overflow: "RLE value index overflow"))?; + .ok_or_else(|| vortex_err!("RLE value index overflow"))?; let scalar = children .slot(RLESlots::VALUES)? - .ok_or_else(|| vortex_err!(InvalidArgument: "RLE values slot is missing"))? + .ok_or_else(|| vortex_err!("RLE values slot is missing"))? .execute_scalar(value_index, ctx)?; Scalar::try_new(array.dtype().clone(), scalar.into_value()) } @@ -79,7 +79,7 @@ fn read_offset(scalar: Scalar) -> VortexResult { scalar .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(InvalidArgument: "RLE offset must be a non-null usize")) + .ok_or_else(|| vortex_err!("RLE offset must be a non-null usize")) } #[cfg(test)] diff --git a/encodings/fastlanes/src/rle/vtable/mod.rs b/encodings/fastlanes/src/rle/vtable/mod.rs index 40f4766b5f8..9e4e11a8a12 100644 --- a/encodings/fastlanes/src/rle/vtable/mod.rs +++ b/encodings/fastlanes/src/rle/vtable/mod.rs @@ -107,7 +107,7 @@ impl VTable for RLE { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "RLEArray buffer index {idx} out of bounds") + vortex_panic!("RLEArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -163,7 +163,7 @@ impl VTable for RLE { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - InvalidArgument: "RLEArray expects 0 buffers, got {}", + "RLEArray expects 0 buffers, got {}", buffers.len() ); let metadata = RLEMetadata::decode(metadata)?; @@ -277,50 +277,50 @@ fn validate_parts( values.dtype(), DType::Primitive(_, Nullability::NonNullable) ), - MismatchedTypes: "RLE values must be a non-nullable primitive type, got {}", + "RLE values must be a non-nullable primitive type, got {}", values.dtype() ); vortex_ensure!( matches!(indices.dtype().as_ptype(), PType::U8 | PType::U16), - MismatchedTypes: "RLE indices must be u8 or u16, got {}", + "RLE indices must be u8 or u16, got {}", indices.dtype() ); vortex_ensure!( values_idx_offsets.dtype().is_unsigned_int() && !values_idx_offsets.dtype().is_nullable(), - MismatchedTypes: "RLE value idx offsets must be non-nullable unsigned integer, got {}", + "RLE value idx offsets must be non-nullable unsigned integer, got {}", values_idx_offsets.dtype() ); vortex_ensure!( indices.len().is_multiple_of(crate::FL_CHUNK_SIZE), - InvalidArgument: "RLE indices length must be a multiple of {}, got {}", + "RLE indices length must be a multiple of {}, got {}", crate::FL_CHUNK_SIZE, indices.len() ); vortex_ensure!( offset + length <= indices.len(), - InvalidArgument: "RLE offset + length, {offset} + {length}, must not exceed the indices length {}", + "RLE offset + length, {offset} + {length}, must not exceed the indices length {}", indices.len() ); vortex_ensure_eq!( indices.len().div_ceil(crate::FL_CHUNK_SIZE), values_idx_offsets.len(), - InvalidArgument: "RLE must have one value idx offset per chunk" + "RLE must have one value idx offset per chunk" ); vortex_ensure!( indices.len() >= values.len(), - InvalidArgument: "RLE must have at least as many indices as values, got {} indices and {} values", + "RLE must have at least as many indices as values, got {} indices and {} values", indices.len(), values.len() ); let expected_dtype = DType::Primitive(values.dtype().as_ptype(), indices.dtype().nullability()); - vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes: "RLE dtype mismatch"); + vortex_ensure_eq!(dtype, &expected_dtype, "RLE dtype mismatch"); Ok(()) } diff --git a/encodings/fsst/src/array.rs b/encodings/fsst/src/array.rs index ef3d723c36d..ae8d909b052 100644 --- a/encodings/fsst/src/array.rs +++ b/encodings/fsst/src/array.rs @@ -83,9 +83,8 @@ pub struct FSSTMetadata { impl FSSTMetadata { pub fn get_uncompressed_lengths_ptype(&self) -> VortexResult { - PType::try_from(self.uncompressed_lengths_ptype).map_err( - |_| vortex_err!(InvalidArgument: "Invalid PType {}", self.uncompressed_lengths_ptype), - ) + PType::try_from(self.uncompressed_lengths_ptype) + .map_err(|_| vortex_err!("Invalid PType {}", self.uncompressed_lengths_ptype)) } } @@ -157,7 +156,7 @@ impl VTable for FSST { .into_byte_buffer(), ), 2 => array.codes_bytes_handle().clone(), - _ => vortex_panic!(OutOfBounds: "FSSTArray buffer index {idx} out of bounds"), + _ => vortex_panic!("FSSTArray buffer index {idx} out of bounds"), } } @@ -166,7 +165,7 @@ impl VTable for FSST { 0 => Some("symbols".to_string()), 1 => Some("symbol_lengths".to_string()), 2 => Some("compressed_codes".to_string()), - _ => vortex_panic!(OutOfBounds: "FSSTArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!("FSSTArray buffer_name index {idx} out of bounds"), } } @@ -175,7 +174,7 @@ impl VTable for FSST { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 3, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 3); let symbols = Buffer::::from_byte_buffer(buffers[0].clone().try_to_host_sync()?); let symbol_lengths = Buffer::::from_byte_buffer(buffers[1].clone().try_to_host_sync()?); let data = FSSTData::try_new(symbols, symbol_lengths, buffers[2].clone(), array.len())?; @@ -280,7 +279,7 @@ impl VTable for FSST { let validity = children.get(2, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "Expected 2 or 3 children, got {}", children.len()); + vortex_bail!("Expected 2 or 3 children, got {}", children.len()); }; FSSTData::validate_parts( @@ -310,7 +309,7 @@ impl VTable for FSST { } vortex_bail!( - MismatchedTypes: "InvalidArgument: Expected 2 or 3 buffers, got {}", + "InvalidArgument: Expected 2 or 3 buffers, got {}", buffers.len() ); } @@ -350,7 +349,7 @@ impl VTable for FSST { // canonicalize-then-append fallback — it would decode to a `VarBinView` only for // `VarBinView::append_to_builder` to reject the same remainder. let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for FSST requires a variable-binary builder") + vortex_bail!("append_to_builder for FSST requires a variable-binary builder") }; // Decompress the whole block of data into a new buffer, which the builder adopts as a @@ -511,13 +510,13 @@ impl FSSTSymbolTable { vortex_ensure!( padded_symbols.len() == FSST_SYMBOL_TABLE_LEN && padded_symbol_lengths.len() == FSST_SYMBOL_TABLE_LEN, - InvalidArgument: "padded symbol table must have exactly {FSST_SYMBOL_TABLE_LEN} entries, found {} symbols and {} symbol lengths", + "padded symbol table must have exactly {FSST_SYMBOL_TABLE_LEN} entries, found {} symbols and {} symbol lengths", padded_symbols.len(), padded_symbol_lengths.len() ); vortex_ensure!( n_symbols <= FSST_SYMBOL_TABLE_LEN, - InvalidArgument: "n_symbols must be <= {FSST_SYMBOL_TABLE_LEN}, found {n_symbols}" + "n_symbols must be <= {FSST_SYMBOL_TABLE_LEN}, found {n_symbols}" ); Ok(Self { padded_symbols, @@ -667,14 +666,14 @@ impl FSST { ctx: &mut ExecutionCtx, ) -> VortexResult> { if children.len() != 2 { - vortex_bail!(InvalidArgument: "Expected 2 children, got {}", children.len()); + vortex_bail!("Expected 2 children, got {}", children.len()); } let codes = children.get(0, &DType::Binary(dtype.nullability()), len)?; let codes: VarBinArray = codes .as_opt::() .ok_or_else(|| { vortex_err!( - MismatchedTypes: "Expected VarBinArray for codes, got {}", + "Expected VarBinArray for codes, got {}", codes.encoding_id() ) })? @@ -764,11 +763,11 @@ impl FSSTData { vortex_ensure_eq!( symbols.len(), symbol_lengths.len(), - InvalidArgument: "symbols and symbol_lengths arrays must have same length" + "symbols and symbol_lengths arrays must have same length" ); vortex_ensure!( symbols.len() <= FSST_SYMBOL_TABLE_LEN, - InvalidArgument: "symbols array must have length <= {FSST_SYMBOL_TABLE_LEN}, found {}", + "symbols array must have length <= {FSST_SYMBOL_TABLE_LEN}, found {}", symbols.len() ); let n_symbols = symbols.len(); @@ -817,15 +816,15 @@ impl FSSTData { ) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - MismatchedTypes: "FSST arrays must be Binary or Utf8, found {dtype}" + "FSST arrays must be Binary or Utf8, found {dtype}" ); if symbols.len() > FSST_SYMBOL_TABLE_LEN { - vortex_bail!(InvalidArgument: "symbols array must have length <= {FSST_SYMBOL_TABLE_LEN}"); + vortex_bail!("symbols array must have length <= {FSST_SYMBOL_TABLE_LEN}"); } if symbols.len() != symbol_lengths.len() { - vortex_bail!(InvalidArgument: "symbols and symbol_lengths arrays must have same length"); + vortex_bail!("symbols and symbol_lengths arrays must have same length"); } Self::validate_symbol_lengths(symbol_lengths)?; @@ -833,24 +832,30 @@ impl FSSTData { // codes_offsets.len() - 1 == number of elements let codes_len = codes_offsets.len().saturating_sub(1); if codes_len != len { - vortex_bail!(InvalidArgument: "codes must have same len as outer array"); + vortex_bail!("codes must have same len as outer array"); } if uncompressed_lengths.len() != len { - vortex_bail!(InvalidArgument: "uncompressed_lengths must be same len as codes"); + vortex_bail!("uncompressed_lengths must be same len as codes"); } if !uncompressed_lengths.dtype().is_int() || uncompressed_lengths.dtype().is_nullable() { - vortex_bail!(InvalidArgument: "uncompressed_lengths must have integer type and cannot be nullable, found {}", uncompressed_lengths.dtype()); + vortex_bail!( + "uncompressed_lengths must have integer type and cannot be nullable, found {}", + uncompressed_lengths.dtype() + ); } // Offsets must be non-nullable integer. if !codes_offsets.dtype().is_int() || codes_offsets.dtype().is_nullable() { - vortex_bail!(InvalidArgument: "codes offsets must be non-nullable integer type, found {}", codes_offsets.dtype()); + vortex_bail!( + "codes offsets must be non-nullable integer type, found {}", + codes_offsets.dtype() + ); } if codes_nullability != dtype.nullability() { - vortex_bail!(InvalidArgument: "codes nullability must match outer dtype nullability"); + vortex_bail!("codes nullability must match outer dtype nullability"); } Ok(()) @@ -870,7 +875,7 @@ impl FSSTData { (&codes_offsets.execute_scalar(codes_offsets.len() - 1, ctx)?).try_into()?; vortex_ensure!( last_offset <= codes_bytes.len(), - InvalidArgument: "Last codes offset {} exceeds codes bytes length {}", + "Last codes offset {} exceeds codes bytes length {}", last_offset, codes_bytes.len() ); @@ -883,12 +888,14 @@ impl FSSTData { let mut expected = 2; for (idx, &len) in symbol_lengths.iter().enumerate() { if len > 8 || len == 0 { - vortex_bail!(InvalidArgument: "symbol length at index {idx} must be between 1 and 8, found {len}"); + vortex_bail!("symbol length at index {idx} must be between 1 and 8, found {len}"); } if expected == 1 { if len != 1 { - vortex_bail!(InvalidArgument: "symbol length at index {idx} must be 1 after one-byte symbols begin, found {len}"); + vortex_bail!( + "symbol length at index {idx} must be 1 after one-byte symbols begin, found {len}" + ); } } else { if len == 1 { @@ -896,7 +903,9 @@ impl FSSTData { } if len < expected { - vortex_bail!(InvalidArgument: "symbol length at index {idx} violates FSST symbol table ordering"); + vortex_bail!( + "symbol length at index {idx} violates FSST symbol table ordering" + ); } expected = len; } @@ -1100,7 +1109,7 @@ mod test { let sliced = fsst_array .slice(1..3)? .try_downcast::() - .map_err(|_| vortex_err!(AssertionFailed: "slice must return an FSST array"))?; + .map_err(|_| vortex_err!("slice must return an FSST array"))?; let sliced_compressor_ptr = sliced.compressor() as *const Compressor; assert_eq!(compressor_ptr, sliced_compressor_ptr); @@ -1204,7 +1213,7 @@ mod test { let padded = deserialized .clone() .try_downcast::() - .map_err(|_| vortex_err!(Serde: "deserialize must return an FSST array"))?; + .map_err(|_| vortex_err!("deserialize must return an FSST array"))?; assert_eq!(padded.padded_symbols().len(), FSST_SYMBOL_TABLE_LEN); assert_eq!(padded.n_symbols(), fsst_array.symbols().len()); diff --git a/encodings/fsst/src/canonical.rs b/encodings/fsst/src/canonical.rs index 49cb4166c04..448acdf3cc6 100644 --- a/encodings/fsst/src/canonical.rs +++ b/encodings/fsst/src/canonical.rs @@ -88,17 +88,17 @@ impl FsstDecodePlan { offsets.last().and_then(ToPrimitive::to_usize), ) }); - let (first_offset, last_offset) = first_offset.zip(last_offset).ok_or_else( - || vortex_err!(Overflow: "FSST codes offsets are missing, negative or overflow usize"), - )?; + let (first_offset, last_offset) = first_offset.zip(last_offset).ok_or_else(|| { + vortex_err!("FSST codes offsets are missing, negative or overflow usize") + })?; let codes = fsst_array.codes_bytes(); vortex_ensure!( first_offset <= last_offset, - InvalidArgument: "FSST first codes offset {first_offset} exceeds last codes offset {last_offset}" + "FSST first codes offset {first_offset} exceeds last codes offset {last_offset}" ); vortex_ensure!( last_offset <= codes.len(), - InvalidArgument: "FSST last codes offset {last_offset} exceeds codes bytes length {}", + "FSST last codes offset {last_offset} exceeds codes bytes length {}", codes.len() ); let codes = codes.slice(first_offset..last_offset); @@ -113,15 +113,13 @@ impl FsstDecodePlan { .iter() .try_fold(0usize, |acc, &x| acc.checked_add(x.to_usize()?)) }) - .ok_or_else( - || vortex_err!(Overflow: "FSST uncompressed lengths are negative or overflow"), - )?; + .ok_or_else(|| vortex_err!("FSST uncompressed lengths are negative or overflow"))?; // Stored lengths size the output buffer, so bound them by the codes: // symbols emit 1 to 8 bytes; escapes use two code bytes per output byte. vortex_ensure!( codes.len().div_ceil(2) <= total_size && total_size <= codes.len().saturating_mul(8), - Serde: "FSST recorded length {total_size} is impossible for {} code bytes", + "FSST recorded length {total_size} is impossible for {} code bytes", codes.len() ); @@ -144,7 +142,7 @@ impl FsstDecodePlan { out: &mut [MaybeUninit], ) -> VortexResult { let len = decompressor.decompress_into(self.codes.as_slice(), out); - vortex_ensure_eq!(len, self.total_size, Serde: "FSST decoded length mismatch"); + vortex_ensure_eq!(len, self.total_size, "FSST decoded length mismatch"); Ok(len) } } diff --git a/encodings/fsst/src/compress.rs b/encodings/fsst/src/compress.rs index e58c6fb793c..bb786e47175 100644 --- a/encodings/fsst/src/compress.rs +++ b/encodings/fsst/src/compress.rs @@ -60,7 +60,7 @@ pub fn fsst_compress( compress_varbin_array(varbin, compressor, ctx) } else { vortex_bail!( - InvalidArgument: "fsst_compress requires VarBinView or VarBin encoding, got {}", + "fsst_compress requires VarBinView or VarBin encoding, got {}", array.encoding_id() ) } @@ -76,7 +76,7 @@ pub fn fsst_train_compressor(array: &ArrayRef, ctx: &mut ExecutionCtx) -> Vortex train_varbin_array(varbin, ctx) } else { vortex_bail!( - InvalidArgument: "fsst_train_compressor requires VarBinView or VarBin encoding, got {}", + "fsst_train_compressor requires VarBinView or VarBin encoding, got {}", array.encoding_id() ) } diff --git a/encodings/fsst/src/compute/compare.rs b/encodings/fsst/src/compute/compare.rs index bff8c0ab354..53422acebee 100644 --- a/encodings/fsst/src/compute/compare.rs +++ b/encodings/fsst/src/compute/compare.rs @@ -53,7 +53,7 @@ fn compare_fsst_constant( .as_utf8() .is_empty() .vortex_expect("RHS should not be null"), - _ => vortex_bail!(MismatchedTypes: "VarBinArray can only have type of Binary or Utf8"), + _ => vortex_bail!("VarBinArray can only have type of Binary or Utf8"), }; if is_rhs_empty { let buffer = match operator { diff --git a/encodings/fsst/src/dfa/flat_contains.rs b/encodings/fsst/src/dfa/flat_contains.rs index 5979e9884f3..a33b82b4a0a 100644 --- a/encodings/fsst/src/dfa/flat_contains.rs +++ b/encodings/fsst/src/dfa/flat_contains.rs @@ -101,7 +101,7 @@ impl FlatContainsDfa { ) -> VortexResult { if needle.len() > Self::MAX_NEEDLE_LEN { vortex_bail!( - InvalidArgument: "needle length {} exceeds maximum {} for flat contains DFA", + "needle length {} exceeds maximum {} for flat contains DFA", needle.len(), Self::MAX_NEEDLE_LEN ); diff --git a/encodings/fsst/src/dfa/prefix.rs b/encodings/fsst/src/dfa/prefix.rs index de177c4a6c0..5c40affd7a1 100644 --- a/encodings/fsst/src/dfa/prefix.rs +++ b/encodings/fsst/src/dfa/prefix.rs @@ -61,7 +61,7 @@ impl FlatPrefixDfa { ) -> VortexResult { if prefix.len() > Self::MAX_PREFIX_LEN { vortex_bail!( - InvalidArgument: "prefix length {} exceeds maximum {} for flat prefix DFA", + "prefix length {} exceeds maximum {} for flat prefix DFA", prefix.len(), Self::MAX_PREFIX_LEN ); diff --git a/encodings/fsst/src/slice.rs b/encodings/fsst/src/slice.rs index b31d2e264a9..c2b2e320d31 100644 --- a/encodings/fsst/src/slice.rs +++ b/encodings/fsst/src/slice.rs @@ -27,7 +27,7 @@ impl SliceReduce for FSST { .codes() .slice(range.clone())? .try_downcast::() - .map_err(|_| vortex_err!(AssertionFailed: "cannot fail conversion"))?, + .map_err(|_| vortex_err!("cannot fail conversion"))?, array.uncompressed_lengths().slice(range)?, ) } diff --git a/encodings/onpair/src/array.rs b/encodings/onpair/src/array.rs index 3bd099ee36c..a521c1bc18c 100644 --- a/encodings/onpair/src/array.rs +++ b/encodings/onpair/src/array.rs @@ -104,9 +104,8 @@ pub struct OnPairMetadata { impl OnPairMetadata { /// Decode the recorded [`PType`] of the `uncompressed_lengths` slot child. pub fn get_uncompressed_lengths_ptype(&self) -> VortexResult { - PType::try_from(self.uncompressed_lengths_ptype).map_err( - |_| vortex_err!(InvalidArgument: "Invalid PType {}", self.uncompressed_lengths_ptype), - ) + PType::try_from(self.uncompressed_lengths_ptype) + .map_err(|_| vortex_err!("Invalid PType {}", self.uncompressed_lengths_ptype)) } } @@ -234,7 +233,7 @@ fn build_dictionary( offsets: Buffer, ) -> VortexResult> { CompactDictionary::validate_safety(OnPairDictionaryStorage { bytes, offsets }) - .map_err(|e| vortex_err!(InvalidArgument: "Unsafe OnPair dictionary: {e}")) + .map_err(|e| vortex_err!("Unsafe OnPair dictionary: {e}")) } /// A safety-validated dictionary built from host-materialized parts, owned @@ -414,23 +413,23 @@ fn validate_parts( ) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - MismatchedTypes: "OnPair arrays must be Binary or Utf8, found {dtype}" + "OnPair arrays must be Binary or Utf8, found {dtype}" ); if !dict_offsets.dtype().is_int() || dict_offsets.dtype().is_nullable() { - vortex_bail!(InvalidArgument: "dict_offsets must be non-nullable integer"); + vortex_bail!("dict_offsets must be non-nullable integer"); } if !codes.dtype().is_int() || codes.dtype().is_nullable() { - vortex_bail!(InvalidArgument: "codes must be non-nullable integer"); + vortex_bail!("codes must be non-nullable integer"); } if !codes_offsets.dtype().is_int() || codes_offsets.dtype().is_nullable() { - vortex_bail!(InvalidArgument: "codes_offsets must be non-nullable integer"); + vortex_bail!("codes_offsets must be non-nullable integer"); } if !uncompressed_lengths.dtype().is_int() || uncompressed_lengths.dtype().is_nullable() { - vortex_bail!(InvalidArgument: "uncompressed_lengths must be non-nullable integer"); + vortex_bail!("uncompressed_lengths must be non-nullable integer"); } if codes_offsets.len() != uncompressed_lengths.len() + 1 { - vortex_bail!(InvalidArgument: + vortex_bail!( "codes_offsets.len ({}) != uncompressed_lengths.len + 1 ({})", codes_offsets.len(), uncompressed_lengths.len() + 1 @@ -465,7 +464,7 @@ impl VTable for OnPair { s.uncompressed_lengths, )?; if s.uncompressed_lengths.len() != len { - vortex_bail!(InvalidArgument: "uncompressed_lengths must have same len as outer array"); + vortex_bail!("uncompressed_lengths must have same len as outer array"); } Ok(()) } @@ -477,14 +476,14 @@ impl VTable for OnPair { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.dict_bytes_handle().clone(), - _ => vortex_panic!(OutOfBounds: "OnPairArray buffer index {idx} out of bounds"), + _ => vortex_panic!("OnPairArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("dict_bytes".to_string()), - _ => vortex_panic!(OutOfBounds: "OnPairArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!("OnPairArray buffer_name index {idx} out of bounds"), } } @@ -493,7 +492,7 @@ impl VTable for OnPair { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 1); let mut data = array.data().clone(); data.dict_bytes = buffers[0].clone(); // The replacement blob may differ from the one the memoized dictionary @@ -514,7 +513,7 @@ impl VTable for OnPair { _session: &VortexSession, ) -> VortexResult>> { let dict_size = u32::try_from(array.dict_offsets().len().saturating_sub(1)) - .map_err(|_| vortex_err!(Overflow: "OnPair dict_size exceeds u32"))?; + .map_err(|_| vortex_err!("OnPair dict_size exceeds u32"))?; let codes_len = array.codes().len() as u64; Ok(Some( OnPairMetadata { @@ -539,7 +538,7 @@ impl VTable for OnPair { _session: &VortexSession, ) -> VortexResult> { if buffers.len() != 1 { - vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); + vortex_bail!("Expected 1 buffer, got {}", buffers.len()); } let metadata = OnPairMetadata::decode(metadata)?; let uncompressed_ptype = metadata.get_uncompressed_lengths_ptype()?; @@ -547,21 +546,19 @@ impl VTable for OnPair { // Slot children do not persist their own lengths, so metadata records // the dictionary and code-stream sizes needed to deserialize them. let dict_offsets_len = metadata.dict_size as usize + 1; - let codes_len = usize::try_from(metadata.codes_len).map_err( - |_| vortex_err!(Overflow: "codes_len {} overflows usize", metadata.codes_len), - )?; + let codes_len = usize::try_from(metadata.codes_len) + .map_err(|_| vortex_err!("codes_len {} overflows usize", metadata.codes_len))?; // The cascading compressor may have narrowed any of these integer // children to a tighter ptype; the recorded ptype tells the framework // exactly which dtype to materialise as. let dict_offsets_ptype = PType::try_from(metadata.dict_offsets_ptype).map_err(|_| { - vortex_err!(InvalidArgument: "invalid dict_offsets_ptype {}", metadata.dict_offsets_ptype) + vortex_err!("invalid dict_offsets_ptype {}", metadata.dict_offsets_ptype) })?; - let codes_ptype = PType::try_from(metadata.codes_ptype).map_err( - |_| vortex_err!(InvalidArgument: "invalid codes_ptype {}", metadata.codes_ptype), - )?; + let codes_ptype = PType::try_from(metadata.codes_ptype) + .map_err(|_| vortex_err!("invalid codes_ptype {}", metadata.codes_ptype))?; let codes_offsets_ptype = PType::try_from(metadata.codes_offsets_ptype).map_err(|_| { vortex_err!( - InvalidArgument: "invalid codes_offsets_ptype {}", + "invalid codes_offsets_ptype {}", metadata.codes_offsets_ptype ) })?; @@ -588,7 +585,7 @@ impl VTable for OnPair { let validity = match children.len() { 4 => Validity::from(dtype.nullability()), 5 => Validity::Array(children.get(4, &Validity::DTYPE, len)?), - other => vortex_bail!(InvalidArgument: "Expected 4 or 5 children, got {other}"), + other => vortex_bail!("Expected 4 or 5 children, got {other}"), }; let data = OnPairData::new(buffers[0].clone()); @@ -656,7 +653,7 @@ impl VTable for OnPair { // canonicalize-then-append fallback — it would decode to a `VarBinView` only for // `VarBinView::append_to_builder` to reject the same remainder. let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for OnPair requires a variable-binary builder") + vortex_bail!("append_to_builder for OnPair requires a variable-binary builder") }; // Decode the whole code stream into a new buffer, which the builder adopts as a data diff --git a/encodings/onpair/src/canonical.rs b/encodings/onpair/src/canonical.rs index a6217144cea..f31fae71cd0 100644 --- a/encodings/onpair/src/canonical.rs +++ b/encodings/onpair/src/canonical.rs @@ -76,9 +76,7 @@ impl<'a> OnPairDecodePlan<'a> { .iter() .try_fold(0usize, |acc, &l| acc.checked_add(l.to_usize()?)) }) - .ok_or_else( - || vortex_err!(Overflow: "OnPair uncompressed lengths are negative or overflow"), - )?; + .ok_or_else(|| vortex_err!("OnPair uncompressed lengths are negative or overflow"))?; // `codes_offsets` holds the per-row code boundaries and may itself be a // sliced or filtered view of the original. Its first and last entries @@ -94,11 +92,11 @@ impl<'a> OnPairDecodePlan<'a> { let code_end = code_boundary_at(codes_offsets, array.len(), ctx)?; vortex_ensure!( code_start <= code_end, - InvalidArgument: "OnPair codes_offsets must be nondecreasing" + "OnPair codes_offsets must be nondecreasing" ); vortex_ensure!( code_end <= array.codes().len(), - InvalidArgument: "OnPair codes_offsets end {} exceeds codes len {}", + "OnPair codes_offsets end {} exceeds codes len {}", code_end, array.codes().len() ); @@ -106,7 +104,7 @@ impl<'a> OnPairDecodePlan<'a> { let n_codes = code_end - code_start; vortex_ensure!( n_codes <= total_size && total_size <= n_codes.saturating_mul(onpair::MAX_TOKEN_SIZE), - Serde: "OnPair recorded length {total_size} is impossible for {n_codes} codes" + "OnPair recorded length {total_size} is impossible for {n_codes} codes" ); // Slice the `codes` child to that window *before* unpacking it, so a sliced @@ -136,14 +134,14 @@ impl<'a> OnPairDecodePlan<'a> { let written = match onpair::try_decode_into(self.codes.as_slice(), self.dict, out) { Ok(written) => written, Err(_) => { - vortex_bail!(Serde: "OnPair codes decode to more bytes than uncompressed_lengths records") + vortex_bail!("OnPair codes decode to more bytes than uncompressed_lengths records") } }; vortex_ensure_eq!( written, self.total_size, - Serde: "OnPair codes decoded length must match uncompressed_lengths" + "OnPair codes decoded length must match uncompressed_lengths" ); Ok(written) } diff --git a/encodings/onpair/src/compute/compare.rs b/encodings/onpair/src/compute/compare.rs index 1af2d261613..fe8e6a0cec3 100644 --- a/encodings/onpair/src/compute/compare.rs +++ b/encodings/onpair/src/compute/compare.rs @@ -211,7 +211,7 @@ mod tests { let mut ctx = SESSION.create_execution_ctx(); let arr = onpair_compress(input.as_array(), DEFAULT_CONFIG, &mut ctx)? .try_downcast::() - .map_err(|array| vortex_err!(MismatchedTypes: "expected OnPair array, got {}", array.encoding_id()))?; + .map_err(|array| vortex_err!("expected OnPair array, got {}", array.encoding_id()))?; let rhs = ConstantArray::new("hello", arr.len()).into_array(); let eq = @@ -254,7 +254,7 @@ mod tests { assert!(sliced.is::(), "slice dropped OnPair encoding"); let sliced = sliced .try_downcast::() - .map_err(|_| vortex_err!(AssertionFailed: "sliced array was not OnPair"))?; + .map_err(|_| vortex_err!("sliced array was not OnPair"))?; let rhs = ConstantArray::new("hello", sliced.len()).into_array(); let eq = ::compare( diff --git a/encodings/onpair/src/decode.rs b/encodings/onpair/src/decode.rs index ee4fe22f224..a6071757e23 100644 --- a/encodings/onpair/src/decode.rs +++ b/encodings/onpair/src/decode.rs @@ -52,9 +52,9 @@ pub(crate) fn collect_widened_range( primitive.as_slice::

()[range] .iter() .map(|&value| { - T::from(value).ok_or_else( - || vortex_err!(Overflow: "OnPair value {value} does not fit {}", T::PTYPE), - ) + T::from(value).ok_or_else(|| { + vortex_err!("OnPair value {value} does not fit {}", T::PTYPE) + }) }) .collect::>>() .map(Buffer::from) @@ -78,7 +78,7 @@ pub(crate) fn code_boundary_at( .as_primitive() .as_opt::() .flatten() - .ok_or_else(|| vortex_err!(InvalidArgument: "OnPair codes_offsets[{index}] is null, negative, or too large")) + .ok_or_else(|| vortex_err!("OnPair codes_offsets[{index}] is null, negative, or too large")) } /// A validated, materialised window over an array's `codes`: the widened @@ -122,17 +122,17 @@ pub(crate) fn collect_codes_window( vortex_ensure_eq!( offsets.len(), len + 1, - InvalidArgument: "OnPair codes_offsets must have len + 1 entries" + "OnPair codes_offsets must have len + 1 entries" ); vortex_ensure!( offsets.is_sorted(), - InvalidArgument: "OnPair codes_offsets must be nondecreasing" + "OnPair codes_offsets must be nondecreasing" ); let code_start = usize::try_from(offsets[0]).vortex_expect("code offset fits usize"); let code_end = usize::try_from(offsets[len]).vortex_expect("code offset fits usize"); vortex_ensure!( code_end <= array.codes().len(), - InvalidArgument: "OnPair codes_offsets end {} exceeds codes len {}", + "OnPair codes_offsets end {} exceeds codes len {}", code_end, array.codes().len() ); diff --git a/encodings/onpair/src/ops.rs b/encodings/onpair/src/ops.rs index e2ec3e4a5fe..33e64225ab0 100644 --- a/encodings/onpair/src/ops.rs +++ b/encodings/onpair/src/ops.rs @@ -48,23 +48,21 @@ impl OperationsVTable for OnPair { .as_opt::() .flatten() .ok_or_else(|| { - vortex_err!( - InvalidArgument: "OnPair uncompressed_lengths[{index}] is null, negative, or too large" - ) + vortex_err!("OnPair uncompressed_lengths[{index}] is null, negative, or too large") })?; // The stored length controls allocation; each code emits 1 to MAX_TOKEN_SIZE bytes. vortex_ensure!( codes.len() <= len && len <= codes.len().saturating_mul(onpair::MAX_TOKEN_SIZE), - Serde: "OnPair row {index} recorded length {len} is impossible for {} codes", + "OnPair row {index} recorded length {len} is impossible for {} codes", codes.len() ); let mut buf: Vec = Vec::with_capacity(len); let written = match onpair::try_decode_into(codes.as_slice(), dict, buf.spare_capacity_mut()) { Ok(written) => written, - Err(_) => vortex_bail!(Serde: "OnPair row {index} exceeds its recorded length"), + Err(_) => vortex_bail!("OnPair row {index} exceeds its recorded length"), }; - vortex_ensure_eq!(written, len, Serde: "OnPair row {index} decoded length mismatch"); + vortex_ensure_eq!(written, len, "OnPair row {index} decoded length mismatch"); // SAFETY: `try_decode_into` initialised exactly `written` bytes. unsafe { buf.set_len(written) }; Ok(varbin_scalar(ByteBuffer::from(buf), array.dtype())) diff --git a/encodings/onpair/src/tests.rs b/encodings/onpair/src/tests.rs index f463f5150a1..aa735b0524a 100644 --- a/encodings/onpair/src/tests.rs +++ b/encodings/onpair/src/tests.rs @@ -51,7 +51,7 @@ fn compress_onpair( onpair_compress(array, DEFAULT_CONFIG, ctx)? .try_downcast::() .map_err(|array| { - vortex_error::vortex_err!(MismatchedTypes: "expected OnPair array, got {}", array.encoding_id()) + vortex_error::vortex_err!("expected OnPair array, got {}", array.encoding_id()) }) } @@ -391,7 +391,7 @@ fn test_onpair_filter_shares_dict() -> vortex_error::VortexResult<()> { ); let typed = filtered .try_downcast::() - .map_err(|_| vortex_error::vortex_err!(AssertionFailed: "filter result was not OnPair"))?; + .map_err(|_| vortex_error::vortex_err!("filter result was not OnPair"))?; assert_eq!(typed.dict_bytes().as_ptr(), arr.dict_bytes().as_ptr()); assert_eq!(typed.dict_bytes().as_slice(), arr.dict_bytes().as_slice()); assert_eq!(typed.dict_offsets().len(), arr.dict_offsets().len()); @@ -487,7 +487,7 @@ fn test_onpair_filter_with_narrowed_codes_offsets_u16() -> vortex_error::VortexR .expect("OnPair filter must return Some"); let typed = filtered .try_downcast::() - .map_err(|_| vortex_error::vortex_err!(AssertionFailed: "filter result was not OnPair"))?; + .map_err(|_| vortex_error::vortex_err!("filter result was not OnPair"))?; assert_eq!(typed.len(), expected.len()); assert_arrays_eq!(typed, VarBinViewArray::from_iter_str(&expected), &mut ctx); @@ -623,7 +623,7 @@ fn test_onpair_take_shares_dict() -> vortex_error::VortexResult<()> { .expect("OnPair take must return Some"); let typed = taken .try_downcast::() - .map_err(|_| vortex_error::vortex_err!(AssertionFailed: "take result was not OnPair"))?; + .map_err(|_| vortex_error::vortex_err!("take result was not OnPair"))?; assert_eq!(typed.dict_bytes().as_slice(), arr.dict_bytes().as_slice()); assert_eq!(typed.dict_offsets().len(), arr.dict_offsets().len()); diff --git a/encodings/parquet-variant/src/array.rs b/encodings/parquet-variant/src/array.rs index 88a1ab4ae1e..8a88ed61d82 100644 --- a/encodings/parquet-variant/src/array.rs +++ b/encodings/parquet-variant/src/array.rs @@ -388,11 +388,11 @@ fn parquet_shredded_field_from_logical( .as_opt::() .ok_or_else(|| { vortex_err!( - NotImplemented: "cannot rebuild Parquet shredded field: nested Variant lacks Parquet Variant core storage" + "cannot rebuild Parquet shredded field: nested Variant lacks Parquet Variant core storage" ) })?; let value = core.value().cloned().ok_or_else(|| { - vortex_err!(InvalidArgument: "cannot rebuild Parquet shredded field: partially shredded Variant has no residual value") + vortex_err!("cannot rebuild Parquet shredded field: partially shredded Variant has no residual value") })?; let typed_value = variant .shredded() @@ -552,7 +552,7 @@ mod tests { ); let inner = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant child"))?; + .ok_or_else(|| vortex_err!("expected parquet variant child"))?; let mut ctx = SESSION.create_execution_ctx(); let roundtripped = inner.to_arrow(&ArrowExportOptions::default(), &mut ctx)?; @@ -622,10 +622,10 @@ mod tests { let parquet_array = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; + .ok_or_else(|| vortex_err!("expected parquet variant array"))?; let typed_value = parquet_array .typed_value() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; + .ok_or_else(|| vortex_err!("expected typed_value child"))?; assert_arrays_eq!( typed_value, PrimitiveArray::from_option_iter([Some(10), None, Some(30)]), @@ -729,16 +729,16 @@ mod tests { let vortex_arr = ParquetVariant::from_arrow_variant(&arrow_variant, &SESSION.arrow())?; let parquet_array = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; + .ok_or_else(|| vortex_err!("expected parquet variant array"))?; let mut ctx = SESSION.create_execution_ctx(); let value = parquet_array .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected synthesized value child"))?; + .ok_or_else(|| vortex_err!("expected synthesized value child"))?; assert!(value.all_invalid(&mut ctx)?); let typed_value = parquet_array .typed_value() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; + .ok_or_else(|| vortex_err!("expected typed_value child"))?; assert_arrays_eq!( typed_value, PrimitiveArray::from_option_iter([Some(10i32), Some(20), Some(30)]), @@ -768,7 +768,7 @@ mod tests { let vortex_arr = ParquetVariant::from_arrow_variant(&arrow_variant, &SESSION.arrow())?; let parquet_array = vortex_arr .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; + .ok_or_else(|| vortex_err!("expected parquet variant array"))?; assert!(parquet_array.value().is_some()); assert!(parquet_array.typed_value().is_some()); @@ -841,7 +841,7 @@ mod tests { assert!( original .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant"))? + .ok_or_else(|| vortex_err!("expected parquet variant"))? .typed_value() .is_some(), "fixture must be shredded" @@ -850,15 +850,15 @@ mod tests { // Canonicalize: the forward transform lifts `typed_value` into a logical shredded child. let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = original.clone().execute::(&mut ctx)? else { - return Err(vortex_err!(MismatchedTypes: "expected canonical variant")); + return Err(vortex_err!("expected canonical variant")); }; let core = canonical .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; let logical = canonical .shredded() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))? + .ok_or_else(|| vortex_err!("expected canonical shredded child"))? .clone(); // Inverse transform: rebuild a Parquet `typed_value` and reattach it. diff --git a/encodings/parquet-variant/src/arrow.rs b/encodings/parquet-variant/src/arrow.rs index 530f10fe162..f6eaf1d1c79 100644 --- a/encodings/parquet-variant/src/arrow.rs +++ b/encodings/parquet-variant/src/arrow.rs @@ -81,7 +81,7 @@ pub(crate) fn export_storage_to_target( }; let Some(child) = child else { vortex_bail!( - InvalidArgument: "cannot export Parquet Variant storage field '{}' because source has no {} child", + "cannot export Parquet Variant storage field '{}' because source has no {} child", field.name(), field.name() ); @@ -128,16 +128,16 @@ pub(crate) fn parquet_variant_for_export( return Ok(executed); } - let variant = executed.as_opt::().ok_or_else( - || vortex_err!(NotImplemented: "cannot export Variant without ParquetVariant storage"), - )?; + let variant = executed + .as_opt::() + .ok_or_else(|| vortex_err!("cannot export Variant without ParquetVariant storage"))?; let core_storage = variant .core_storage() .clone() .execute_until::(ctx)?; - let parquet_core = core_storage.as_opt::().ok_or_else( - || vortex_err!(NotImplemented: "cannot export Variant without ParquetVariant core storage"), - )?; + let parquet_core = core_storage + .as_opt::() + .ok_or_else(|| vortex_err!("cannot export Variant without ParquetVariant core storage"))?; let Some(shredded) = variant.shredded() else { return Ok(core_storage); }; @@ -211,13 +211,11 @@ impl ArrowExportVTable for ParquetVariant { )?)); } if has_value && !request_has_value { - vortex_bail!( - InvalidArgument: "cannot export Parquet Variant storage without losing value child" - ); + vortex_bail!("cannot export Parquet Variant storage without losing value child"); } if has_typed_value && !request_has_typed_value { vortex_bail!( - InvalidArgument: "cannot export Parquet Variant storage without losing typed_value child" + "cannot export Parquet Variant storage without losing typed_value child" ); } diff --git a/encodings/parquet-variant/src/json_to_variant_tests.rs b/encodings/parquet-variant/src/json_to_variant_tests.rs index 516bd0b55b5..e66ed56c67d 100644 --- a/encodings/parquet-variant/src/json_to_variant_tests.rs +++ b/encodings/parquet-variant/src/json_to_variant_tests.rs @@ -75,9 +75,7 @@ fn assert_variant_i64_rows(array: &ArrayRef, expected: &[Option]) -> Vortex Some(expected) => { let value = variant .value() - .ok_or_else( - || vortex_err!(InvalidArgument: "expected non-null variant at row {idx}"), - )? + .ok_or_else(|| vortex_err!("expected non-null variant at row {idx}"))? .cast(&i64_dtype())?; assert_eq!(value.as_primitive().typed_value::(), Some(*expected)); } @@ -114,14 +112,14 @@ fn converts_json_extension_rows() -> VortexResult<()> { let object = row0 .as_variant() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant"))?; + .ok_or_else(|| vortex_err!("expected non-null variant"))?; let field = object .as_struct() .field("a") - .ok_or_else(|| vortex_err!(InvalidArgument: "expected field a"))? + .ok_or_else(|| vortex_err!("expected field a"))? .as_variant() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null field a"))? + .ok_or_else(|| vortex_err!("expected non-null field a"))? .cast(&i64_dtype())?; assert_eq!(field.as_primitive().typed_value::(), Some(expected)); } @@ -130,7 +128,7 @@ fn converts_json_extension_rows() -> VortexResult<()> { let value = row1 .as_variant() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant"))? + .ok_or_else(|| vortex_err!("expected non-null variant"))? .cast(&i64_dtype())?; assert_eq!(value.as_primitive().typed_value::(), Some(2)); Ok(()) @@ -212,11 +210,11 @@ fn shredding_produces_typed_value_child() -> VortexResult<()> { // The canonical form must expose field `a` through the shredded tree. let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = result.clone().execute::(&mut ctx)? else { - vortex_bail!(MismatchedTypes: "expected canonical variant array"); + vortex_bail!("expected canonical variant array"); }; let shredded = canonical .shredded() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))? + .ok_or_else(|| vortex_err!("expected canonical shredded child"))? .clone() .execute::(&mut ctx)?; assert!(shredded.unmasked_field_by_name_opt("a").is_some()); @@ -292,7 +290,7 @@ fn shredding_root_path_shreds_top_level_values() -> VortexResult<()> { let value = row2 .as_variant() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant"))?; + .ok_or_else(|| vortex_err!("expected non-null variant"))?; assert_eq!( value.as_utf8().value().map(|value| value.to_string()), Some("not-a-number".to_string()) diff --git a/encodings/parquet-variant/src/kernel.rs b/encodings/parquet-variant/src/kernel.rs index f162349b523..b218d9404f4 100644 --- a/encodings/parquet-variant/src/kernel.rs +++ b/encodings/parquet-variant/src/kernel.rs @@ -126,7 +126,7 @@ impl ExecuteParentKernel for VariantGetKernel { // Import through the same `as_type` field the cast targeted, so an extension target // dtype comes back as that extension rather than as its bare storage type. let as_type = as_type.ok_or_else(|| { - vortex_err!(AssertionFailed: "a non-variant target dtype must produce an as_type field") + vortex_err!("a non-variant target dtype must produce an as_type field") })?; session.arrow().from_arrow_array(arrow_output, &as_type)? }; @@ -134,7 +134,7 @@ impl ExecuteParentKernel for VariantGetKernel { vortex_ensure_eq!( output.dtype(), parent.dtype(), - MismatchedTypes: "VariantGet output dtype must match parent dtype" + "VariantGet output dtype must match parent dtype" ); Ok(Some(output)) } @@ -208,9 +208,8 @@ pub(crate) fn to_parquet_variant_path(path: &VariantPath) -> VortexResult { - let index = usize::try_from(*index).map_err( - |_| vortex_err!(Overflow: "VariantGet path index {index} is too large"), - )?; + let index = usize::try_from(*index) + .map_err(|_| vortex_err!("VariantGet path index {index} is too large"))?; Ok(PqVariantPathElement::index(index)) } }) @@ -372,7 +371,7 @@ mod tests { let arrow = SESSION.arrow(); let as_type = to_arrow_as_type(Some(&uuid), &arrow)? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected an as_type field"))?; + .ok_or_else(|| vortex_err!("expected an as_type field"))?; assert_eq!(as_type.data_type(), &DataType::FixedSizeBinary(16)); assert_eq!(as_type.extension_type_name(), Some(ArrowUuid::NAME)); @@ -395,7 +394,7 @@ mod tests { )), &arrow, )? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected an as_type field"))?; + .ok_or_else(|| vortex_err!("expected an as_type field"))?; assert_eq!(as_type.data_type(), &DataType::Int32); assert_eq!(as_type.extension_type_name(), None); assert!(as_type.is_nullable()); @@ -458,7 +457,7 @@ mod tests { .get(pos) .is_some_and(|byte| !matches!(byte, b'.' | b'[')) { - vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.' or '[' after '$'"); + vortex_bail!("Invalid Variant path {path:?}: expected '.' or '[' after '$'"); } while pos < path.len() { @@ -480,7 +479,7 @@ mod tests { pos = next_pos; } _ => { - vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.', '[', or end of path") + vortex_bail!("Invalid Variant path {path:?}: expected '.', '[', or end of path") } } } @@ -499,7 +498,7 @@ mod tests { } vortex_ensure!( pos > start, - InvalidArgument: "Invalid Variant path {path:?}: expected field name" + "Invalid Variant path {path:?}: expected field name" ); Ok((&path[start..pos], pos)) } @@ -515,15 +514,15 @@ mod tests { } vortex_ensure!( pos > start, - InvalidArgument: "Invalid Variant path {path:?}: expected list index" + "Invalid Variant path {path:?}: expected list index" ); vortex_ensure!( path.as_bytes().get(pos) == Some(&b']'), - InvalidArgument: "Invalid Variant path {path:?}: expected closing ']'" + "Invalid Variant path {path:?}: expected closing ']'" ); - let index = path[start..pos].parse().map_err( - |_| vortex_err!(Overflow: "Invalid Variant path {path:?}: list index is too large"), - )?; + let index = path[start..pos] + .parse() + .map_err(|_| vortex_err!("Invalid Variant path {path:?}: list index is too large"))?; Ok((index, pos + 1)) } @@ -873,7 +872,7 @@ mod tests { let parquet_array = ParquetVariant::from_arrow_variant(&arrow_variant, &SESSION.arrow())?; let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = parquet_array.execute::(&mut ctx)? else { - return Err(vortex_err!(MismatchedTypes: "expected canonical variant array")); + return Err(vortex_err!("expected canonical variant array")); }; Ok(canonical.into_array()) } @@ -915,9 +914,9 @@ mod tests { let variant = scalar.as_variant(); match expected { Some(expected) => { - let value = variant.value().ok_or_else( - || vortex_err!(InvalidArgument: "expected non-null variant scalar"), - )?; + let value = variant + .value() + .ok_or_else(|| vortex_err!("expected non-null variant scalar"))?; let value = value.cast(&VortexDType::Primitive(PType::I32, Nullability::Nullable))?; assert_eq!(value.as_primitive().typed_value::(), Some(*expected)); @@ -941,17 +940,17 @@ mod tests { let object = scalar .as_variant() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null variant object"))? + .ok_or_else(|| vortex_err!("expected non-null variant object"))? .as_struct(); match expected_a[idx] { Some(expected) => { let value = object .field("a") - .ok_or_else(|| vortex_err!(InvalidArgument: "expected field a"))? + .ok_or_else(|| vortex_err!("expected field a"))? .as_variant() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null field a"))? + .ok_or_else(|| vortex_err!("expected non-null field a"))? .cast(&VortexDType::Primitive(PType::I32, Nullability::Nullable))?; assert_eq!(value.as_primitive().typed_value::(), Some(expected)); } @@ -960,11 +959,11 @@ mod tests { let field_b = object .field("b") - .ok_or_else(|| vortex_err!(InvalidArgument: "expected field b"))?; + .ok_or_else(|| vortex_err!("expected field b"))?; let value = field_b .as_variant() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected non-null field b"))?; + .ok_or_else(|| vortex_err!("expected non-null field b"))?; assert_eq!( value.as_utf8().value().map(|value| value.as_str()), Some(expected_b[idx]) @@ -999,7 +998,7 @@ mod tests { let executed_variant = executed.as_::(); let typed_value = executed_variant .typed_value() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; + .ok_or_else(|| vortex_err!("expected typed_value child"))?; assert_arrays_eq!( typed_value, @@ -1077,13 +1076,13 @@ mod tests { let core_storage = canonical_variant .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; assert!(core_storage.typed_value().is_none()); assert!(core_storage.value().is_some()); let shredded = canonical_variant .shredded() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))? + .ok_or_else(|| vortex_err!("expected canonical shredded child"))? .clone() .execute::(&mut SESSION.create_execution_ctx())?; assert_eq!( @@ -1183,14 +1182,14 @@ mod tests { let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(canonical) = parquet_array.execute::(&mut ctx)? else { - return Err(vortex_err!(MismatchedTypes: "expected canonical variant array")); + return Err(vortex_err!("expected canonical variant array")); }; assert!(canonical.shredded().is_some()); let core_storage = canonical .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; assert!(core_storage.typed_value().is_none()); assert!(core_storage.value().is_some()); diff --git a/encodings/parquet-variant/src/operations.rs b/encodings/parquet-variant/src/operations.rs index 1229b2f88ce..60a60a19eca 100644 --- a/encodings/parquet-variant/src/operations.rs +++ b/encodings/parquet-variant/src/operations.rs @@ -225,7 +225,7 @@ fn scalar_from_shredded_object_scalar( let unshredded = scalar_from_unshredded_value(metadata, &value)?; if !unshredded.is_null() { let Some(unshredded) = unshredded.as_struct_opt() else { - vortex_bail!(InvalidArgument: "Variant typed_value must be object if typed_value is a struct"); + vortex_bail!("Variant typed_value must be object if typed_value is a struct"); }; for name in unshredded.names().iter() { if names @@ -322,16 +322,17 @@ fn parquet_variant_to_scalar(variant: PqVariant<'_, '_>) -> VortexResult let dtype = DType::Extension( Timestamp::new_with_tz(TimeUnit::Nanoseconds, Some(Arc::from("UTC")), nn).erased(), ); - let nanos = v.timestamp_nanos_opt().ok_or_else( - || vortex_err!(Overflow: "Timestamp nanoseconds value out of i64 range"), - )?; + let nanos = v + .timestamp_nanos_opt() + .ok_or_else(|| vortex_err!("Timestamp nanoseconds value out of i64 range"))?; Scalar::try_new(dtype, Some(ScalarValue::Primitive(PValue::I64(nanos))))? } PqVariant::TimestampNtzNanos(v) => { let dtype = DType::Extension(Timestamp::new(TimeUnit::Nanoseconds, nn).erased()); - let nanos = v.and_utc().timestamp_nanos_opt().ok_or_else( - || vortex_err!(Overflow: "Timestamp nanoseconds value out of i64 range"), - )?; + let nanos = v + .and_utc() + .timestamp_nanos_opt() + .ok_or_else(|| vortex_err!("Timestamp nanoseconds value out of i64 range"))?; Scalar::try_new(dtype, Some(ScalarValue::Primitive(PValue::I64(nanos))))? } PqVariant::Time(v) => { diff --git a/encodings/parquet-variant/src/vtable.rs b/encodings/parquet-variant/src/vtable.rs index ea8296005ad..70de3b1d582 100644 --- a/encodings/parquet-variant/src/vtable.rs +++ b/encodings/parquet-variant/src/vtable.rs @@ -96,57 +96,57 @@ impl VTable for ParquetVariant { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), ParquetVariantSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), ParquetVariantSlots::COUNT); let validity = child_to_validity( slots[ParquetVariantSlots::VALIDITY].as_ref(), dtype.nullability(), ); let metadata = slots[ParquetVariantSlots::METADATA] .as_ref() - .ok_or_else(|| vortex_err!(NotFound: "ParquetVariantArray metadata slot"))?; + .ok_or_else(|| vortex_err!("ParquetVariantArray metadata slot"))?; let value = slots[ParquetVariantSlots::VALUE].as_ref(); let typed_value = slots[ParquetVariantSlots::TYPED_VALUE].as_ref(); vortex_ensure!( matches!(dtype, DType::Variant(_)), - MismatchedTypes: "Expected Variant DType, found {dtype}" + "Expected Variant DType, found {dtype}" ); vortex_ensure!( value.is_some() || typed_value.is_some(), - InvalidArgument: "at least one of value or typed_value must be present" + "at least one of value or typed_value must be present" ); vortex_ensure_eq!( dtype.nullability(), validity.nullability(), - InvalidArgument: "variant dtype nullability must match validity nullability" + "variant dtype nullability must match validity nullability" ); vortex_ensure_eq!( metadata.dtype(), &DType::Binary(Nullability::NonNullable), - MismatchedTypes: "metadata dtype must be non-nullable binary" + "metadata dtype must be non-nullable binary" ); vortex_ensure_eq!( metadata.len(), len, - InvalidArgument: "metadata length must match array length" + "metadata length must match array length" ); if let Some(validity_len) = validity.maybe_len() { - vortex_ensure_eq!(validity_len, len, InvalidArgument: "validity length must match array length"); + vortex_ensure_eq!(validity_len, len, "validity length must match array length"); } if let Some(value) = value { vortex_ensure!( matches!(value.dtype(), DType::Binary(_)), - MismatchedTypes: "value dtype must be binary, found {}", + "value dtype must be binary, found {}", value.dtype() ); - vortex_ensure_eq!(value.len(), len, InvalidArgument: "value length must match array length"); + vortex_ensure_eq!(value.len(), len, "value length must match array length"); } if let Some(typed_value) = typed_value { vortex_ensure_eq!( typed_value.len(), len, - InvalidArgument: "typed_value length must match array length" + "typed_value length must match array length" ); } Ok(()) @@ -157,7 +157,7 @@ impl VTable for ParquetVariant { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ParquetVariantArray buffer index {idx} out of bounds") + vortex_panic!("ParquetVariantArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -205,7 +205,7 @@ impl VTable for ParquetVariant { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - InvalidArgument: "ParquetVariantArray expects 0 buffers, got {}", + "ParquetVariantArray expects 0 buffers, got {}", buffers.len() ); @@ -215,17 +215,17 @@ impl VTable for ParquetVariant { None => None, }; - vortex_ensure!(matches!(dtype, DType::Variant(_)), MismatchedTypes: "Expected Variant DType"); + vortex_ensure!(matches!(dtype, DType::Variant(_)), "Expected Variant DType"); let has_typed_value = typed_value_dtype.is_some(); vortex_ensure!( proto.has_value || has_typed_value, - InvalidArgument: "At least one of value or typed_value must be present" + "At least one of value or typed_value must be present" ); let expected_children = 1 + proto.has_value as usize + has_typed_value as usize; vortex_ensure!( children.len() == expected_children || children.len() == expected_children + 1, - InvalidArgument: "Expected {} or {} children, got {}", + "Expected {} or {} children, got {}", expected_children, expected_children + 1, children.len() @@ -250,9 +250,8 @@ impl VTable for ParquetVariant { let typed_value = if has_typed_value { // typed_value can be any type — primitive, list, struct, etc. - let dtype = typed_value_dtype.ok_or_else( - || vortex_err!(NotFound: "typed_value_dtype missing for typed_value child"), - )?; + let dtype = typed_value_dtype + .ok_or_else(|| vortex_err!("typed_value_dtype missing for typed_value child"))?; let tv = children.get(child_idx, &dtype, len)?; Some(tv) } else { @@ -474,17 +473,17 @@ mod tests { .into_array() .execute::(&mut ctx)? else { - return Err(vortex_err!(MismatchedTypes: "expected canonical variant")); + return Err(vortex_err!("expected canonical variant")); }; let core_storage = variant .core_storage() .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant core storage"))?; + .ok_or_else(|| vortex_err!("expected parquet variant core storage"))?; assert!(core_storage.typed_value().is_none()); let shredded = variant .shredded() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected canonical shredded child"))?; + .ok_or_else(|| vortex_err!("expected canonical shredded child"))?; assert_eq!( shredded.dtype(), &DType::Primitive(PType::I32, Nullability::Nullable) @@ -584,10 +583,10 @@ mod tests { assert!(array.array_eq(&decoded, EqMode::Value)); let decoded_pv = decoded .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; + .ok_or_else(|| vortex_err!("expected parquet variant array"))?; let typed = decoded_pv .typed_value() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; + .ok_or_else(|| vortex_err!("expected typed_value child"))?; assert_eq!(typed.dtype(), &DType::Variant(Nullability::NonNullable)); Ok(()) } @@ -607,7 +606,7 @@ mod tests { assert_eq!(decoded.dtype(), &DType::Variant(Nullability::Nullable)); let decoded_pv = decoded .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; + .ok_or_else(|| vortex_err!("expected parquet variant array"))?; assert!(decoded_pv.value().is_some()); assert!(decoded_pv.typed_value().is_none()); Ok(()) @@ -631,10 +630,10 @@ mod tests { assert!(array.array_eq(&decoded, EqMode::Value)); let decoded_pv = decoded .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected parquet variant array"))?; + .ok_or_else(|| vortex_err!("expected parquet variant array"))?; let typed = decoded_pv .typed_value() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected typed_value child"))?; + .ok_or_else(|| vortex_err!("expected typed_value child"))?; assert_eq!( typed.dtype(), &DType::Primitive(PType::I32, Nullability::NonNullable) diff --git a/encodings/pco/src/array.rs b/encodings/pco/src/array.rs index 9a2c8591830..684155fa875 100644 --- a/encodings/pco/src/array.rs +++ b/encodings/pco/src/array.rs @@ -217,7 +217,7 @@ impl VTable for Pco { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "PcoArray expected 0 or 1 child, got {}", children.len()); + vortex_bail!("PcoArray expected 0 or 1 child, got {}", children.len()); }; vortex_ensure!(buffers.len() >= metadata.chunks.len()); @@ -315,11 +315,11 @@ pub(crate) fn vortex_err_from_pco(err: PcoError) -> VortexError { use pco::errors::ErrorKind::*; match err.kind { Io(io_kind) => VortexError::from(std::io::Error::new(io_kind, err.message)), - InvalidArgument => vortex_err!(InvalidArgument: "{}", err.message), + InvalidArgument => vortex_err!("{}", err.message), kind @ (Corruption | InsufficientData) => { - vortex_err!(Serde: "Pco {:?} error: {}", kind, err.message) + vortex_err!("Pco {:?} error: {}", kind, err.message) } - other => vortex_err!(Other: "Pco {:?} error: {}", other, err.message), + other => vortex_err!("Pco {:?} error: {}", other, err.message), } } @@ -410,24 +410,20 @@ impl PcoData { /// Validate dtype, validity, slice, and Pco component invariants. pub fn validate(&self, dtype: &DType, len: usize, validity: &Validity) -> VortexResult<()> { let _ = number_type_from_ptype(self.ptype); - vortex_ensure_eq!(dtype.as_ptype(), self.ptype, MismatchedTypes); - vortex_ensure_eq!(dtype.nullability(), validity.nullability(), InvalidArgument); + vortex_ensure_eq!(dtype.as_ptype(), self.ptype); + vortex_ensure_eq!(dtype.nullability(), validity.nullability()); vortex_ensure!( self.slice_start <= self.slice_stop && self.slice_stop <= self.unsliced_n_rows, - InvalidArgument: "invalid slice range {}..{} for {} rows", + "invalid slice range {}..{} for {} rows", self.slice_start, self.slice_stop, self.unsliced_n_rows ); - vortex_ensure_eq!(self.slice_stop - self.slice_start, len, InvalidArgument); + vortex_ensure_eq!(self.slice_stop - self.slice_start, len); if let Some(validity_len) = validity.maybe_len() { - vortex_ensure_eq!(validity_len, self.unsliced_n_rows, InvalidArgument); + vortex_ensure_eq!(validity_len, self.unsliced_n_rows); } - vortex_ensure_eq!( - self.chunk_metas.len(), - self.metadata.chunks.len(), - InvalidArgument - ); + vortex_ensure_eq!(self.chunk_metas.len(), self.metadata.chunks.len()); vortex_ensure_eq!( self.pages.len(), self.metadata @@ -435,7 +431,7 @@ impl PcoData { .iter() .map(|chunk| chunk.pages.len()) .sum::(), - InvalidArgument: "page count does not match metadata" + "page count does not match metadata" ); let mut n_values = 0usize; @@ -445,33 +441,33 @@ impl PcoData { let page_n_values = page.n_values as usize; vortex_ensure!( page_n_values != 0, - InvalidArgument: "Pco chunk {chunk_idx} contains an empty page" + "Pco chunk {chunk_idx} contains an empty page" ); - chunk_n_values = chunk_n_values.checked_add(page_n_values).ok_or_else( - || vortex_err!(Overflow: "Pco chunk {chunk_idx} value count overflows usize"), - )?; + chunk_n_values = chunk_n_values.checked_add(page_n_values).ok_or_else(|| { + vortex_err!("Pco chunk {chunk_idx} value count overflows usize") + })?; } vortex_ensure!( chunk_n_values <= VALUES_PER_CHUNK, - InvalidArgument: "Pco chunk {chunk_idx} contains {chunk_n_values} values, exceeding the maximum of {VALUES_PER_CHUNK}" + "Pco chunk {chunk_idx} contains {chunk_n_values} values, exceeding the maximum of {VALUES_PER_CHUNK}" ); n_values = n_values .checked_add(chunk_n_values) - .ok_or_else(|| vortex_err!(Overflow: "Pco value count overflows usize"))?; + .ok_or_else(|| vortex_err!("Pco value count overflows usize"))?; } vortex_ensure!( n_values <= self.unsliced_n_rows, - InvalidArgument: "Pco contains {n_values} values for only {} rows", + "Pco contains {n_values} values for only {} rows", self.unsliced_n_rows ); if validity.definitely_no_nulls() { vortex_ensure_eq!( n_values, self.unsliced_n_rows, - InvalidArgument: "Pco value count must match the row count of a non-null array" + "Pco value count must match the row count of a non-null array" ); } else if validity.definitely_all_null() { - vortex_ensure_eq!(n_values, 0, InvalidArgument: "Pco contains values for an all-null array"); + vortex_ensure_eq!(n_values, 0, "Pco contains values for an all-null array"); } Ok(()) } @@ -606,7 +602,7 @@ impl PcoData { ) -> VortexResult { let parray = array.try_downcast::().map_err(|a| { vortex_err!( - MismatchedTypes: "Pco can only encode primitive arrays, got {}", + "Pco can only encode primitive arrays, got {}", a.encoding_id() ) })?; @@ -684,7 +680,7 @@ impl PcoData { let page: &[u8] = self .pages .get(page_idx) - .ok_or_else(|| vortex_err!(NotFound: "Missing Pco page {page_idx}"))? + .ok_or_else(|| vortex_err!("Missing Pco page {page_idx}"))? .as_ref(); let mut cd = match chunk_decompressor.take() { @@ -720,7 +716,7 @@ impl PcoData { let value_stop = value_offset + slice_n_values; vortex_ensure!( value_stop <= decompressed_values.len(), - InvalidArgument: "Pco contains {} decompressed values, but the requested range ends at {value_stop}", + "Pco contains {} decompressed values, but the requested range ends at {value_stop}", decompressed_values.len() ); Ok(decompressed_values diff --git a/encodings/runend/src/array.rs b/encodings/runend/src/array.rs index 1a652cb32cf..787a5a02ecd 100644 --- a/encodings/runend/src/array.rs +++ b/encodings/runend/src/array.rs @@ -112,11 +112,11 @@ impl VTable for RunEnd { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "RunEndArray buffer index {idx} out of bounds") + vortex_panic!("RunEndArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "RunEndArray buffer_name index {idx} out of bounds") + vortex_panic!("RunEndArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -307,7 +307,7 @@ impl RunEnd { let data = unsafe { RunEndData::new_unchecked(0) }; Array::try_from_parts(ArrayParts::new(RunEnd, dtype, len, data, slots)) } else { - vortex_bail!(MismatchedTypes: "REE can only encode primitive arrays") + vortex_bail!("REE can only encode primitive arrays") } } } @@ -375,14 +375,14 @@ impl RunEndData { // DType validation vortex_ensure!( ends.dtype().is_unsigned_int(), - MismatchedTypes: "run ends must be unsigned integers, was {}", + "run ends must be unsigned integers, was {}", ends.dtype(), ); vortex_ensure_eq!(ends.len(), values.len()); // Handle empty run-ends if ends.is_empty() { - vortex_ensure_eq!(offset, 0, InvalidArgument: "non-zero offset provided for empty RunEndArray"); + vortex_ensure_eq!(offset, 0, "non-zero offset provided for empty RunEndArray"); return Ok(false); } @@ -398,12 +398,12 @@ impl RunEndData { length: usize, ) -> VortexResult<()> { if first_run_end < offset { - vortex_bail!(InvalidArgument: "First run end {first_run_end} must be >= offset {offset}"); + vortex_bail!("First run end {first_run_end} must be >= offset {offset}"); } let min_required_end = offset + length; if last_run_end < min_required_end { - vortex_bail!(InvalidArgument: "Last run end {last_run_end} must be >= offset+length {min_required_end}"); + vortex_bail!("Last run end {last_run_end} must be >= offset+length {min_required_end}"); } Ok(()) @@ -465,7 +465,7 @@ impl RunEndData { // SAFETY: runend_encode handles this unsafe { Ok(Self::new_unchecked(0)) } } else { - vortex_bail!(MismatchedTypes: "REE can only encode primitive arrays") + vortex_bail!("REE can only encode primitive arrays") } } @@ -532,7 +532,7 @@ pub(super) fn run_end_canonicalize( .execute_as::("values", ctx)?; runend_decode_listview(pends, values, array.offset(), array.len())?.into_array() } - _ => vortex_bail!(InvalidArgument: "Unsupported RunEnd value type: {}", array.dtype()), + _ => vortex_bail!("Unsupported RunEnd value type: {}", array.dtype()), }) } diff --git a/encodings/runend/src/compute/take.rs b/encodings/runend/src/compute/take.rs index c61da1c8733..a50787ef7fd 100644 --- a/encodings/runend/src/compute/take.rs +++ b/encodings/runend/src/compute/take.rs @@ -293,7 +293,7 @@ fn prefer_linear_scan( fn check_index(index: usize, array_len: usize) -> VortexResult<()> { if index >= array_len { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", index, 0, array_len); + vortex_bail!("index {} out of bounds from {} to {}", index, 0, array_len); } Ok(()) } diff --git a/encodings/runend/src/iter.rs b/encodings/runend/src/iter.rs index 356e2ff05ca..0e2f9bc30f7 100644 --- a/encodings/runend/src/iter.rs +++ b/encodings/runend/src/iter.rs @@ -13,14 +13,14 @@ pub fn trimmed_ends_iter( ) -> impl Iterator + use<'_, E> { let offset_e = E::from_usize(offset).unwrap_or_else(|| { vortex_panic!( - Overflow: "offset {} cannot be converted to {}", + "offset {} cannot be converted to {}", offset, std::any::type_name::() ) }); let length_e = E::from_usize(length).unwrap_or_else(|| { vortex_panic!( - Overflow: "length {} cannot be converted to {}", + "length {} cannot be converted to {}", length, std::any::type_name::() ) @@ -30,7 +30,7 @@ pub fn trimmed_ends_iter( .copied() .map(move |v| { if v < offset_e { - vortex_panic!(AssertionFailed: "run end {v} must be >= offset {offset}"); + vortex_panic!("run end {v} must be >= offset {offset}"); } v - offset_e }) diff --git a/encodings/runend/src/probe.rs b/encodings/runend/src/probe.rs index 9332d2b4916..abcb3d22e0d 100644 --- a/encodings/runend/src/probe.rs +++ b/encodings/runend/src/probe.rs @@ -22,13 +22,13 @@ pub(crate) fn scalar_at( let logical_index = array .offset() .checked_add(index) - .ok_or_else(|| vortex_err!(Overflow: "RunEnd logical index overflow"))?; + .ok_or_else(|| vortex_err!("RunEnd logical index overflow"))?; // Search for the first end strictly greater than the logical index. Every comparison // uses the same ends probe, so a retained read keeps the child's preparation within and // between searches. let mut ends = state .slot(RunEndSlots::ENDS)? - .ok_or_else(|| vortex_err!(InvalidArgument: "RunEnd ends slot is missing"))?; + .ok_or_else(|| vortex_err!("RunEnd ends slot is missing"))?; let mut left = 0; let mut right = ends.array().len(); while left < right { @@ -42,7 +42,7 @@ pub(crate) fn scalar_at( } state .slot(RunEndSlots::VALUES)? - .ok_or_else(|| vortex_err!(InvalidArgument: "RunEnd values slot is missing"))? + .ok_or_else(|| vortex_err!("RunEnd values slot is missing"))? .execute_scalar(left, ctx) } diff --git a/encodings/sequence/src/array.rs b/encodings/sequence/src/array.rs index 963c6a30941..81eacb0627f 100644 --- a/encodings/sequence/src/array.rs +++ b/encodings/sequence/src/array.rs @@ -127,14 +127,14 @@ impl SequenceData { length: usize, ) -> VortexResult<()> { let DType::Primitive(ptype, _) = dtype else { - vortex_bail!(NotImplemented: "only primitive dtypes are supported in SequenceArray currently"); + vortex_bail!("only primitive dtypes are supported in SequenceArray currently"); }; if !ptype.is_int() { - vortex_bail!(NotImplemented: "only integer ptypes are supported in SequenceArray currently") + vortex_bail!("only integer ptypes are supported in SequenceArray currently") } - vortex_ensure!(length > 0, InvalidArgument: "SequenceArray length must be greater than zero"); + vortex_ensure!(length > 0, "SequenceArray length must be greater than zero"); Self::narrowed_base(base, *ptype)?; Self::ensure_last_expressible(base, multiplier, *ptype, length) @@ -149,7 +149,7 @@ impl SequenceData { ) -> VortexResult<()> { let steps = (length - 1) as u64; let (ascending, magnitude) = eval::step_parts(multiplier) - .ok_or_else(|| vortex_err!(MismatchedTypes: "step {multiplier} must be an integer"))?; + .ok_or_else(|| vortex_err!("step {multiplier} must be an integer"))?; if steps == 0 || magnitude == 0 { return Ok(()); } @@ -171,7 +171,7 @@ impl SequenceData { vortex_ensure!( steps <= room / magnitude, - Overflow: "final value not expressible, base = {base:?}, multiplier = {multiplier:?}, len = {length}" + "final value not expressible, base = {base:?}, multiplier = {multiplier:?}, len = {length}" ); Ok(()) } @@ -182,18 +182,18 @@ impl SequenceData { match multiplier .kind .as_ref() - .ok_or_else(|| vortex_err!(Serde: "multiplier value missing kind"))? + .ok_or_else(|| vortex_err!("multiplier value missing kind"))? { Kind::Int64Value(_) => Ok(PType::I64), Kind::Uint64Value(_) => Ok(PType::U64), _ => { - vortex_bail!(NotImplemented: "only integer ptypes are supported in SequenceArray currently") + vortex_bail!("only integer ptypes are supported in SequenceArray currently") } } } fn narrowed_base(base: PValue, ptype: PType) -> VortexResult { - vortex_ensure!(base.ptype().is_int(), MismatchedTypes: "base {base} must be an integer"); + vortex_ensure!(base.ptype().is_int(), "base {base} must be an integer"); match_each_integer_ptype!(ptype, |P| { Ok(PValue::from(base.cast::

()?)) }) } @@ -212,7 +212,7 @@ impl SequenceData { let v: i64 = v.as_(); PValue::from(v) }, - float: |v| { vortex_bail!(MismatchedTypes: "step {v} must be an integer") } + float: |v| { vortex_bail!("step {v} must be an integer") } ); Ok((base, multiplier)) @@ -247,7 +247,7 @@ impl SequenceData { pub(crate) fn wrapping_parts(&self) -> VortexResult<(O, O)> { eval::wrapping_parts(self.base, self.multiplier).ok_or_else(|| { vortex_err!( - MismatchedTypes: "SequenceArray values must be integers, got base {:?} and step {:?}", + "SequenceArray values must be integers, got base {:?} and step {:?}", self.base, self.multiplier ) @@ -321,11 +321,11 @@ impl VTable for Sequence { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "SequenceArray buffer index {idx} out of bounds") + vortex_panic!("SequenceArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "SequenceArray buffer_name index {idx} out of bounds") + vortex_panic!("SequenceArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -359,17 +359,17 @@ impl VTable for Sequence { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - InvalidArgument: "SequenceArray expects 0 buffers, got {}", + "SequenceArray expects 0 buffers, got {}", buffers.len() ); vortex_ensure!( children.is_empty(), - InvalidArgument: "SequenceArray expects 0 children, got {}", + "SequenceArray expects 0 children, got {}", children.len() ); let DType::Primitive(output_ptype, _) = dtype else { vortex_bail!( - NotImplemented: "only primitive dtypes are supported in SequenceArray currently, got {dtype}" + "only primitive dtypes are supported in SequenceArray currently, got {dtype}" ); }; let metadata = SequenceMetadata::decode(metadata)?; @@ -377,12 +377,12 @@ impl VTable for Sequence { let base_metadata = metadata .base .as_ref() - .ok_or_else(|| vortex_err!(Serde: "base required"))?; + .ok_or_else(|| vortex_err!("base required"))?; let multiplier_metadata = metadata .multiplier .as_ref() - .ok_or_else(|| vortex_err!(Serde: "multiplier required"))?; + .ok_or_else(|| vortex_err!("multiplier required"))?; // We go via Scalar to validate that the value is valid for the ptype. let base = Scalar::from_proto_value( @@ -745,9 +745,9 @@ mod tests { &SESSION, )?; - let decoded_sequence = decoded.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "decoded array should still be a SequenceArray"), - )?; + let decoded_sequence = decoded + .as_opt::() + .ok_or_else(|| vortex_err!("decoded array should still be a SequenceArray"))?; assert_eq!(decoded_sequence.ptype(), output_ptype); assert_eq!(decoded_sequence.multiplier(), array.multiplier()); assert_eq!(decoded.dtype(), &dtype); diff --git a/encodings/sequence/src/compute/min_max.rs b/encodings/sequence/src/compute/min_max.rs index a229c7961b3..adb0781657f 100644 --- a/encodings/sequence/src/compute/min_max.rs +++ b/encodings/sequence/src/compute/min_max.rs @@ -50,9 +50,8 @@ impl DynAggregateKernel for SequenceMinMaxKernel { // A sequence's extrema are its first and last values. let last = seq.index_value(seq.len() - 1); - let (ascending, _) = eval::step_parts(seq.multiplier()).ok_or_else( - || vortex_err!(MismatchedTypes: "step {} must be an integer", seq.multiplier()), - )?; + let (ascending, _) = eval::step_parts(seq.multiplier()) + .ok_or_else(|| vortex_err!("step {} must be an integer", seq.multiplier()))?; let (min_pvalue, max_pvalue) = if ascending { (seq.base(), last) @@ -112,9 +111,7 @@ mod tests { &mut SESSION.create_execution_ctx(), NumericalAggregateOpts::default(), )? - .ok_or_else( - || vortex_err!(AssertionFailed: "min_max of a non-empty sequence should not be null"), - )?; + .ok_or_else(|| vortex_err!("min_max of a non-empty sequence should not be null"))?; assert_eq!(min, Scalar::from(60u8)); assert_eq!(max, Scalar::from(100u8)); diff --git a/encodings/sequence/src/compute/take.rs b/encodings/sequence/src/compute/take.rs index 9525eebe12b..5089f65d486 100644 --- a/encodings/sequence/src/compute/take.rs +++ b/encodings/sequence/src/compute/take.rs @@ -48,7 +48,7 @@ fn take_inner( AllOr::All => { if let Err(position) = indices.try_map_into(out, value_at) { vortex_panic!( - OutOfBounds: "index {} out of bounds from {} to {}", + "index {} out of bounds from {} to {}", indices[position].as_(), 0, len @@ -66,7 +66,7 @@ fn take_inner( AllOr::Some(bits) => { if let Err(position) = indices.try_map_masked_into(bits, out, value_at) { vortex_panic!( - OutOfBounds: "index {} out of bounds from {} to {}", + "index {} out of bounds from {} to {}", indices[position].as_(), 0, len diff --git a/encodings/sequence/src/model_tests.rs b/encodings/sequence/src/model_tests.rs index 9db8962c2b8..9bfb4624bf0 100644 --- a/encodings/sequence/src/model_tests.rs +++ b/encodings/sequence/src/model_tests.rs @@ -122,7 +122,7 @@ fn values(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult> { fn constant(value: i128, ptype: PType, len: usize) -> VortexResult { let value = narrow(value, ptype) - .ok_or_else(|| vortex_err!(Overflow: "{value} is not representable in {ptype}"))?; + .ok_or_else(|| vortex_err!("{value} is not representable in {ptype}"))?; let scalar = Scalar::try_new( DType::Primitive(ptype, NonNullable), Some(ScalarValue::Primitive(value)), diff --git a/encodings/sparse/src/canonical.rs b/encodings/sparse/src/canonical.rs index de8aa616b67..796fda56ef5 100644 --- a/encodings/sparse/src/canonical.rs +++ b/encodings/sparse/src/canonical.rs @@ -104,7 +104,7 @@ impl SparseStringParts { .map(BufferString::into_inner), DType::Binary(_) => fill_scalar.as_binary().value().cloned(), dtype => { - vortex_bail!(MismatchedTypes: "Sparse string decode of non-string dtype {dtype}") + vortex_bail!("Sparse string decode of non-string dtype {dtype}") } }; Ok(Self { @@ -249,7 +249,7 @@ where } vortex_ensure!( previous <= row && row < len, - InvalidArgument: "Sparse patch indices must be ascending within the array length {len}" + "Sparse patch indices must be ascending within the array length {len}" ); fill_run(builder, row - previous)?; if patch_validity.value(patch) { @@ -349,7 +349,7 @@ pub(super) fn execute_sparse(parts: SparseParts, ctx: &mut ExecutionCtx) -> Vort execute_sparse_fixed_size_list(&patches, &fill_value, len, *nullability, ctx)? } DType::Map(..) => { - vortex_bail!(InvalidArgument: "Sparse canonicalization does not support Map arrays yet") + vortex_bail!("Sparse canonicalization does not support Map arrays yet") } DType::Struct(struct_fields, ..) => execute_sparse_struct( struct_fields, @@ -359,14 +359,12 @@ pub(super) fn execute_sparse(parts: SparseParts, ctx: &mut ExecutionCtx) -> Vort len, ctx, )?, - DType::Union(..) => vortex_bail!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_bail!("TODO(connor)[Union]: unimplemented"), DType::Variant(_) => { - vortex_bail!(InvalidArgument: "Sparse canonicalization does not support Variant") + vortex_bail!("Sparse canonicalization does not support Variant") } DType::Extension(..) => { - vortex_bail!( - NotImplemented: "Sparse canonicalization does not support Extension arrays yet" - ) + vortex_bail!("Sparse canonicalization does not support Extension arrays yet") } }) } diff --git a/encodings/sparse/src/compute/sum.rs b/encodings/sparse/src/compute/sum.rs index c55d3f9c5e5..c02e3e04e44 100644 --- a/encodings/sparse/src/compute/sum.rs +++ b/encodings/sparse/src/compute/sum.rs @@ -116,12 +116,12 @@ mod tests { .aggregate_fns() .find_aggregate_kernel(arr.encoding_id(), aggregate.id()) else { - vortex_bail!(NotFound: "Sparse SumV2 kernel is not registered"); + vortex_bail!("Sparse SumV2 kernel is not registered"); }; let Some(partial) = kernel.aggregate(&aggregate, arr, &mut SESSION.create_execution_ctx())? else { - vortex_bail!(AssertionFailed: "Sparse SumV2 kernel declined the aggregate"); + vortex_bail!("Sparse SumV2 kernel declined the aggregate"); }; let mut accumulator = Accumulator::try_new(SumV2, options, arr.dtype().clone())?; diff --git a/encodings/sparse/src/lib.rs b/encodings/sparse/src/lib.rs index 655bb6ddd22..55e5ed883e2 100644 --- a/encodings/sparse/src/lib.rs +++ b/encodings/sparse/src/lib.rs @@ -231,14 +231,14 @@ impl VTable for Sparse { ScalarValue::to_proto_bytes::>(array.fill_value.value()).into(); BufferHandle::new_host(fill_value_buffer) } - _ => vortex_panic!(OutOfBounds: "SparseArray buffer index {idx} out of bounds"), + _ => vortex_panic!("SparseArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("fill_value".to_string()), - _ => vortex_panic!(OutOfBounds: "SparseArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!("SparseArray buffer_name index {idx} out of bounds"), } } @@ -275,14 +275,14 @@ impl VTable for Sparse { // Once we have the patches metadata, we need to get the fill value from the buffers. if buffers.len() != 1 { - vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); + vortex_bail!("Expected 1 buffer, got {}", buffers.len()); } let scalar_bytes: &[u8] = &buffers[0].clone().try_to_host_sync()?; let scalar_value = ScalarValue::from_proto_bytes(scalar_bytes, dtype, session)?; let fill_value = Scalar::try_new(dtype.clone(), scalar_value)?; - vortex_ensure_eq!(children.len(), 2, InvalidArgument: "SparseArray expects 2 children"); + vortex_ensure_eq!(children.len(), 2, "SparseArray expects 2 children"); let patch_indices = children.get( 0, @@ -437,7 +437,7 @@ impl Sparse { vortex_ensure_eq!( values.dtype(), &dtype, - MismatchedTypes: "sparse values dtype must match fill value dtype" + "sparse values dtype must match fill value dtype" ); let patches = Patches::new(len, 0, indices, values, None, ctx)?; let slots = SparseData::make_slots(&patches); @@ -486,9 +486,9 @@ impl SparseData { dtype: &DType, len: usize, ) -> VortexResult<()> { - vortex_ensure_eq!(fill_value.dtype(), dtype, MismatchedTypes); - vortex_ensure_eq!(patches.array_len(), len, InvalidArgument); - vortex_ensure_eq!(patches.values().dtype(), dtype, MismatchedTypes); + vortex_ensure_eq!(fill_value.dtype(), dtype); + vortex_ensure_eq!(patches.array_len(), len); + vortex_ensure_eq!(patches.values().dtype(), dtype); Ok(()) } @@ -514,11 +514,7 @@ impl SparseData { /// Patch values must already match the fill dtype; callers are expected to construct patches /// with the correct dtype rather than relying on this to normalize them. fn from_patches(patches: &Patches, fill_value: Scalar) -> VortexResult { - vortex_ensure_eq!( - patches.values().dtype(), - fill_value.dtype(), - MismatchedTypes - ); + vortex_ensure_eq!(patches.values().dtype(), fill_value.dtype()); Ok(Self::from_patches_unchecked(patches, fill_value)) } @@ -572,7 +568,7 @@ impl SparseData { && !array.dtype().eq_ignore_nullability(fill_value.dtype()) { vortex_bail!( - MismatchedTypes: "Array and fill value types must have the same base type. got {} and {}", + "Array and fill value types must have the same base type. got {} and {}", array.dtype(), fill_value.dtype() ) diff --git a/encodings/uuid/src/arrow.rs b/encodings/uuid/src/arrow.rs index 79af83b6ca5..55202147633 100644 --- a/encodings/uuid/src/arrow.rs +++ b/encodings/uuid/src/arrow.rs @@ -581,7 +581,7 @@ mod tests { .downcast_ref::>() .ok_or_else(|| { vortex_err!( - MismatchedTypes: "expected an Int32 run-end array, got {}", + "expected an Int32 run-end array, got {}", exported.data_type() ) })?; diff --git a/encodings/uuid/src/metadata.rs b/encodings/uuid/src/metadata.rs index 83b212675be..986e0330d71 100644 --- a/encodings/uuid/src/metadata.rs +++ b/encodings/uuid/src/metadata.rs @@ -26,7 +26,7 @@ pub(crate) fn u8_to_version(b: u8) -> VortexResult { // UUID crate changed from 0xff to 0x0f for maximum uuid version in 1.23.0 0x0f => Ok(Version::Max), 0xff => Ok(Version::Max), - _ => vortex_bail!(Serde: "unknown UUID version discriminant: {b}"), + _ => vortex_bail!("unknown UUID version discriminant: {b}"), } } diff --git a/encodings/uuid/src/vtable.rs b/encodings/uuid/src/vtable.rs index 7ae5191d244..03b7400347f 100644 --- a/encodings/uuid/src/vtable.rs +++ b/encodings/uuid/src/vtable.rs @@ -45,7 +45,7 @@ impl ExtVTable for Uuid { 0 => None, 1 => Some(u8_to_version(metadata[0])?), other => { - vortex_bail!(InvalidArgument: "UUID metadata must be 0 or 1 bytes, got {other}") + vortex_bail!("UUID metadata must be 0 or 1 bytes, got {other}") } }; @@ -55,23 +55,23 @@ impl ExtVTable for Uuid { fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { let storage_dtype = ext_dtype.storage_dtype(); let DType::FixedSizeList(element_dtype, list_size, _nullability) = storage_dtype else { - vortex_bail!(InvalidArgument: "UUID storage dtype must be a FixedSizeList, got {storage_dtype}"); + vortex_bail!("UUID storage dtype must be a FixedSizeList, got {storage_dtype}"); }; vortex_ensure_eq!( *list_size as usize, UUID_BYTE_LEN, - InvalidArgument: "UUID storage FixedSizeList size mismatch" + "UUID storage FixedSizeList size mismatch" ); let DType::Primitive(ptype, elem_nullability) = element_dtype.as_ref() else { - vortex_bail!(MismatchedTypes: "UUID element dtype must be Primitive(U8), got {element_dtype}"); + vortex_bail!("UUID element dtype must be Primitive(U8), got {element_dtype}"); }; - vortex_ensure_eq!(*ptype, PType::U8, MismatchedTypes: "UUID element dtype must be U8"); + vortex_ensure_eq!(*ptype, PType::U8, "UUID element dtype must be U8"); vortex_ensure!( !elem_nullability.is_nullable(), - InvalidArgument: "UUID element dtype must be non-nullable" + "UUID element dtype must be non-nullable" ); Ok(()) @@ -85,16 +85,16 @@ impl ExtVTable for Uuid { vortex_ensure_eq!( elements.len(), UUID_BYTE_LEN, - InvalidArgument: "UUID scalar byte length mismatch" + "UUID scalar byte length mismatch" ); let mut bytes = [0u8; UUID_BYTE_LEN]; for (i, elem) in elements.iter().enumerate() { let Some(scalar_value) = elem else { - vortex_bail!(InvalidArgument: "UUID byte at index {i} must not be null"); + vortex_bail!("UUID byte at index {i} must not be null"); }; let PValue::U8(b) = scalar_value.as_primitive() else { - vortex_bail!(InvalidArgument: "UUID byte at index {i} must be U8"); + vortex_bail!("UUID byte at index {i} must be U8"); }; bytes[i] = *b; } @@ -104,11 +104,12 @@ impl ExtVTable for Uuid { // Verify the parsed UUID matches the expected version, if one is set. if let Some(expected) = ext_dtype.metadata().version { let expected = expected as u8; - let actual = parsed.get_version().ok_or_else( - || vortex_err!(InvalidArgument: "UUID has unrecognized version nibble"), - )? as u8; + let actual = parsed + .get_version() + .ok_or_else(|| vortex_err!("UUID has unrecognized version nibble"))? + as u8; - vortex_ensure_eq!(expected, actual, InvalidArgument: "UUID version mismatch"); + vortex_ensure_eq!(expected, actual, "UUID version mismatch"); } Ok(parsed) @@ -224,7 +225,7 @@ mod tests { #[test] fn unpack_native_uuid() -> VortexResult<()> { let expected = uuid::Uuid::parse_str("550e8400-e29b-41d4-a716-446655440000") - .map_err(|e| vortex_error::vortex_err!(InvalidArgument: "{e}"))?; + .map_err(|e| vortex_error::vortex_err!("{e}"))?; let ext_dtype = ExtDType::try_new( UuidMetadata::default(), @@ -241,9 +242,9 @@ mod tests { Nullability::NonNullable, ); - let storage_value = storage_scalar.value().ok_or_else( - || vortex_error::vortex_err!(MismatchedTypes: "expected non-null scalar"), - )?; + let storage_value = storage_scalar + .value() + .ok_or_else(|| vortex_error::vortex_err!("expected non-null scalar"))?; let result = Uuid::unpack_native(&ext_dtype, storage_value)?; assert_eq!(result, expected); assert_eq!(result.to_string(), "550e8400-e29b-41d4-a716-446655440000"); @@ -254,7 +255,7 @@ mod tests { fn unpack_native_rejects_version_mismatch() -> VortexResult<()> { // This is a v4 UUID. let v4_uuid = uuid::Uuid::parse_str("550e8400-e29b-41d4-a716-446655440000") - .map_err(|e| vortex_error::vortex_err!(InvalidArgument: "{e}"))?; + .map_err(|e| vortex_error::vortex_err!("{e}"))?; assert_eq!(v4_uuid.get_version(), Some(Version::Random)); // Metadata says v7, but the UUID is v4. @@ -276,9 +277,9 @@ mod tests { Nullability::NonNullable, ); - let storage_value = storage_scalar.value().ok_or_else( - || vortex_error::vortex_err!(MismatchedTypes: "expected non-null scalar"), - )?; + let storage_value = storage_scalar + .value() + .ok_or_else(|| vortex_error::vortex_err!("expected non-null scalar"))?; assert!(Uuid::unpack_native(&ext_dtype, storage_value).is_err()); Ok(()) } @@ -302,7 +303,7 @@ mod tests { fn unpack_native_accepts_matching_version() -> VortexResult<()> { // This is a v4 UUID. let v4_uuid = uuid::Uuid::parse_str("550e8400-e29b-41d4-a716-446655440000") - .map_err(|e| vortex_error::vortex_err!(InvalidArgument: "{e}"))?; + .map_err(|e| vortex_error::vortex_err!("{e}"))?; let ext_dtype = ExtDType::try_new( UuidMetadata { diff --git a/encodings/zigzag/src/array.rs b/encodings/zigzag/src/array.rs index 556e0ac03bc..101da38b521 100644 --- a/encodings/zigzag/src/array.rs +++ b/encodings/zigzag/src/array.rs @@ -67,8 +67,8 @@ impl VTable for ZigZag { ) -> VortexResult<()> { let encoded = ZigZagSlotsView::from_slots(slots).encoded; let expected_dtype = ZigZagData::dtype_from_encoded_dtype(encoded.dtype())?; - vortex_ensure_eq!(dtype, &expected_dtype, MismatchedTypes); - vortex_ensure_eq!(encoded.len(), len, InvalidArgument); + vortex_ensure_eq!(dtype, &expected_dtype); + vortex_ensure_eq!(encoded.len(), len); Ok(()) } @@ -77,11 +77,11 @@ impl VTable for ZigZag { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ZigZagArray buffer index {idx} out of bounds") + vortex_panic!("ZigZagArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "ZigZagArray buffer_name index {idx} out of bounds") + vortex_panic!("ZigZagArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -110,12 +110,12 @@ impl VTable for ZigZag { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "ZigZagArray expects empty metadata, got {} bytes", + "ZigZagArray expects empty metadata, got {} bytes", metadata.len() ); } if children.len() != 1 { - vortex_bail!(MismatchedTypes: "Expected 1 child, got {}", children.len()); + vortex_bail!("Expected 1 child, got {}", children.len()); } let ptype = PType::try_from(dtype)?; @@ -218,7 +218,10 @@ impl ZigZagData { pub fn try_new(encoded_dtype: &DType) -> VortexResult { if !encoded_dtype.is_unsigned_int() { - vortex_bail!(MismatchedTypes: "expected type: unsigned int but instead got {}", encoded_dtype); + vortex_bail!( + "expected type: unsigned int but instead got {}", + encoded_dtype + ); } Self::dtype_from_encoded_dtype(encoded_dtype)?; @@ -244,7 +247,7 @@ impl OperationsVTable for ZigZag { let array = state.array(); let scalar = state .slot(ZigZagSlots::ENCODED)? - .ok_or_else(|| vortex_err!(InvalidArgument: "ZigZag encoded slot is missing"))? + .ok_or_else(|| vortex_err!("ZigZag encoded slot is missing"))? .execute_scalar(index, ctx)?; if scalar.is_null() { return scalar.primitive_reinterpret_cast(ZigZagArrayExt::ptype(&array)); diff --git a/encodings/zigzag/src/compress.rs b/encodings/zigzag/src/compress.rs index 3d29d6c642e..b7082d4514e 100644 --- a/encodings/zigzag/src/compress.rs +++ b/encodings/zigzag/src/compress.rs @@ -28,7 +28,7 @@ pub fn zigzag_encode(parray: ArrayView<'_, Primitive>) -> VortexResult zigzag_encode_primitive::(parray.into_buffer_mut(), validity), PType::I64 => zigzag_encode_primitive::(parray.into_buffer_mut(), validity), _ => vortex_bail!( - MismatchedTypes: "ZigZag can only encode signed integers, got {}", + "ZigZag can only encode signed integers, got {}", parray.ptype() ), }; @@ -61,7 +61,7 @@ pub fn zigzag_decode(parray: PrimitiveArray) -> PrimitiveArray { PType::U32 => zigzag_decode_primitive::(parray.into_buffer_mut(), validity), PType::U64 => zigzag_decode_primitive::(parray.into_buffer_mut(), validity), _ => vortex_panic!( - MismatchedTypes: "ZigZag can only decode unsigned integers, got {}", + "ZigZag can only decode unsigned integers, got {}", parray.ptype() ), } diff --git a/encodings/zstd/src/array.rs b/encodings/zstd/src/array.rs index c5059c70c8c..78034a5fd83 100644 --- a/encodings/zstd/src/array.rs +++ b/encodings/zstd/src/array.rs @@ -195,7 +195,7 @@ impl VTable for Zstd { let mut data = array.data().clone(); if data.dictionary.is_some() { let Some((dictionary, frames)) = buffers.split_first() else { - vortex_bail!(MismatchedTypes: "Expected dictionary buffer"); + vortex_bail!("Expected dictionary buffer"); }; data.dictionary = Some(dictionary.clone().try_to_host_sync()?); data.frames = frames @@ -240,7 +240,7 @@ impl VTable for Zstd { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "ZstdArray expected 0 or 1 child, got {}", children.len()); + vortex_bail!("ZstdArray expected 0 or 1 child, got {}", children.len()); }; let (dictionary_buffer, compressed_buffers) = if metadata.dictionary_size == 0 { @@ -398,7 +398,7 @@ fn append_to_varbinview( vortex_ensure_eq!( valid_views.len(), mask.true_count(), - Serde: "Corrupt zstd metadata: the decompressed frames must hold one value per valid row of \ + "Corrupt zstd metadata: the decompressed frames must hold one value per valid row of \ the slice" ); @@ -672,7 +672,7 @@ fn walk_views( buffers.push(buffer.slice(segment_start..offset)); segment_start = offset; let Some(next_index) = buf_index.checked_add(1) else { - error = Some(vortex_err!(Overflow: "Zstd values need more than u32::MAX buffers")); + error = Some(vortex_err!("Zstd values need more than u32::MAX buffers")); break; }; buf_index = next_index; @@ -680,14 +680,14 @@ fn walk_views( let Ok(local_offset) = u32::try_from(value_data_offset - segment_start) else { error = Some(vortex_err!( - Overflow: "Zstd value offset {} does not fit in u32; max_buffer_len {max_buffer_len} is too large", + "Zstd value offset {} does not fit in u32; max_buffer_len {max_buffer_len} is too large", value_data_offset - segment_start )); break; }; let Some(value) = buffer.get(value_data_offset..value_data_offset + str_len) else { error = Some(vortex_err!( - Serde: "Corrupt zstd value: {str_len} bytes at offset {value_data_offset} run past the \ + "Corrupt zstd value: {str_len} bytes at offset {value_data_offset} run past the \ end of the {} byte frame buffer", buffer.len() )); @@ -711,7 +711,7 @@ fn slice_views( ) -> VortexResult> { vortex_ensure!( range.end <= views.len(), - Serde: "Corrupt zstd metadata: values {}..{} are out of bounds of the {} values held by the \ + "Corrupt zstd metadata: values {}..{} are out of bounds of the {} values held by the \ decompressed frames", range.start, range.end, @@ -784,7 +784,7 @@ impl DecompressedSlice { .checked_sub(self.n_skipped_values) .ok_or_else(|| { vortex_err!( - Serde: "Corrupt zstd metadata: skipped frames hold {} values, past the first \ + "Corrupt zstd metadata: skipped frames hold {} values, past the first \ requested value {}", self.n_skipped_values, self.value_idx_start @@ -795,7 +795,7 @@ impl DecompressedSlice { .checked_sub(self.n_skipped_values) .ok_or_else(|| { vortex_err!( - Serde: "Corrupt zstd metadata: skipped frames hold {} values, past the last \ + "Corrupt zstd metadata: skipped frames hold {} values, past the last \ requested value {}", self.n_skipped_values, self.value_idx_stop @@ -803,7 +803,7 @@ impl DecompressedSlice { })?; vortex_ensure!( start <= end, - Serde: "Corrupt zstd metadata: value range {start}..{end} is not ascending" + "Corrupt zstd metadata: value range {start}..{end} is not ascending" ); Ok(start..end) } @@ -828,7 +828,7 @@ impl DecompressedSlice { }; vortex_ensure!( from <= to && to <= buffer.len(), - Serde: "Corrupt zstd metadata: values {from}..{to} are out of bounds of the {} byte frame \ + "Corrupt zstd metadata: values {from}..{to} are out of bounds of the {} byte frame \ buffer", buffer.len() ); @@ -843,7 +843,7 @@ impl DecompressedSlice { let buffer = self.bytes.as_slice(); let bytes = buffer.get(range.clone()).ok_or_else(|| { vortex_err!( - Serde: "Corrupt zstd metadata: values {}..{} are out of bounds of the {} byte frame \ + "Corrupt zstd metadata: values {}..{} are out of bounds of the {} byte frame \ buffer", range.start, range.end, @@ -852,11 +852,11 @@ impl DecompressedSlice { })?; // Every value carries a length prefix, so the region must be at least that large. let prefix_bytes = n_values.checked_mul(size_of::()).ok_or_else(|| { - vortex_err!(Serde: "Corrupt zstd metadata: value count {n_values} overflows a byte count") + vortex_err!("Corrupt zstd metadata: value count {n_values} overflows a byte count") })?; let num_bytes = bytes.len().checked_sub(prefix_bytes).ok_or_else(|| { vortex_err!( - Serde: "Corrupt zstd metadata: {n_values} values do not fit in the {} bytes holding them", + "Corrupt zstd metadata: {n_values} values do not fit in the {} bytes holding them", bytes.len() ) })?; @@ -874,7 +874,7 @@ fn zstd_value_offset(buffer: &[u8], mut offset: usize, count: usize) -> VortexRe } vortex_ensure!( offset <= buffer.len(), - Serde: "Corrupt zstd values: walking {count} values ended at offset {offset}, past the end of \ + "Corrupt zstd values: walking {count} values ended at offset {offset}, past the end of \ the {} byte frame buffer", buffer.len() ); @@ -889,7 +889,7 @@ fn zstd_value_len(buffer: &[u8], offset: usize) -> VortexResult { .and_then(|rest| rest.first_chunk::<{ size_of::() }>()) .ok_or_else(|| { vortex_err!( - Serde: "Corrupt zstd values: length prefix at offset {offset} runs past the end of the \ + "Corrupt zstd values: length prefix at offset {offset} runs past the end of the \ {} byte frame buffer", buffer.len() ) @@ -955,38 +955,37 @@ impl ZstdData { dtype, DType::Primitive(..) | DType::Binary(_) | DType::Utf8(_) ), - MismatchedTypes: "Unsupported dtype for Zstd array: {dtype}" + "Unsupported dtype for Zstd array: {dtype}" ); vortex_ensure!( self.slice_start <= self.slice_stop, - InvalidArgument: "Invalid slice range {}..{}", + "Invalid slice range {}..{}", self.slice_start, self.slice_stop ); vortex_ensure!( self.slice_stop <= self.unsliced_n_rows, - InvalidArgument: "Slice stop {} exceeds unsliced row count {}", + "Slice stop {} exceeds unsliced row count {}", self.slice_stop, self.unsliced_n_rows ); - vortex_ensure_eq!(self.slice_stop - self.slice_start, len, InvalidArgument); + vortex_ensure_eq!(self.slice_stop - self.slice_start, len); if let Some(validity_len) = validity.maybe_len() { - vortex_ensure_eq!(validity_len, self.unsliced_n_rows, InvalidArgument); + vortex_ensure_eq!(validity_len, self.unsliced_n_rows); } match &self.dictionary { Some(dictionary) => vortex_ensure_eq!( usize::try_from(self.metadata.dictionary_size)?, - dictionary.len(), - Serde + dictionary.len() ), None => vortex_ensure_eq!( self.metadata.dictionary_size, 0, - Serde: "Dictionary metadata present without dictionary buffer" + "Dictionary metadata present without dictionary buffer" ), } - vortex_ensure_eq!(self.frames.len(), self.metadata.frames.len(), Serde); + vortex_ensure_eq!(self.frames.len(), self.metadata.frames.len()); for (index, (frame, metadata)) in self.frames.iter().zip(&self.metadata.frames).enumerate() { validate_frame_content_size(frame.as_slice(), metadata.uncompressed_size, index)?; @@ -1291,9 +1290,8 @@ impl ZstdData { ctx: &mut ExecutionCtx, ) -> VortexResult { let canonical = array.execute::(ctx)?; - Self::from_canonical(&canonical, level, values_per_frame, ctx)?.ok_or_else( - || vortex_err!(MismatchedTypes: "Zstd can only encode Primitive and VarBinView arrays"), - ) + Self::from_canonical(&canonical, level, values_per_frame, ctx)? + .ok_or_else(|| vortex_err!("Zstd can only encode Primitive and VarBinView arrays")) } fn byte_width(dtype: &DType) -> usize { @@ -1334,14 +1332,14 @@ impl ZstdData { let frame_uncompressed_size = usize::try_from(frame_meta.uncompressed_size).map_err(|_| { vortex_err!( - Overflow: "Zstd frame uncompressed size {} does not fit in a usize", + "Zstd frame uncompressed size {} does not fit in a usize", frame_meta.uncompressed_size ) })?; let frame_n_values = if frame_meta.n_values != 0 { usize::try_from(frame_meta.n_values).map_err(|_| { vortex_err!( - Overflow: "Zstd frame value count {} does not fit in a usize", + "Zstd frame value count {} does not fit in a usize", frame_meta.n_values ) })? @@ -1356,23 +1354,23 @@ impl ZstdData { vortex_ensure_eq!( self.frames.len(), 1, - Serde: "Zstd frame metadata for a variable-width array is missing its value count" + "Zstd frame metadata for a variable-width array is missing its value count" ); unsliced_mask.true_count() }; // Bounding the running total also bounds the two accumulators below, which partition // it between the frames we keep and the ones we skip. - let value_idx_stop = value_idx_start.checked_add(frame_n_values).ok_or_else( - || vortex_err!(Serde: "Corrupt zstd metadata: frame value counts overflow a usize"), - )?; + let value_idx_stop = value_idx_start.checked_add(frame_n_values).ok_or_else(|| { + vortex_err!("Corrupt zstd metadata: frame value counts overflow a usize") + })?; if value_idx_stop > slice_value_idx_start { // we need this frame frames_to_decompress.push(frame); uncompressed_size_to_decompress = uncompressed_size_to_decompress .checked_add(frame_uncompressed_size) .ok_or_else(|| { - vortex_err!(Serde: "Corrupt zstd metadata: frame sizes overflow a usize") + vortex_err!("Corrupt zstd metadata: frame sizes overflow a usize") })?; n_buffered_values += frame_n_values; } else { @@ -1411,7 +1409,7 @@ impl ZstdData { }; if uncompressed_start != uncompressed_size_to_decompress { vortex_bail!( - Serde: "Zstd metadata or frames were corrupt; expected {} bytes but decompressed {}", + "Zstd metadata or frames were corrupt; expected {} bytes but decompressed {}", uncompressed_size_to_decompress, uncompressed_start ); @@ -1435,7 +1433,7 @@ impl ZstdData { if !dtype.is_nullable() && !matches!(slice_validity, Validity::NonNullable) { vortex_ensure!( matches!(slice_validity, Validity::AllValid), - Serde: "ZSTD array expects to be non-nullable but there are nulls after decompression" + "ZSTD array expects to be non-nullable but there are nulls after decompression" ); slice_validity = Validity::NonNullable; @@ -1474,7 +1472,7 @@ impl ZstdData { .map(|(byte_start, byte_stop)| byte_start..byte_stop) .ok_or_else(|| { vortex_err!( - Serde: "Corrupt zstd metadata: values {start}..{end} of {} bytes each are \ + "Corrupt zstd metadata: values {start}..{end} of {} bytes each are \ out of bounds of the {} byte frame buffer", slice.byte_width, slice.bytes.len() @@ -1537,7 +1535,7 @@ impl ZstdData { } } } - _ => vortex_bail!(MismatchedTypes: "Unsupported dtype for Zstd array: {}", dtype), + _ => vortex_bail!("Unsupported dtype for Zstd array: {}", dtype), } } diff --git a/encodings/zstd/src/lib.rs b/encodings/zstd/src/lib.rs index 89e5980ea68..ea08ae07402 100644 --- a/encodings/zstd/src/lib.rs +++ b/encodings/zstd/src/lib.rs @@ -66,12 +66,12 @@ pub(crate) fn validate_frame_content_size( index: usize, ) -> VortexResult<()> { let frame_content_size = zstd::zstd_safe::get_frame_content_size(frame) - .map_err(|error| vortex_err!(InvalidArgument: "Invalid zstd frame {index}: {error}"))? - .ok_or_else(|| vortex_err!(Serde: "Zstd frame {index} does not declare a content size"))?; + .map_err(|error| vortex_err!("Invalid zstd frame {index}: {error}"))? + .ok_or_else(|| vortex_err!("Zstd frame {index} does not declare a content size"))?; vortex_ensure_eq!( metadata_size, frame_content_size, - Serde: "Zstd frame {index} metadata declares a different uncompressed size than its header" + "Zstd frame {index} metadata declares a different uncompressed size than its header" ); Ok(()) } diff --git a/encodings/zstd/src/zstd_buffers.rs b/encodings/zstd/src/zstd_buffers.rs index c4881877e74..7619ce9ec6e 100644 --- a/encodings/zstd/src/zstd_buffers.rs +++ b/encodings/zstd/src/zstd_buffers.rs @@ -78,9 +78,9 @@ impl ZstdBuffers { level: i32, session: &VortexSession, ) -> VortexResult { - let serialization = session.array_serialize(array)?.ok_or_else( - || vortex_err!(Serde: "[ZstdBuffers]: Array does not support serialization"), - )?; + let serialization = session + .array_serialize(array)? + .ok_or_else(|| vortex_err!("[ZstdBuffers]: Array does not support serialization"))?; let mut compressed_buffers = Vec::with_capacity(serialization.buffers.len()); let mut uncompressed_sizes = Vec::with_capacity(serialization.buffers.len()); @@ -132,7 +132,7 @@ impl ZstdBuffers { .registry() .get(&array.data().inner_encoding_id) .ok_or_else(|| { - vortex_err!(NotFound: "Unknown inner encoding: {}", array.data().inner_encoding_id) + vortex_err!("Unknown inner encoding: {}", array.data().inner_encoding_id) })?; let children: Vec = array.slots()[..array.data().inner_child_count] @@ -260,12 +260,12 @@ impl ZstdBuffersData { vortex_ensure_eq!( self.compressed_buffers.len(), self.uncompressed_sizes.len(), - Serde: "zstd_buffers metadata mismatch" + "zstd_buffers metadata mismatch" ); vortex_ensure_eq!( self.compressed_buffers.len(), self.buffer_alignments.len(), - Serde: "zstd_buffers metadata mismatch" + "zstd_buffers metadata mismatch" ); Ok(()) } @@ -294,7 +294,7 @@ impl ZstdBuffersData { // of the unsafe calls below. if spare.len() < size { return Err(vortex_err!( - MismatchedTypes: "Insufficient output capacity: expected at least {}, got {}", + "Insufficient output capacity: expected at least {}, got {}", size, spare.len() )); @@ -307,7 +307,7 @@ impl ZstdBuffersData { let written = decompressor.decompress_to_buffer(compressed.as_slice(), dst)?; if written != size { return Err(vortex_err!( - MismatchedTypes: "Decompressed size mismatch: expected {}, got {}", + "Decompressed size mismatch: expected {}, got {}", size, written )); @@ -467,7 +467,7 @@ impl VTable for ZstdBuffers { data.validate()?; vortex_ensure!( data.inner_child_count <= slots.len(), - InvalidArgument: "ZstdBuffers has {} slots but {} inner children", + "ZstdBuffers has {} slots but {} inner children", slots.len(), data.inner_child_count ); @@ -476,24 +476,24 @@ impl VTable for ZstdBuffers { Some(idx) => { vortex_ensure!( dtype.is_nullable(), - InvalidArgument: "ZstdBuffers validity requires a nullable dtype" + "ZstdBuffers validity requires a nullable dtype" ); vortex_ensure!( idx < slots.len(), - OutOfBounds: "ZstdBuffers validity slot {idx} out of bounds" + "ZstdBuffers validity slot {idx} out of bounds" ); vortex_ensure!( extra_slots == usize::from(idx == data.inner_child_count), - InvalidArgument: "ZstdBuffers has {extra_slots} unexpected extra slots" + "ZstdBuffers has {extra_slots} unexpected extra slots" ); - let validity = slots[idx].as_ref().ok_or_else( - || vortex_err!(InvalidArgument: "ZstdBuffers validity slot {idx} is empty"), - )?; + let validity = slots[idx] + .as_ref() + .ok_or_else(|| vortex_err!("ZstdBuffers validity slot {idx} is empty"))?; vortex_ensure_eq!(validity.dtype(), &Validity::DTYPE); vortex_ensure_eq!(validity.len(), len); } None => { - vortex_ensure_eq!(extra_slots, 0, InvalidArgument: "ZstdBuffers has unexpected extra slots") + vortex_ensure_eq!(extra_slots, 0, "ZstdBuffers has unexpected extra slots") } } Ok(()) diff --git a/fuzz/fuzz_targets/array_ops.rs b/fuzz/fuzz_targets/array_ops.rs index b483ed6e648..17324abe3c3 100644 --- a/fuzz/fuzz_targets/array_ops.rs +++ b/fuzz/fuzz_targets/array_ops.rs @@ -30,6 +30,6 @@ fuzz_target!( match run_fuzz_action(fuzz_action) { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, - Err(e) => vortex_panic!(AssertionFailed: "{e}"), + Err(e) => vortex_panic!("{e}"), } }); diff --git a/fuzz/fuzz_targets/compress_gpu.rs b/fuzz/fuzz_targets/compress_gpu.rs index a6d616a6933..91d7e9b9f9d 100644 --- a/fuzz/fuzz_targets/compress_gpu.rs +++ b/fuzz/fuzz_targets/compress_gpu.rs @@ -22,7 +22,7 @@ fuzz_target!(|fuzz: FuzzCompressGpu| -> Corpus { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, Err(e) => { - vortex_panic!(AssertionFailed: "{e}"); + vortex_panic!("{e}"); } } }); diff --git a/fuzz/fuzz_targets/compress_roundtrip.rs b/fuzz/fuzz_targets/compress_roundtrip.rs index 75ae06ccc28..bb5b9e464ce 100644 --- a/fuzz/fuzz_targets/compress_roundtrip.rs +++ b/fuzz/fuzz_targets/compress_roundtrip.rs @@ -14,7 +14,7 @@ fuzz_target!(|fuzz: FuzzCompressRoundtrip| -> Corpus { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, Err(e) => { - vortex_panic!(AssertionFailed: "{e}"); + vortex_panic!("{e}"); } } }); diff --git a/fuzz/fuzz_targets/fsst_like.rs b/fuzz/fuzz_targets/fsst_like.rs index 2cd0e18f8d9..bf61b2430cf 100644 --- a/fuzz/fuzz_targets/fsst_like.rs +++ b/fuzz/fuzz_targets/fsst_like.rs @@ -30,6 +30,6 @@ fuzz_target!( match run_fsst_like_fuzz(fuzz_action) { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, - Err(e) => vortex_panic!(AssertionFailed: "{e}"), + Err(e) => vortex_panic!("{e}"), } }); diff --git a/fuzz/fuzz_targets/row_encode.rs b/fuzz/fuzz_targets/row_encode.rs index f421128bfeb..07d63cc322c 100644 --- a/fuzz/fuzz_targets/row_encode.rs +++ b/fuzz/fuzz_targets/row_encode.rs @@ -30,6 +30,6 @@ fuzz_target!( match run_row_encode(input) { Ok(true) => Corpus::Keep, Ok(false) => Corpus::Reject, - Err(e) => vortex_panic!(AssertionFailed: "{e}"), + Err(e) => vortex_panic!("{e}"), } }); diff --git a/fuzz/src/array/compare.rs b/fuzz/src/array/compare.rs index bf8b1bcb2c0..03ce50a7170 100644 --- a/fuzz/src/array/compare.rs +++ b/fuzz/src/array/compare.rs @@ -107,9 +107,7 @@ pub fn compare_canonical_array( .decimal_value() .vortex_expect("nulls handled before") .cast::() - .unwrap_or_else( - || vortex_panic!(NotImplemented: "todo: handle upcast of decimal array"), - ); + .unwrap_or_else(|| vortex_panic!("todo: handle upcast of decimal array")); let buf = decimal_array.buffer::(); compare_to( buf.as_slice() diff --git a/fuzz/src/array/fill_null.rs b/fuzz/src/array/fill_null.rs index 6b07121dde9..69e10482658 100644 --- a/fuzz/src/array/fill_null.rs +++ b/fuzz/src/array/fill_null.rs @@ -52,7 +52,7 @@ pub fn fill_null_canonical_array( | Canonical::FixedSizeList(_) | Canonical::Extension(_) => canonical.into_array().fill_null(fill_value.clone())?, Canonical::Union(_) => { - vortex_bail!(NotImplemented: "TODO(connor)[Union]: support Union arrays in the fill_null fuzzer") + vortex_bail!("TODO(connor)[Union]: support Union arrays in the fill_null fuzzer") } Canonical::Variant(_) => unreachable!("Variant arrays are not fuzzed"), }) diff --git a/fuzz/src/array/mask.rs b/fuzz/src/array/mask.rs index 904b08edd91..c20f024448a 100644 --- a/fuzz/src/array/mask.rs +++ b/fuzz/src/array/mask.rs @@ -165,7 +165,7 @@ pub fn mask_canonical_array( ExtensionArray::new(ext_dtype, masked_storage).into_array() } Canonical::Union(_) => { - vortex_bail!(NotImplemented: "TODO(connor)[Union]: support Union arrays in the mask fuzzer") + vortex_bail!("TODO(connor)[Union]: support Union arrays in the mask fuzzer") } Canonical::Variant(_) => unreachable!("Variant arrays are not fuzzed"), }) diff --git a/fuzz/src/array/mod.rs b/fuzz/src/array/mod.rs index f23cf40b54c..638bd1559cf 100644 --- a/fuzz/src/array/mod.rs +++ b/fuzz/src/array/mod.rs @@ -142,35 +142,35 @@ impl ExpectedValue { pub fn array(self) -> ArrayRef { match self { ExpectedValue::Array(array) => array, - _ => vortex_panic!(AssertionFailed: "expected array"), + _ => vortex_panic!("expected array"), } } pub fn search(self) -> SearchResult { match self { ExpectedValue::Search(s) => s, - _ => vortex_panic!(AssertionFailed: "expected search"), + _ => vortex_panic!("expected search"), } } pub fn scalar(self) -> Scalar { match self { ExpectedValue::Scalar(s) => s, - _ => vortex_panic!(AssertionFailed: "expected scalar"), + _ => vortex_panic!("expected scalar"), } } pub fn min_max(self) -> Option { match self { ExpectedValue::MinMax(m) => m, - _ => vortex_panic!(AssertionFailed: "expected min_max"), + _ => vortex_panic!("expected min_max"), } } pub fn scalar_vec(self) -> Vec { match self { ExpectedValue::ScalarVec(v) => v, - _ => vortex_panic!(AssertionFailed: "expected scalar_vec"), + _ => vortex_panic!("expected scalar_vec"), } } } @@ -516,7 +516,7 @@ fn actions_for_dtype(dtype: &DType) -> HashSet { }) } DType::Map(..) => [Compress, Slice, Take, Filter, Mask, ScalarAt].into(), - DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), // Currently, no support at all DType::Variant(_) => unreachable!("Variant dtype shouldn't be fuzzed"), DType::Extension(_) => { @@ -650,7 +650,7 @@ pub fn run_fuzz_action(fuzz_action: FuzzArrayAction) -> VortexFuzzResult { .vortex_expect("compare operation should succeed in fuzz test"); if let Err(e) = assert_array_eq(&expected.array(), &compare_result, i, &mut ctx) { vortex_panic!( - AssertionFailed: "Failed to compare {}with {op} {v}\nError: {e}", + "Failed to compare {}with {op} {v}\nError: {e}", current_array.display_tree() ) } @@ -662,7 +662,7 @@ pub fn run_fuzz_action(fuzz_action: FuzzArrayAction) -> VortexFuzzResult { .vortex_expect("cast operation should succeed in fuzz test"); if let Err(e) = assert_array_eq(&expected.array(), &cast_result, i, &mut ctx) { vortex_panic!( - AssertionFailed: "Failed to cast {} to dtype {to}\nError: {e}", + "Failed to cast {} to dtype {to}\nError: {e}", current_array.display_tree() ) } diff --git a/fuzz/src/array/scalar_at.rs b/fuzz/src/array/scalar_at.rs index 5d73ee3d6b1..c978aacbc0d 100644 --- a/fuzz/src/array/scalar_at.rs +++ b/fuzz/src/array/scalar_at.rs @@ -108,7 +108,7 @@ pub fn scalar_at_canonical_array( Scalar::extension_ref(array.ext_dtype().clone(), storage_scalar) } Canonical::Union(_) => { - vortex_bail!(NotImplemented: "TODO(connor)[Union]: support Union arrays in the scalar_at fuzzer") + vortex_bail!("TODO(connor)[Union]: support Union arrays in the scalar_at fuzzer") } Canonical::Map(array) => { let entries = array.entries_at(index, ctx)?.execute::(ctx)?; diff --git a/fuzz/src/array/search_sorted.rs b/fuzz/src/array/search_sorted.rs index b728de1a462..eb9c8131001 100644 --- a/fuzz/src/array/search_sorted.rs +++ b/fuzz/src/array/search_sorted.rs @@ -122,11 +122,11 @@ pub fn search_sorted_canonical_array( .decimal_value() .map(|v| { v.cast::().ok_or_else(|| { - vortex_err!(MismatchedTypes: "cannot cast value {v} to decimal value type {d}") + vortex_err!("cannot cast value {v} to decimal value type {d}") }) }) .transpose()? - .ok_or_else(|| vortex_err!(AssertionFailed: "unexpected null scalar"))?; + .ok_or_else(|| vortex_err!("unexpected null scalar"))?; Ok(linear_search( opt_values.iter().map(|value| value.cmp(&Some(to_find))), side, diff --git a/fuzz/src/array/sum/mod.rs b/fuzz/src/array/sum/mod.rs index f9488f47a38..98b3f69ce2c 100644 --- a/fuzz/src/array/sum/mod.rs +++ b/fuzz/src/array/sum/mod.rs @@ -68,7 +68,7 @@ pub fn sum_canonical_array( ) }) } - _ => vortex_bail!(NotImplemented: "Unsupported sum dtype: {}", array.dtype()), + _ => vortex_bail!("Unsupported sum dtype: {}", array.dtype()), } } @@ -141,6 +141,6 @@ fn native_values(array: &ArrayRef, ctx: &mut ExecutionCtx) -> Vortex .map(|value| T::from(value).vortex_expect("decimal value fits accumulator")) .collect() }), - _ => vortex_bail!(NotImplemented: "Unsupported sum dtype: {}", array.dtype()), + _ => vortex_bail!("Unsupported sum dtype: {}", array.dtype()), }) } diff --git a/fuzz/src/array/sum/tests.rs b/fuzz/src/array/sum/tests.rs index 4f770745b89..f48fb01604f 100644 --- a/fuzz/src/array/sum/tests.rs +++ b/fuzz/src/array/sum/tests.rs @@ -144,7 +144,7 @@ fn test_sum_decimal_storage(#[case] values_type: DecimalType) -> VortexResult<() let array = match_each_decimal_value_type!(values_type, |D| { let value = DecimalValue::I8(99) .cast::() - .ok_or_else(|| vortex_err!(AssertionFailed: "99 fits in every decimal storage type"))?; + .ok_or_else(|| vortex_err!("99 fits in every decimal storage type"))?; DecimalArray::new( buffer![value, value, -value], DecimalDType::new(2, 0), @@ -323,7 +323,7 @@ fn test_sum_action_accepts_unambiguous_inputs( actions.push((Action::Sum, ExpectedValue::Scalar(expected))); assert!( run_fuzz_action(FuzzArrayAction { array, actions }) - .map_err(|error| vortex_err!(AssertionFailed: "{error}"))? + .map_err(|error| vortex_err!("{error}"))? ); Ok(()) } diff --git a/fuzz/src/fsst_like.rs b/fuzz/src/fsst_like.rs index 5d8ab7338cf..0cd9b4c0cae 100644 --- a/fuzz/src/fsst_like.rs +++ b/fuzz/src/fsst_like.rs @@ -139,7 +139,7 @@ pub fn run_fsst_like_fuzz(fuzz: FuzzFsstLike) -> VortexFuzzResult { if expected_val != actual_val { return Err(VortexFuzzError::VortexError( vortex_error::vortex_err!( - MismatchedTypes: "FSST LIKE mismatch at index {idx}:\n \ + "FSST LIKE mismatch at index {idx}:\n \ pattern: {pattern:?}\n \ string: {:?}\n \ expected: {expected_val}\n \ diff --git a/fuzz/src/gpu/mod.rs b/fuzz/src/gpu/mod.rs index 3cccde25f20..91e116e38cd 100644 --- a/fuzz/src/gpu/mod.rs +++ b/fuzz/src/gpu/mod.rs @@ -104,7 +104,7 @@ pub async fn run_compress_gpu(fuzz: FuzzCompressGpu) -> VortexFuzzResult { if !vortex_cuda::cuda_available() { return Err(VortexFuzzError::VortexError( - vortex_err!(Io: "no cuda device to run the fuzzer on"), + vortex_err!("no cuda device to run the fuzzer on"), Backtrace::capture(), )); } diff --git a/lang/cpp/include/vortex/array.hpp b/lang/cpp/include/vortex/array.hpp index 88d06e51905..3da45d83a70 100644 --- a/lang/cpp/include/vortex/array.hpp +++ b/lang/cpp/include/vortex/array.hpp @@ -442,7 +442,7 @@ PrimitiveView Array::values(const Session &session) const { Array canonical = canonicalize(session); const vx_array *raw = detail::Access::c_ptr(canonical); if (!vx_array_is_primitive(raw, detail::to_ptype())) { - throw VortexException("values: T does not match the array's ptype", ErrorCode::MismatchedTypes); + throw VortexException("values: T does not match the array's ptype"); } vx_error *error = nullptr; const void *data = vx_array_data_ptr_primitive(raw, &error); diff --git a/lang/cpp/include/vortex/error.hpp b/lang/cpp/include/vortex/error.hpp index 8f01c0c782d..60b8d298958 100644 --- a/lang/cpp/include/vortex/error.hpp +++ b/lang/cpp/include/vortex/error.hpp @@ -11,21 +11,13 @@ namespace vortex { enum class ErrorCode { Other = VX_ERROR_CODE_OTHER, - OutOfBounds = VX_ERROR_CODE_OUT_OF_BOUNDS, - InvalidArgument = VX_ERROR_CODE_INVALID_ARGUMENT, - Serialization = VX_ERROR_CODE_SERIALIZATION, - NotImplemented = VX_ERROR_CODE_NOT_IMPLEMENTED, - MismatchedTypes = VX_ERROR_CODE_MISMATCHED_TYPES, - AssertionFailed = VX_ERROR_CODE_ASSERTION_FAILED, - Io = VX_ERROR_CODE_IO, Panic = VX_ERROR_CODE_PANIC, - NotFound = VX_ERROR_CODE_NOT_FOUND, - Overflow = VX_ERROR_CODE_OVERFLOW, }; class VortexException : public std::runtime_error { public: - VortexException(const std::string &message, ErrorCode code) : std::runtime_error(message), code_(code) { + explicit VortexException(const std::string &message, ErrorCode code = ErrorCode::Other) + : std::runtime_error(message), code_(code) { } ErrorCode code() const { diff --git a/lang/cpp/include/vortex/estimate.hpp b/lang/cpp/include/vortex/estimate.hpp index 1b412555b0f..ff6f3c332b5 100644 --- a/lang/cpp/include/vortex/estimate.hpp +++ b/lang/cpp/include/vortex/estimate.hpp @@ -31,7 +31,7 @@ class Estimate { */ inline uint64_t value() const { if (type() == EstimateType::Unknown) { - throw VortexException("estimate is unknown", ErrorCode::InvalidArgument); + throw VortexException("estimate is unknown"); } return raw_.estimate; } diff --git a/lang/cpp/include/vortex/scalar.hpp b/lang/cpp/include/vortex/scalar.hpp index 9c4b7a39dd4..4deed75be05 100644 --- a/lang/cpp/include/vortex/scalar.hpp +++ b/lang/cpp/include/vortex/scalar.hpp @@ -65,86 +65,85 @@ class Scalar { template T Scalar::get() const { using enum DataTypeVariant; - using enum ErrorCode; using enum PType; const DataType data_type = dtype(); const DataTypeVariant variant = data_type.variant(); if (is_null()) { - throw VortexException("Scalar is null", InvalidArgument); + throw VortexException("Scalar is null"); } const vx_scalar *const h = handle_.get(); if constexpr (std::is_same_v) { if (variant != Bool) { - throw VortexException("scalar get type doesn't match", InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_bool(h); } else if constexpr (std::is_same_v) { if (variant != Utf8) { - throw VortexException("scalar get type doesn't match", InvalidArgument); + throw VortexException("scalar get type doesn't match"); } vx_view v = vx_scalar_get_utf8(h); return std::string_view(v.ptr, v.len); } else if constexpr (std::is_same_v) { if (variant != Binary) { - throw VortexException("scalar get type doesn't match", InvalidArgument); + throw VortexException("scalar get type doesn't match"); } vx_view v = vx_scalar_get_binary(h); return BinaryView(reinterpret_cast(v.ptr), v.len); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != U8) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_u8(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != U16) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_u16(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != U32) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_u32(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != U64) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_u64(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != I8) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_i8(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != I16) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_i16(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != I32) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_i32(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != I64) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_i64(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != F32) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_f32(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != F64) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } return vx_scalar_get_f64(h); } else if constexpr (std::is_same_v) { if (variant != Primitive || data_type.primitive_type() != F16) { - throw VortexException("scalar get type doesn't match", ErrorCode::InvalidArgument); + throw VortexException("scalar get type doesn't match"); } const uint16_t bits = vx_scalar_get_f16_bits(h); #if __STDCPP_FLOAT16_T__ != 1 @@ -160,10 +159,10 @@ T Scalar::get() const { template T Scalar::get_decimal() const { if (is_null()) { - throw VortexException("Scalar is null", ErrorCode::InvalidArgument); + throw VortexException("Scalar is null"); } if (dtype().variant() != DataTypeVariant::Decimal) { - throw VortexException("DataType is not Decimal", ErrorCode::InvalidArgument); + throw VortexException("DataType is not Decimal"); } const vx_scalar *const h = handle_.get(); if constexpr (std::is_same_v) { diff --git a/lang/cpp/src/array.cpp b/lang/cpp/src/array.cpp index f774c3c2228..2e0775ce613 100644 --- a/lang/cpp/src/array.cpp +++ b/lang/cpp/src/array.cpp @@ -26,14 +26,13 @@ Validity::Validity(const Validity &other) Validity::Validity(ValidityType type) : type_(type), array_(nullptr) { if (type == ValidityType::FromArray) { - throw VortexException("Validity(ValidityType) called with ValidityType::FromArray", - ErrorCode::InvalidArgument); + throw VortexException("Validity(ValidityType) called with ValidityType::FromArray"); } } Validity Validity::from_array(const Array &bools) { if (!bools.has_dtype(DataTypeVariant::Bool)) { - throw VortexException("Validity array isn't a Bool array", ErrorCode::InvalidArgument); + throw VortexException("Validity array isn't a Bool array"); } return {ValidityType::FromArray, vx_array_clone(Access::c_ptr(bools))}; } @@ -67,7 +66,7 @@ Validity::~Validity() { Array Validity::array() const { if (type_ != ValidityType::FromArray || array_ == nullptr) { - throw VortexException("validity has no backing array", ErrorCode::InvalidArgument); + throw VortexException("validity has no backing array"); } return Access::adopt(vx_array_clone(array_)); } @@ -139,7 +138,7 @@ ValidityBits::~ValidityBits() { static const vx_struct_fields *struct_fields_or_throw(const vx_dtype *dtype) { const vx_struct_fields *fields = vx_dtype_struct_dtype(dtype); if (fields == nullptr) { - throw VortexException("dtype is not a struct", ErrorCode::MismatchedTypes); + throw VortexException("dtype is not a struct"); } return fields; } @@ -254,7 +253,7 @@ Array Array::field(std::string_view name) const { return this->field(i); } } - throw VortexException("no field named \"" + std::string(name) + "\"", ErrorCode::NotFound); + throw VortexException("no field named \"" + std::string(name) + "\""); } Array Array::slice(size_t begin, size_t end) const { @@ -311,7 +310,7 @@ PrimitiveView Array::bools(const Session &session) const { Array canonical = canonicalize(session); const vx_array *raw = Access::c_ptr(canonical); if (!vx_array_has_dtype(raw, DTYPE_BOOL)) { - throw VortexException("bools(): array is not a Bool array", ErrorCode::MismatchedTypes); + throw VortexException("bools(): array is not a Bool array"); } detail::ValidityBits validity(session, raw); const size_t len = vx_array_len(raw); @@ -322,7 +321,7 @@ StringView Array::strings(const Session &session) const { Array canonical = canonicalize(session); const vx_array *raw = Access::c_ptr(canonical); if (!vx_array_has_dtype(raw, DTYPE_UTF8)) { - throw VortexException("strings(): array is not a Utf8 array", ErrorCode::MismatchedTypes); + throw VortexException("strings(): array is not a Utf8 array"); } detail::ValidityBits validity(session, raw); const size_t len = vx_array_len(raw); @@ -333,7 +332,7 @@ BytesView Array::bytes(const Session &session) const { Array canonical = canonicalize(session); const vx_array *raw = Access::c_ptr(canonical); if (!vx_array_has_dtype(raw, DTYPE_BINARY)) { - throw VortexException("bytes(): array is not a Binary array", ErrorCode::MismatchedTypes); + throw VortexException("bytes(): array is not a Binary array"); } detail::ValidityBits validity(session, raw); const size_t len = vx_array_len(raw); diff --git a/lang/cpp/src/dtype.cpp b/lang/cpp/src/dtype.cpp index af7d42ccbd4..c4157495d49 100644 --- a/lang/cpp/src/dtype.cpp +++ b/lang/cpp/src/dtype.cpp @@ -76,7 +76,7 @@ namespace { const vx_struct_fields *struct_fields_or_throw(const vx_dtype *dtype) { const vx_struct_fields *fields = vx_dtype_struct_dtype(dtype); if (fields == nullptr) { - throw VortexException("dtype is not a struct", ErrorCode::MismatchedTypes); + throw VortexException("dtype is not a struct"); } return fields; } @@ -92,12 +92,11 @@ std::vector DataType::fields() const { for (uint64_t idx = 0; idx < fields_size; ++idx) { const vx_view name = vx_struct_fields_field_name(fields.get(), idx); if (name.ptr == nullptr) { - throw VortexException("error getting field name at index "s + std::to_string(idx), - ErrorCode::Other); + throw VortexException("error getting field name at index "s + std::to_string(idx)); } const vx_dtype *dtype = vx_struct_fields_field_dtype(fields.get(), idx); if (dtype == nullptr) { - throw VortexException("error getting dtype at index "s + std::to_string(idx), ErrorCode::Other); + throw VortexException("error getting dtype at index "s + std::to_string(idx)); } out.push_back(StructField {{name.ptr, name.len}, DataType(dtype)}); } @@ -107,7 +106,7 @@ std::vector DataType::fields() const { DataType DataType::list_element() const { const vx_dtype *element = vx_dtype_list_element(handle_.get()); if (element == nullptr) { - throw VortexException("dtype is not a list", ErrorCode::MismatchedTypes); + throw VortexException("dtype is not a list"); } return DataType(element); } @@ -115,7 +114,7 @@ DataType DataType::list_element() const { DataType DataType::fixed_size_list_element() const { const vx_dtype *element = vx_dtype_fixed_size_list_element(handle_.get()); if (element == nullptr) { - throw VortexException("dtype is not a fixed-size list", ErrorCode::MismatchedTypes); + throw VortexException("dtype is not a fixed-size list"); } return DataType(element); } diff --git a/lang/cpp/src/expression.cpp b/lang/cpp/src/expression.cpp index d314ae26293..93ee6fe075a 100644 --- a/lang/cpp/src/expression.cpp +++ b/lang/cpp/src/expression.cpp @@ -35,7 +35,7 @@ Expression &Expression::operator=(const Expression &other) { Expression Expression::operator[](std::string_view field) const { vx_expression *out = vx_expression_get_item(to_view(field), handle_.get()); if (out == nullptr) { - throw VortexException("get_item: field name is not valid UTF-8", ErrorCode::InvalidArgument); + throw VortexException("get_item: field name is not valid UTF-8"); } return Access::adopt(out); } @@ -129,7 +129,7 @@ static Expression combine(vx_expression *(*combiner)(const vx_expression *const } vx_expression *out = combiner(raw.data(), raw.size()); if (out == nullptr) { - throw VortexException("empty expression list", ErrorCode::InvalidArgument); + throw VortexException("empty expression list"); } return Access::adopt(out); } diff --git a/lang/cpp/src/scalar.cpp b/lang/cpp/src/scalar.cpp index f0427aec647..85988c4db25 100644 --- a/lang/cpp/src/scalar.cpp +++ b/lang/cpp/src/scalar.cpp @@ -80,7 +80,7 @@ vx_scalar *make_primitive(vx_ptype ptype, const void *value, bool nullable) { case PTYPE_F64: return vx_scalar_new_f64(*static_cast(value), nullable); } - throw VortexException("unsupported ptype", ErrorCode::InvalidArgument); + throw VortexException("unsupported ptype"); } vx_scalar *make_utf8(std::string_view value, bool nullable) { diff --git a/lang/cpp/src/writer.cpp b/lang/cpp/src/writer.cpp index 57035171a14..ef2c790866d 100644 --- a/lang/cpp/src/writer.cpp +++ b/lang/cpp/src/writer.cpp @@ -33,7 +33,7 @@ Writer Writer::open(const Session &session, std::string_view path, const DataTyp void Writer::push(std::span arrays) { if (handle_ == nullptr) { - throw VortexException("null handle_", ErrorCode::InvalidArgument); + throw VortexException("null handle_"); } vx_error *error = nullptr; for (const Array &array : arrays) { @@ -52,7 +52,7 @@ void Writer::push(std::initializer_list arrays) { void Writer::finish() { if (handle_ == nullptr) { - throw VortexException("finish() called twice", ErrorCode::InvalidArgument); + throw VortexException("finish() called twice"); } vx_error *error = nullptr; vx_array_sink_close(handle_.release(), &error); diff --git a/lang/cpp/tests/array.cpp b/lang/cpp/tests/array.cpp index 3b0f5b842ff..6fa75f94072 100644 --- a/lang/cpp/tests/array.cpp +++ b/lang/cpp/tests/array.cpp @@ -220,8 +220,8 @@ TEST_CASE("Error with a code", "[array]") { (void)a.scalar_at(Session {}, 2); FAIL("expected exception"); } catch (const VortexException &e) { - REQUIRE_FALSE(std::string(e.what()).empty()); - REQUIRE(e.code() == ErrorCode::OutOfBounds); + REQUIRE(std::string(e.what()).find("out of bounds") != std::string::npos); + REQUIRE(e.code() == ErrorCode::Other); } } } // namespace diff --git a/vortex-array/benches/row_fn_bool_retry.rs b/vortex-array/benches/row_fn_bool_retry.rs index dd25f961145..858c7eb8a3a 100644 --- a/vortex-array/benches/row_fn_bool_retry.rs +++ b/vortex-array/benches/row_fn_bool_retry.rs @@ -86,7 +86,7 @@ impl RowFn for Predicate { visitor.visit_deferred_bool::<(i64, i64), bool, true>( |(lhs, rhs)| (lhs < rhs, lhs == i64::MAX || rhs == i64::MAX), |failed| { - vortex_ensure!(!failed, AssertionFailed: "predicate rejected sentinel"); + vortex_ensure!(!failed, "predicate rejected sentinel"); Ok(()) }, ) diff --git a/vortex-array/benches/row_fn_output.rs b/vortex-array/benches/row_fn_output.rs index 0314b54c8eb..200a04a7810 100644 --- a/vortex-array/benches/row_fn_output.rs +++ b/vortex-array/benches/row_fn_output.rs @@ -148,7 +148,7 @@ impl RowFn for DeferredBool { |negative| { vortex_ensure!( !negative, - InvalidArgument: "deferred-bool benchmark inputs must be nonnegative" + "deferred-bool benchmark inputs must be nonnegative" ); Ok(()) }, @@ -178,7 +178,7 @@ impl RowFn for DeferredI64 { |overflowed| { vortex_ensure!( !overflowed, - Overflow: "deferred-i64 benchmark inputs must not overflow" + "deferred-i64 benchmark inputs must not overflow" ); Ok(()) }, diff --git a/vortex-array/src/aggregate_fn/accumulator.rs b/vortex-array/src/aggregate_fn/accumulator.rs index 46dfa31a3a3..388d92ffd2f 100644 --- a/vortex-array/src/aggregate_fn/accumulator.rs +++ b/vortex-array/src/aggregate_fn/accumulator.rs @@ -120,7 +120,7 @@ impl Accumulator { vortex_ensure_eq!( result.dtype(), &self.dtypes.partial_dtype, - AssertionFailed: "Aggregate kernel returned the wrong partial dtype", + "Aggregate kernel returned the wrong partial dtype", ); self.fold_partial_scalar(&result)?; return Ok(()); @@ -156,7 +156,7 @@ impl Accumulator { vortex_ensure_eq!( result.dtype(), &self.dtypes.partial_dtype, - AssertionFailed: "Aggregate kernel returned the wrong partial dtype", + "Aggregate kernel returned the wrong partial dtype", ); self.fold_partial_scalar(&result)?; return Ok(()); @@ -234,7 +234,7 @@ impl DynAccumulator for Accumulator { return Ok(()); } - vortex_ensure_eq!(batch.dtype(), &self.dtypes.dtype, MismatchedTypes: "Input DType mismatch"); + vortex_ensure_eq!(batch.dtype(), &self.dtypes.dtype, "Input DType mismatch"); // Legacy stats bridge: an aggregate still cached under a legacy `Stat` slot consumes that // exact stat before kernel dispatch or decode, and otherwise caches its result there. @@ -250,7 +250,7 @@ impl DynAccumulator for Accumulator { partial .dtype() .eq_ignore_nullability(&self.dtypes.partial_dtype), - MismatchedTypes: "Aggregate {} read legacy stat {} with dtype {}, expected {}", + "Aggregate {} read legacy stat {} with dtype {}, expected {}", self.aggregate_fn, stat, partial.dtype(), @@ -286,13 +286,13 @@ impl DynAccumulator for Accumulator { fn merge_from(&mut self, other: &mut dyn DynAccumulator) -> VortexResult<()> { let Some(other) = other.downcast_mut::() else { vortex_bail!( - MismatchedTypes: "Cannot merge into a {} accumulator from an accumulator of a different aggregate", + "Cannot merge into a {} accumulator from an accumulator of a different aggregate", self.aggregate_fn, ); }; vortex_ensure!( other.options == self.options && other.dtypes.dtype == self.dtypes.dtype, - InvalidArgument: "Cannot merge {} accumulators with different options or input dtypes", + "Cannot merge {} accumulators with different options or input dtypes", self.aggregate_fn, ); match other.partial.take() { @@ -305,7 +305,7 @@ impl DynAccumulator for Accumulator { vortex_ensure_eq!( partial.dtype(), &self.dtypes.partial_dtype, - MismatchedTypes: "Partial DType mismatch for {}", + "Partial DType mismatch for {}", self.aggregate_fn, ); self.fold_partial_scalar(partial) @@ -338,7 +338,7 @@ impl DynAccumulator for Accumulator { vortex_ensure_eq!( partial.dtype(), args.partial_dtype, - AssertionFailed: "Aggregate returned incorrect DType on partial_scalar", + "Aggregate returned incorrect DType on partial_scalar", ); } @@ -355,7 +355,7 @@ impl DynAccumulator for Accumulator { vortex_ensure_eq!( result.dtype(), args.return_dtype, - AssertionFailed: "Aggregate returned incorrect DType on final_scalar", + "Aggregate returned incorrect DType on final_scalar", ); Ok(result) diff --git a/vortex-array/src/aggregate_fn/accumulator_grouped.rs b/vortex-array/src/aggregate_fn/accumulator_grouped.rs index b24c0cd3eeb..832f4a06f78 100644 --- a/vortex-array/src/aggregate_fn/accumulator_grouped.rs +++ b/vortex-array/src/aggregate_fn/accumulator_grouped.rs @@ -234,14 +234,14 @@ impl DynGroupedAccumulator for GroupedAccumulator { DType::List(elem, _) => elem, DType::FixedSizeList(elem, ..) => elem, _ => vortex_bail!( - MismatchedTypes: "Input DType mismatch: expected List or FixedSizeList, got {}", + "Input DType mismatch: expected List or FixedSizeList, got {}", groups.dtype() ), }; vortex_ensure_eq!( elements_dtype.as_ref(), &self.dtypes.dtype, - MismatchedTypes: "Input DType mismatch" + "Input DType mismatch" ); // We first execute the groups until it is a ListView or FixedSizeList, since we only @@ -254,7 +254,7 @@ impl DynGroupedAccumulator for GroupedAccumulator { Canonical::List(groups) => self.accumulate_grouped_array(groups.into(), ctx), Canonical::FixedSizeList(groups) => self.accumulate_grouped_array(groups.into(), ctx), _ => { - vortex_panic!(AssertionFailed: "We checked the DType above, so this should never happen") + vortex_panic!("We checked the DType above, so this should never happen") } } } @@ -276,7 +276,7 @@ impl DynGroupedAccumulator for GroupedAccumulator { vortex_ensure_eq!( results.dtype(), &self.dtypes.return_dtype, - AssertionFailed: "Return DType mismatch" + "Return DType mismatch" ); Ok(results) @@ -369,7 +369,7 @@ impl GroupedAccumulator { vortex_ensure_eq!( state.dtype(), &self.dtypes.partial_dtype, - AssertionFailed: "State DType mismatch" + "State DType mismatch" ); self.partials.push(state); Ok(()) diff --git a/vortex-array/src/aggregate_fn/combined.rs b/vortex-array/src/aggregate_fn/combined.rs index 91c1561ee51..842603c672e 100644 --- a/vortex-array/src/aggregate_fn/combined.rs +++ b/vortex-array/src/aggregate_fn/combined.rs @@ -118,7 +118,7 @@ pub trait BinaryCombined: 'static + Send + Sync + Clone { ) -> VortexResult> { let _ = (metadata, session); vortex_bail!( - Serde: "Combined aggregate function {} is not deserializable", + "Combined aggregate function {} is not deserializable", BinaryCombined::id(self) ); } @@ -146,7 +146,7 @@ fn child_return_dtype( ) -> VortexResult { vtable.return_dtype(options, input_dtype).ok_or_else(|| { vortex_err!( - InvalidArgument: "Aggregate function {} cannot be applied to dtype {}", + "Aggregate function {} cannot be applied to dtype {}", vtable.id(), input_dtype ) @@ -174,7 +174,7 @@ impl Combined { ) -> VortexResult<(AggregateDTypes, AggregateDTypes)> { let partials = args.partial_dtype.as_struct_fields_opt().ok_or_else(|| { vortex_err!( - MismatchedTypes: "Combined partial dtype must be a struct, got {}", + "Combined partial dtype must be a struct, got {}", args.partial_dtype ) })?; @@ -182,7 +182,7 @@ impl Combined { [partials.field_by_index(0), partials.field_by_index(1)] else { vortex_bail!( - MismatchedTypes: "Combined partial dtype {} must have two fields", + "Combined partial dtype {} must have two fields", args.partial_dtype ); }; @@ -254,12 +254,12 @@ impl AggregateFnVTable for Combined { let s = scalar.as_struct(); let lname = self.0.left_name(); let rname = self.0.right_name(); - let l_field = s.field(lname).ok_or_else( - || vortex_err!(NotFound: "BinaryCombined partial missing `{}` field", lname), - )?; - let r_field = s.field(rname).ok_or_else( - || vortex_err!(NotFound: "BinaryCombined partial missing `{}` field", rname), - )?; + let l_field = s + .field(lname) + .ok_or_else(|| vortex_err!("BinaryCombined partial missing `{}` field", lname))?; + let r_field = s + .field(rname) + .ok_or_else(|| vortex_err!("BinaryCombined partial missing `{}` field", rname))?; left.combine_partials(&l_field)?; right.combine_partials(&r_field)?; } diff --git a/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs b/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs index b4b020b34fe..adfb4a22954 100644 --- a/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/all_non_distinct/mod.rs @@ -64,7 +64,7 @@ use crate::validity::Validity; pub fn all_non_distinct(a: &ArrayRef, b: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { if a.dtype() != b.dtype() { vortex_bail!( - MismatchedTypes: "all_non_distinct: dtype mismatch: {} vs {}", + "all_non_distinct: dtype mismatch: {} vs {}", a.dtype(), b.dtype() ); @@ -72,7 +72,7 @@ pub fn all_non_distinct(a: &ArrayRef, b: &ArrayRef, ctx: &mut ExecutionCtx) -> V if a.len() != b.len() { vortex_bail!( - MismatchedTypes: "all_non_distinct: length mismatch: {} vs {}", + "all_non_distinct: length mismatch: {} vs {}", a.len(), b.len() ); @@ -130,7 +130,7 @@ impl AggregateFnVTable for AllNonDistinct { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!(NotImplemented: "AllNonDistinct is not yet serializable"); + vortex_bail!("AllNonDistinct is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { @@ -217,7 +217,7 @@ impl AggregateFnVTable for AllNonDistinct { Columnar::Canonical(c) => { let Canonical::Struct(s) = c else { vortex_bail!( - InvalidArgument: "AllNonDistinct expects a Struct canonical, got {:?}", + "AllNonDistinct expects a Struct canonical, got {:?}", c.dtype() ); }; @@ -255,7 +255,7 @@ impl AggregateFnVTable for AllNonDistinct { _args: AggregateArgs<'_, Self::Options>, _partials: ArrayRef, ) -> VortexResult { - vortex_bail!(InvalidArgument: "AllNonDistinct does not support array finalization"); + vortex_bail!("AllNonDistinct does not support array finalization"); } fn finalize_scalar( @@ -298,7 +298,7 @@ fn check_canonical_identical( check_variant_identical(lhs, rhs, ctx) } _ => Err(vortex_err!( - MismatchedTypes: "Canonical type mismatch in AllNonDistinct: {:?} vs {:?}", + "Canonical type mismatch in AllNonDistinct: {:?} vs {:?}", lhs.dtype(), rhs.dtype() )), diff --git a/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs b/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs index bc809f93f66..d9ae58f6669 100644 --- a/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/bounded_max/mod.rs @@ -142,12 +142,12 @@ impl AggregateFnVTable for BoundedMax { vortex_ensure_eq!( metadata.len(), size_of::(), - Serde: "BoundedMax options have the wrong byte length" + "BoundedMax options have the wrong byte length" ); let mut bytes = [0u8; size_of::()]; bytes.copy_from_slice(metadata); let max_bytes = usize::try_from(u64::from_le_bytes(bytes))?; - vortex_ensure!(max_bytes > 0, InvalidArgument: "BoundedMax requires max_bytes > 0"); + vortex_ensure!(max_bytes > 0, "BoundedMax requires max_bytes > 0"); Ok(BoundedMaxOptions { max_bytes: NonZeroUsize::new(max_bytes).vortex_expect("checked non-zero max_bytes"), }) @@ -207,18 +207,18 @@ impl AggregateFnVTable for BoundedMax { } else { let Some(fields) = scalar.as_struct_opt() else { vortex_bail!( - MismatchedTypes: "BoundedMax partial must be a struct, got {}", + "BoundedMax partial must be a struct, got {}", scalar.dtype() ); }; let Some(bound) = fields.field_by_idx(0) else { - vortex_bail!(NotFound: "BoundedMax partial is missing its bound field"); + vortex_bail!("BoundedMax partial is missing its bound field"); }; let Some(unknown) = fields .field_by_idx(1) .and_then(|unknown| unknown.as_bool().value()) else { - vortex_bail!(NotFound: "BoundedMax partial is missing its non-null unknown field"); + vortex_bail!("BoundedMax partial is missing its non-null unknown field"); }; if unknown { diff --git a/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs b/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs index 35491e68dba..c6c8b1ce7ed 100644 --- a/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/bounded_min/mod.rs @@ -96,12 +96,12 @@ impl AggregateFnVTable for BoundedMin { vortex_ensure_eq!( metadata.len(), size_of::(), - Serde: "BoundedMin options have the wrong byte length" + "BoundedMin options have the wrong byte length" ); let mut bytes = [0u8; size_of::()]; bytes.copy_from_slice(metadata); let max_bytes = usize::try_from(u64::from_le_bytes(bytes))?; - vortex_ensure!(max_bytes > 0, InvalidArgument: "BoundedMin requires max_bytes > 0"); + vortex_ensure!(max_bytes > 0, "BoundedMin requires max_bytes > 0"); Ok(BoundedMinOptions { max_bytes: NonZeroUsize::new(max_bytes).vortex_expect("checked non-zero max_bytes"), }) diff --git a/vortex-array/src/aggregate_fn/fns/count/mod.rs b/vortex-array/src/aggregate_fn/fns/count/mod.rs index fc3b22439c2..ba9a97fc7f8 100644 --- a/vortex-array/src/aggregate_fn/fns/count/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/count/mod.rs @@ -42,7 +42,7 @@ impl AggregateFnVTable for Count { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!(NotImplemented: "Count is not yet serializable"); + vortex_bail!("Count is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, _input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/first/mod.rs b/vortex-array/src/aggregate_fn/fns/first/mod.rs index 603bc077a0b..5f614532482 100644 --- a/vortex-array/src/aggregate_fn/fns/first/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/first/mod.rs @@ -46,7 +46,7 @@ impl AggregateFnVTable for First { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!(NotImplemented: "First is not yet serializable"); + vortex_bail!("First is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs b/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs index e3cfb52cfe2..ff8e526402b 100644 --- a/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/is_constant/mod.rs @@ -275,7 +275,7 @@ impl AggregateFnVTable for IsConstant { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!(NotImplemented: "IsConstant is not yet serializable"); + vortex_bail!("IsConstant is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { @@ -426,10 +426,10 @@ impl AggregateFnVTable for IsConstant { Canonical::FixedSizeList(f) => check_fixed_size_list_constant(f, ctx)?, Canonical::Null(_) => true, Canonical::Union(_) => { - vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement IsConstant for Union arrays") + vortex_bail!("TODO(connor)[Union]: implement IsConstant for Union arrays") } Canonical::Variant(_) => { - vortex_bail!(NotImplemented: "Variant arrays don't support IsConstant") + vortex_bail!("Variant arrays don't support IsConstant") } }; diff --git a/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs b/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs index 9acf0da62eb..402eb1f6fb8 100644 --- a/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/is_sorted/mod.rs @@ -252,7 +252,7 @@ impl AggregateFnVTable for IsSorted { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!(NotImplemented: "IsSorted is not yet serializable"); + vortex_bail!("IsSorted is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/last/mod.rs b/vortex-array/src/aggregate_fn/fns/last/mod.rs index ffc0e140d79..1a631ede3a0 100644 --- a/vortex-array/src/aggregate_fn/fns/last/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/last/mod.rs @@ -46,7 +46,7 @@ impl AggregateFnVTable for Last { } fn serialize(&self, _options: &Self::Options) -> VortexResult>> { - vortex_bail!(NotImplemented: "Last is not yet serializable"); + vortex_bail!("Last is not yet serializable"); } fn return_dtype(&self, _options: &Self::Options, input_dtype: &DType) -> Option { diff --git a/vortex-array/src/aggregate_fn/fns/mean/mod.rs b/vortex-array/src/aggregate_fn/fns/mean/mod.rs index b9b164aa8e1..b2dcf09fab4 100644 --- a/vortex-array/src/aggregate_fn/fns/mean/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/mean/mod.rs @@ -101,7 +101,7 @@ impl BinaryCombined for Mean { count: ArrayRef, ) -> VortexResult { if let DType::Decimal(..) = sum.dtype() { - vortex_bail!(NotImplemented: "grouped mean over decimals is not yet supported"); + vortex_bail!("grouped mean over decimals is not yet supported"); } let target = args.return_dtype.clone(); let sum = sum.cast(target.clone())?; @@ -151,7 +151,7 @@ impl BinaryCombined for Mean { } fn serialize(&self, _options: &CombinedOptions) -> VortexResult>> { - vortex_bail!(NotImplemented: "mean is not yet serializable"); + vortex_bail!("mean is not yet serializable"); } } diff --git a/vortex-array/src/aggregate_fn/fns/min_max/mod.rs b/vortex-array/src/aggregate_fn/fns/min_max/mod.rs index 35a5f03fddc..8aa0e559e84 100644 --- a/vortex-array/src/aggregate_fn/fns/min_max/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/min_max/mod.rs @@ -170,7 +170,7 @@ pub(crate) fn nan_scalar(dtype: &DType) -> Scalar { PType::F16 => Scalar::primitive(f16::NAN, Nullability::NonNullable), PType::F32 => Scalar::primitive(f32::NAN, Nullability::NonNullable), PType::F64 => Scalar::primitive(f64::NAN, Nullability::NonNullable), - _ => vortex_panic!(AssertionFailed: "NaN scalar requested for non-float dtype {dtype}"), + _ => vortex_panic!("NaN scalar requested for non-float dtype {dtype}"), } } @@ -482,14 +482,14 @@ impl AggregateFnVTable for MinMax { } Canonical::Null(_) => Ok(()), Canonical::Union(_) => { - vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement min_max for Union arrays") + vortex_bail!("TODO(connor)[Union]: implement min_max for Union arrays") } Canonical::Struct(_) | Canonical::List(_) | Canonical::Map(_) | Canonical::FixedSizeList(_) | Canonical::Variant(_) => { - vortex_bail!(InvalidArgument: "Unsupported canonical type for min_max: {}", batch.dtype()) + vortex_bail!("Unsupported canonical type for min_max: {}", batch.dtype()) } }, } diff --git a/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs b/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs index 1e937ab791e..ecc1e30afbb 100644 --- a/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs +++ b/vortex-array/src/aggregate_fn/fns/min_max/varbinview.rs @@ -154,7 +154,7 @@ fn make_scalar(dtype: &DType, value: &[u8]) -> Scalar { let value = unsafe { str::from_utf8_unchecked(value) }; Scalar::utf8(value, NonNullable) } - _ => vortex_panic!(MismatchedTypes: "cannot make Scalar from bytes with dtype {dtype}"), + _ => vortex_panic!("cannot make Scalar from bytes with dtype {dtype}"), } } diff --git a/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs b/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs index e3799331e0d..1251db1616b 100644 --- a/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/nan_count/mod.rs @@ -195,7 +195,7 @@ impl AggregateFnVTable for NanCount { Columnar::Canonical(c) => match c { Canonical::Primitive(p) => accumulate_primitive(partial, p, ctx), _ => vortex_bail!( - InvalidArgument: "Unsupported canonical type for nan_count: {}", + "Unsupported canonical type for nan_count: {}", batch.dtype() ), }, diff --git a/vortex-array/src/aggregate_fn/fns/sum/bool.rs b/vortex-array/src/aggregate_fn/fns/sum/bool.rs index 07c78c122b1..d6c42f31ba3 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/bool.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/bool.rs @@ -19,7 +19,7 @@ pub(crate) fn accumulate_bool( ctx: &mut ExecutionCtx, ) -> VortexResult { let SumState::Unsigned(acc) = inner else { - vortex_panic!(AssertionFailed: "expected unsigned sum state for bool input"); + vortex_panic!("expected unsigned sum state for bool input"); }; let mask = b.as_ref().validity()?.execute_mask(b.as_ref().len(), ctx)?; diff --git a/vortex-array/src/aggregate_fn/fns/sum/constant.rs b/vortex-array/src/aggregate_fn/fns/sum/constant.rs index 42278d1936c..f1b21c8b0b2 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/constant.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/constant.rs @@ -27,18 +27,20 @@ pub(crate) fn multiply_constant( let product = match scalar.dtype() { DType::Bool(_) => { - let val = scalar.as_bool().value().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected non-null bool scalar for sum"), - )?; + let val = scalar + .as_bool() + .value() + .ok_or_else(|| vortex_err!("Expected non-null bool scalar for sum"))?; if !val { return Ok(None); } Scalar::primitive(len as u64, Nullability::Nullable) } DType::Primitive(..) => { - let pvalue = scalar.as_primitive().pvalue().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected non-null primitive scalar for sum"), - )?; + let pvalue = scalar + .as_primitive() + .pvalue() + .ok_or_else(|| vortex_err!("Expected non-null primitive scalar for sum"))?; match return_dtype { DType::Primitive(PType::U64, _) => { let val = pvalue.cast::()?; @@ -59,18 +61,19 @@ pub(crate) fn multiply_constant( Scalar::primitive(val * len as f64, Nullability::Nullable) } _ => vortex_bail!( - AssertionFailed: "Unexpected return dtype for primitive sum: {}", + "Unexpected return dtype for primitive sum: {}", return_dtype ), } } DType::Decimal(..) => { - let val = scalar.as_decimal().decimal_value().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected non-null decimal scalar for sum"), - )?; + let val = scalar + .as_decimal() + .decimal_value() + .ok_or_else(|| vortex_err!("Expected non-null decimal scalar for sum"))?; let ret_decimal = *return_dtype .as_decimal_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected decimal return dtype"))?; + .ok_or_else(|| vortex_err!("Expected decimal return dtype"))?; // Multiply in i256, the widest storage type, because the operands can be narrower // than the return type. Then check the product against the return precision. @@ -84,7 +87,7 @@ pub(crate) fn multiply_constant( None => Scalar::null(return_dtype.as_nullable()), } } - _ => vortex_bail!(InvalidArgument: "Unsupported constant type for sum: {}", scalar.dtype()), + _ => vortex_bail!("Unsupported constant type for sum: {}", scalar.dtype()), }; Ok(Some(product)) diff --git a/vortex-array/src/aggregate_fn/fns/sum/decimal.rs b/vortex-array/src/aggregate_fn/fns/sum/decimal.rs index 6f67b22603d..799d83b7219 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/decimal.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/decimal.rs @@ -40,7 +40,7 @@ pub(crate) fn accumulate_decimal( }; let SumState::Decimal(value) = inner else { - vortex_panic!(AssertionFailed: "expected decimal sum state for decimal input"); + vortex_panic!("expected decimal sum state for decimal input"); }; let dtype = return_dtype .as_decimal_opt() diff --git a/vortex-array/src/aggregate_fn/fns/sum/mod.rs b/vortex-array/src/aggregate_fn/fns/sum/mod.rs index 1dbc4055aa3..98596975f93 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/mod.rs @@ -150,7 +150,7 @@ impl AggregateFnVTable for Sum { ) -> VortexResult { vortex_ensure!( scalar.dtype().eq_ignore_nullability(args.return_dtype), - MismatchedTypes: "Sum partial has dtype {}, expected {}", + "Sum partial has dtype {}, expected {}", scalar.dtype(), args.return_dtype ); @@ -284,7 +284,7 @@ impl AggregateFnVTable for Sum { Canonical::Bool(b) => accumulate_bool(&mut inner, b, ctx), Canonical::Decimal(d) => accumulate_decimal(&mut inner, args.return_dtype, d, ctx), _ => { - vortex_bail!(InvalidArgument: "Unsupported canonical type for sum: {}", batch.dtype()) + vortex_bail!("Unsupported canonical type for sum: {}", batch.dtype()) } }, Columnar::Constant(_) => unreachable!(), @@ -345,7 +345,7 @@ pub(crate) fn make_zero_state(return_dtype: &DType) -> SumState { PType::F16 | PType::F32 | PType::F64 => SumState::Float(0.0), }, DType::Decimal(decimal, _) => SumState::Decimal(DecimalValue::zero(decimal)), - _ => vortex_panic!(NotImplemented: "Unsupported sum type"), + _ => vortex_panic!("Unsupported sum type"), } } @@ -360,7 +360,7 @@ fn sum_state_from_scalar(scalar: &Scalar, return_dtype: &DType) -> VortexResult< } DType::Primitive(..) => SumState::Float(f64::try_from(scalar)?), DType::Decimal(..) => SumState::Decimal(DecimalValue::try_from(scalar)?), - _ => vortex_bail!(InvalidArgument: "Unsupported sum type {}", return_dtype), + _ => vortex_bail!("Unsupported sum type {}", return_dtype), }) } @@ -391,7 +391,7 @@ pub(crate) fn checked_add_sum_states( Some(_) | None => true, } } - _ => vortex_bail!(MismatchedTypes: "Mismatched sum partial states"), + _ => vortex_bail!("Mismatched sum partial states"), }) } diff --git a/vortex-array/src/aggregate_fn/fns/sum/primitive.rs b/vortex-array/src/aggregate_fn/fns/sum/primitive.rs index 5f582c8812e..a63edacf6b3 100644 --- a/vortex-array/src/aggregate_fn/fns/sum/primitive.rs +++ b/vortex-array/src/aggregate_fn/fns/sum/primitive.rs @@ -43,24 +43,24 @@ fn accumulate_primitive_all( match inner { SumState::Unsigned(acc) => match_each_native_ptype!(p.ptype(), unsigned: |T| { Ok(sum_unsigned_all(acc, p.as_slice::())) }, - signed: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with signed input") }, - floating: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with float input") } + signed: |_T| { vortex_panic!("unsigned sum state with signed input") }, + floating: |_T| { vortex_panic!("unsigned sum state with float input") } ), SumState::Signed(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!(AssertionFailed: "signed sum state with unsigned input") }, + unsigned: |_T| { vortex_panic!("signed sum state with unsigned input") }, signed: |T| { Ok(sum_signed_all(acc, p.as_slice::())) }, - floating: |_T| { vortex_panic!(AssertionFailed: "signed sum state with float input") } + floating: |_T| { vortex_panic!("signed sum state with float input") } ), SumState::Float(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!(AssertionFailed: "float sum state with unsigned input") }, - signed: |_T| { vortex_panic!(AssertionFailed: "float sum state with signed input") }, + unsigned: |_T| { vortex_panic!("float sum state with unsigned input") }, + signed: |_T| { vortex_panic!("float sum state with signed input") }, floating: |T| { sum_float_all(acc, p.as_slice::(), skip_nans); Ok(false) } ), SumState::Decimal(_) => { - vortex_panic!(AssertionFailed: "decimal sum state with primitive input") + vortex_panic!("decimal sum state with primitive input") } } } @@ -149,11 +149,11 @@ fn accumulate_primitive_valid( } Ok(false) }, - signed: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with signed input") }, - floating: |_T| { vortex_panic!(AssertionFailed: "unsigned sum state with float input") } + signed: |_T| { vortex_panic!("unsigned sum state with signed input") }, + floating: |_T| { vortex_panic!("unsigned sum state with float input") } ), SumState::Signed(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!(AssertionFailed: "signed sum state with unsigned input") }, + unsigned: |_T| { vortex_panic!("signed sum state with unsigned input") }, signed: |T| { let values = p.as_slice::(); for &(start, end) in slices { @@ -163,11 +163,11 @@ fn accumulate_primitive_valid( } Ok(false) }, - floating: |_T| { vortex_panic!(AssertionFailed: "signed sum state with float input") } + floating: |_T| { vortex_panic!("signed sum state with float input") } ), SumState::Float(acc) => match_each_native_ptype!(p.ptype(), - unsigned: |_T| { vortex_panic!(AssertionFailed: "float sum state with unsigned input") }, - signed: |_T| { vortex_panic!(AssertionFailed: "float sum state with signed input") }, + unsigned: |_T| { vortex_panic!("float sum state with unsigned input") }, + signed: |_T| { vortex_panic!("float sum state with signed input") }, floating: |T| { let values = p.as_slice::(); for &(start, end) in slices { @@ -177,7 +177,7 @@ fn accumulate_primitive_valid( } ), SumState::Decimal(_) => { - vortex_panic!(AssertionFailed: "decimal sum state with primitive input") + vortex_panic!("decimal sum state with primitive input") } } } diff --git a/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs b/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs index fc4f9e71fc0..b8f0e731597 100644 --- a/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/sum_v2/mod.rs @@ -95,7 +95,7 @@ impl SumV2 { sum.dtype(), DType::Primitive(PType::U64 | PType::I64 | PType::F64, _) ), - MismatchedTypes: "Expected a widened primitive sum, got {}", + "Expected a widened primitive sum, got {}", sum.dtype(), ); @@ -292,7 +292,7 @@ impl AggregateFnVTable for SumV2 { accumulate_decimal(&mut partial.sum, args.return_dtype, array, ctx) } _ => { - vortex_bail!(InvalidArgument: "Unsupported canonical type for sum_v2: {}", batch.dtype()) + vortex_bail!("Unsupported canonical type for sum_v2: {}", batch.dtype()) } }, Columnar::Constant(_) => unreachable!(), @@ -405,24 +405,24 @@ fn decode_partial_scalar<'a>( scalar: &'a Scalar, return_dtype: &DType, ) -> VortexResult<(&'a ScalarValue, bool, bool)> { - vortex_ensure!(!scalar.is_null(), InvalidArgument: "SumV2 partial must not be null"); + vortex_ensure!(!scalar.is_null(), "SumV2 partial must not be null"); let (DType::Struct(fields, _), Some(ScalarValue::Tuple(values))) = (scalar.dtype(), scalar.value()) else { - vortex_bail!(MismatchedTypes: "SumV2 partial must be a struct, got {}", scalar.dtype()); + vortex_bail!("SumV2 partial must be a struct, got {}", scalar.dtype()); }; let field_index = |name: &str| { fields .find(name) - .ok_or_else(|| vortex_err!(NotFound: "SumV2 partial is missing the {name} field")) + .ok_or_else(|| vortex_err!("SumV2 partial is missing the {name} field")) }; let bool_field = |name: &str| -> VortexResult { match &values[field_index(name)?] { Some(ScalarValue::Bool(value)) => Ok(*value), _ => { - vortex_bail!(MismatchedTypes: "SumV2 partial field {name} must be a non-null bool") + vortex_bail!("SumV2 partial field {name} must be a non-null bool") } } }; @@ -436,7 +436,7 @@ fn decode_partial_scalar<'a>( let sum = values[sum_index] .as_ref() - .ok_or_else(|| vortex_err!(InvalidArgument: "SumV2 partial sum must not be null"))?; + .ok_or_else(|| vortex_err!("SumV2 partial sum must not be null"))?; Ok(( sum, @@ -449,7 +449,7 @@ fn validate_sum_field_dtype(sum_dtype: &DType, return_dtype: &DType) -> VortexRe vortex_ensure!( sum_dtype.nullability() == Nullability::NonNullable && sum_dtype.eq_ignore_nullability(return_dtype), - MismatchedTypes: "SumV2 partial value has dtype {}, expected {}", + "SumV2 partial value has dtype {}, expected {}", sum_dtype, return_dtype.as_nonnullable(), ); @@ -461,9 +461,9 @@ fn checked_add_sum_state( return_dtype: &DType, other: &Scalar, ) -> VortexResult { - let other = other.value().ok_or_else( - || vortex_err!(InvalidArgument: "Can't extract present value from null scalar"), - )?; + let other = other + .value() + .ok_or_else(|| vortex_err!("Can't extract present value from null scalar"))?; checked_add_sum_value(state, return_dtype, other) } @@ -496,7 +496,7 @@ fn checked_add_sum_value( } } (_, other) => { - vortex_bail!(MismatchedTypes: "SumV2 cannot add {other} to a {return_dtype} sum") + vortex_bail!("SumV2 cannot add {other} to a {return_dtype} sum") } }) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs index 7f6f9724606..4c5c0a4df8d 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/bool.rs @@ -23,5 +23,5 @@ pub(super) fn bool_uncompressed_size_in_bytes( value_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs index 590326fac61..c04fa55f0ab 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/decimal.rs @@ -15,16 +15,14 @@ pub(super) fn decimal_uncompressed_size_in_bytes( ctx: &mut ExecutionCtx, ) -> VortexResult { let value_size = u64::try_from(array.len()) - .map_err(|e| vortex_err!(Overflow: "Failed to convert decimal array length to u64: {e}"))? + .map_err(|e| vortex_err!("Failed to convert decimal array length to u64: {e}"))? .checked_mul( u64::try_from( DecimalType::smallest_decimal_value_type(&array.decimal_dtype()).byte_width(), ) - .map_err( - |e| vortex_err!(Overflow: "Failed to convert decimal byte width to u64: {e}"), - )?, + .map_err(|e| vortex_err!("Failed to convert decimal byte width to u64: {e}"))?, ) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; let validity_size = validity_uncompressed_size_in_bytes( array .as_ref() @@ -34,5 +32,5 @@ pub(super) fn decimal_uncompressed_size_in_bytes( value_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs index 947f42fb9d1..0d36b3b6208 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/fixed_size_list.rs @@ -26,5 +26,5 @@ pub(super) fn fixed_size_list_uncompressed_size_in_bytes( elements_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs index 9a30dfc4aa0..8abf0586396 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/list_view.rs @@ -40,18 +40,18 @@ pub(super) fn list_view_uncompressed_size_in_bytes( }; let view_buffer_size = u64::try_from(array.len()) - .map_err(|e| vortex_err!(Overflow: "Failed to convert list array length to u64: {e}"))? + .map_err(|e| vortex_err!("Failed to convert list array length to u64: {e}"))? .checked_mul(8) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; // ListView stores both offsets and sizes as u64 view buffers. size = size .checked_add(view_buffer_size) .and_then(|size| size.checked_add(view_buffer_size)) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; size = size .checked_add(validity_uncompressed_size_in_bytes(validity)?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; Ok(size) } @@ -135,7 +135,7 @@ fn referenced_elements_size( values_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } fn for_each_valid_list( diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs index 50cd013d347..eca323d70a1 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/mod.rs @@ -142,7 +142,7 @@ pub fn uncompressed_size_in_bytes( let size = uncompressed_size_in_bytes_u64(array, opts, ctx)?; usize::try_from(size) - .map_err(|e| vortex_err!(Overflow: "Failed to convert uncompressed size to usize: {e}")) + .map_err(|e| vortex_err!("Failed to convert uncompressed size to usize: {e}")) } fn uncompressed_size_in_bytes_u64( @@ -260,7 +260,7 @@ impl AggregateFnVTable for UncompressedSizeInBytes { ) -> VortexResult { first .checked_add(second) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } fn to_scalar( @@ -298,7 +298,7 @@ impl AggregateFnVTable for UncompressedSizeInBytes { }; *partial = partial .checked_add(size) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; Ok(()) } @@ -344,7 +344,7 @@ pub(crate) fn canonical_uncompressed_size_in_bytes( Canonical::Union(array) => union_uncompressed_size_in_bytes(array, opts, ctx), Canonical::Extension(array) => extension_uncompressed_size_in_bytes(array, opts, ctx), Canonical::Variant(_) => { - vortex_bail!(InvalidArgument: "UncompressedSizeInBytes is not supported for Variant arrays") + vortex_bail!("UncompressedSizeInBytes is not supported for Variant arrays") } } } @@ -383,13 +383,13 @@ pub(crate) fn constant_uncompressed_size_in_bytes( return canonical_uncompressed_size_in_bytes(&canonical, opts, ctx); } DType::Variant(_) => { - vortex_bail!(InvalidArgument: "UncompressedSizeInBytes is not supported for Variant arrays") + vortex_bail!("UncompressedSizeInBytes is not supported for Variant arrays") } }; value_size .checked_add(constant_validity_size(array, ctx)?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } fn constant_varbinview_value_size(len: usize, scalar_len: Option) -> VortexResult { @@ -397,15 +397,13 @@ fn constant_varbinview_value_size(len: usize, scalar_len: Option) -> Vort // Only a value too long to inline adds a data buffer, matching `constant_canonicalize`. let data_size = match scalar_len { Some(scalar_len) if scalar_len > BinaryView::MAX_INLINED_SIZE => u64::try_from(scalar_len) - .map_err( - |e| vortex_err!(Overflow: "Failed to convert data buffer length to u64: {e}"), - )?, + .map_err(|e| vortex_err!("Failed to convert data buffer length to u64: {e}"))?, _ => 0, }; views_size .checked_add(data_size) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } fn constant_validity_size( @@ -418,12 +416,12 @@ fn constant_validity_size( fn checked_len_mul(len: usize, width: usize, name: &str) -> VortexResult { let len = u64::try_from(len) - .map_err(|e| vortex_err!(Overflow: "Failed to convert {name} length to u64: {e}"))?; + .map_err(|e| vortex_err!("Failed to convert {name} length to u64: {e}"))?; let width = u64::try_from(width) - .map_err(|e| vortex_err!(Overflow: "Failed to convert {name} byte width to u64: {e}"))?; + .map_err(|e| vortex_err!("Failed to convert {name} byte width to u64: {e}"))?; len.checked_mul(width) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } fn supports_uncompressed_size_in_bytes(dtype: &DType) -> bool { @@ -464,7 +462,7 @@ pub(crate) fn validity_uncompressed_size_in_bytes(validity: Mask) -> VortexResul pub(crate) fn packed_bit_buffer_size_in_bytes(len: usize) -> VortexResult { u64::try_from(len.div_ceil(8)) - .map_err(|e| vortex_err!(Overflow: "Failed to convert bit buffer length to u64: {e}")) + .map_err(|e| vortex_err!("Failed to convert bit buffer length to u64: {e}")) } #[cfg(test)] @@ -562,9 +560,7 @@ mod tests { acc.finish()? .as_primitive() .typed_value::() - .ok_or_else( - || vortex_err!(AssertionFailed: "uncompressed size result should not be null"), - ) + .ok_or_else(|| vortex_err!("uncompressed size result should not be null")) } /// A view array whose rows point into one shared data buffer, like Arrow's Parquet reader diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs index 079f843f011..8ca149e791a 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/primitive.rs @@ -14,11 +14,12 @@ pub(super) fn primitive_uncompressed_size_in_bytes( ctx: &mut ExecutionCtx, ) -> VortexResult { let value_size = u64::try_from(array.len()) - .map_err(|e| vortex_err!(Overflow: "Failed to convert primitive array length to u64: {e}"))? - .checked_mul(u64::try_from(array.ptype().byte_width()).map_err( - |e| vortex_err!(Overflow: "Failed to convert primitive byte width to u64: {e}"), - )?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .map_err(|e| vortex_err!("Failed to convert primitive array length to u64: {e}"))? + .checked_mul( + u64::try_from(array.ptype().byte_width()) + .map_err(|e| vortex_err!("Failed to convert primitive byte width to u64: {e}"))?, + ) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; let validity_size = validity_uncompressed_size_in_bytes( array .as_ref() @@ -28,5 +29,5 @@ pub(super) fn primitive_uncompressed_size_in_bytes( value_size .checked_add(validity_size) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs index 794bbce480c..069a2df76bb 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/struct_.rs @@ -21,7 +21,7 @@ pub(super) fn struct_uncompressed_size_in_bytes( for field in array.iter_unmasked_fields() { size = size .checked_add(uncompressed_size_in_bytes_u64(field, opts, ctx)?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; } size = size @@ -31,7 +31,7 @@ pub(super) fn struct_uncompressed_size_in_bytes( .validity()? .execute_mask(array.as_ref().len(), ctx)?, )?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; Ok(size) } diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs index 2aa0c71479f..760a874d4a7 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/union.rs @@ -21,7 +21,7 @@ pub(super) fn union_uncompressed_size_in_bytes( for child in array.iter_children() { size = size .checked_add(uncompressed_size_in_bytes_u64(child, opts, ctx)?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; } Ok(size) diff --git a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs index 41fea5e2c63..55cabfff1a4 100644 --- a/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs +++ b/vortex-array/src/aggregate_fn/fns/uncompressed_size_in_bytes/varbinview.rs @@ -19,13 +19,12 @@ pub(super) fn varbinview_uncompressed_size_in_bytes( ctx: &mut ExecutionCtx, ) -> VortexResult { let views_size = u64::try_from(array.len()) - .map_err( - |e| vortex_err!(Overflow: "Failed to convert varbinview array length to u64: {e}"), - )? - .checked_mul(u64::try_from(size_of::()).map_err( - |e| vortex_err!(Overflow: "Failed to convert binary view width to u64: {e}"), - )?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .map_err(|e| vortex_err!("Failed to convert varbinview array length to u64: {e}"))? + .checked_mul( + u64::try_from(size_of::()) + .map_err(|e| vortex_err!("Failed to convert binary view width to u64: {e}"))?, + ) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; let validity = array .as_ref() @@ -41,7 +40,7 @@ pub(super) fn varbinview_uncompressed_size_in_bytes( views_size .checked_add(data_size) .and_then(|size| size.checked_add(validity_uncompressed_size_in_bytes(validity).ok()?)) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64")) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64")) } /// Every byte of every data buffer, referenced or not. @@ -49,10 +48,11 @@ fn held_data_size(array: &VarBinViewArray) -> VortexResult { let mut size = 0u64; for buffer in array.data_buffers().iter() { size = size - .checked_add(u64::try_from(buffer.len()).map_err( - |e| vortex_err!(Overflow: "Failed to convert data buffer length to u64: {e}"), - )?) - .ok_or_else(|| vortex_err!(Overflow: "uncompressed size in bytes overflowed u64"))?; + .checked_add( + u64::try_from(buffer.len()) + .map_err(|e| vortex_err!("Failed to convert data buffer length to u64: {e}"))?, + ) + .ok_or_else(|| vortex_err!("uncompressed size in bytes overflowed u64"))?; } Ok(size) } diff --git a/vortex-array/src/aggregate_fn/foreign.rs b/vortex-array/src/aggregate_fn/foreign.rs index bc953fa0a60..7e32d9e0b2c 100644 --- a/vortex-array/src/aggregate_fn/foreign.rs +++ b/vortex-array/src/aggregate_fn/foreign.rs @@ -82,7 +82,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { &self, _args: AggregateArgs<'_, Self::Options>, ) -> VortexResult { - vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) } fn partial_from_scalar( @@ -90,7 +90,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _scalar: &Scalar, ) -> VortexResult { - vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) } fn merge_partials( @@ -99,7 +99,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _first: Self::Partial, _second: Self::Partial, ) -> VortexResult { - vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) } fn to_scalar( @@ -107,7 +107,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) } fn is_saturated( @@ -125,7 +125,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _batch: &Columnar, _ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) } fn finalize( @@ -133,7 +133,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _states: ArrayRef, ) -> VortexResult { - vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) } fn finalize_scalar( @@ -141,7 +141,7 @@ impl AggregateFnVTable for ForeignAggregateFnVTable { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_bail!(NotFound: "Cannot execute unknown aggregate function '{}'", self.id) + vortex_bail!("Cannot execute unknown aggregate function '{}'", self.id) } } diff --git a/vortex-array/src/aggregate_fn/proto.rs b/vortex-array/src/aggregate_fn/proto.rs index c954ea80046..684d582ce21 100644 --- a/vortex-array/src/aggregate_fn/proto.rs +++ b/vortex-array/src/aggregate_fn/proto.rs @@ -17,9 +17,10 @@ impl AggregateFnRef { /// /// Note: the serialization format is not stable and may change between versions. pub fn serialize_proto(&self) -> VortexResult { - let metadata = self.options().serialize()?.ok_or_else( - || vortex_err!(Serde: "Aggregate function '{}' is not serializable", self.id()), - )?; + let metadata = self + .options() + .serialize()? + .ok_or_else(|| vortex_err!("Aggregate function '{}' is not serializable", self.id()))?; Ok(pb::AggregateFn { id: self.id().to_string(), @@ -41,12 +42,12 @@ impl AggregateFnRef { } else if session.allows_unknown() { new_foreign_aggregate_fn(agg_fn_id, proto.metadata().to_vec()) } else { - return Err(vortex_err!(NotFound: "unknown aggregate function id: {}", proto.id)); + return Err(vortex_err!("unknown aggregate function id: {}", proto.id)); }; if agg_fn.id() != agg_fn_id { vortex_bail!( - MismatchedTypes: "Aggregate function ID mismatch: expected {}, got {}", + "Aggregate function ID mismatch: expected {}, got {}", agg_fn_id, agg_fn.id() ); @@ -151,7 +152,7 @@ mod tests { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_panic!(NotImplemented: "TestAgg is for serde tests only"); + vortex_panic!("TestAgg is for serde tests only"); } fn is_saturated( @@ -185,7 +186,7 @@ mod tests { _args: AggregateArgs<'_, Self::Options>, _partial: &Self::Partial, ) -> VortexResult { - vortex_panic!(NotImplemented: "TestAgg is for serde tests only"); + vortex_panic!("TestAgg is for serde tests only"); } } diff --git a/vortex-array/src/aggregate_fn/storage_pushdown.rs b/vortex-array/src/aggregate_fn/storage_pushdown.rs index 84ad002851b..2e8d5123693 100644 --- a/vortex-array/src/aggregate_fn/storage_pushdown.rs +++ b/vortex-array/src/aggregate_fn/storage_pushdown.rs @@ -144,7 +144,7 @@ impl ExtensionStoragePushdown { ) -> VortexResult> { let dtype = self.storage_dtype(args.dtype).ok_or_else(|| { vortex_err!( - MismatchedTypes: "Aggregate function {} expects extension type {}, got {}", + "Aggregate function {} expects extension type {}, got {}", self.id, self.ext.id(), args.dtype @@ -288,7 +288,7 @@ impl AggregateFnVTable for ExtensionStorageP } Columnar::Canonical(_) => { vortex_bail!( - MismatchedTypes: "Aggregate function {} expects an extension array, got {}", + "Aggregate function {} expects an extension array, got {}", self.id, batch.dtype() ) diff --git a/vortex-array/src/aggregate_fn/vtable.rs b/vortex-array/src/aggregate_fn/vtable.rs index 3cb40bd243d..ba236ab1d5f 100644 --- a/vortex-array/src/aggregate_fn/vtable.rs +++ b/vortex-array/src/aggregate_fn/vtable.rs @@ -59,14 +59,14 @@ impl AggregateDTypes { ) -> VortexResult { let return_dtype = vtable.return_dtype(options, &dtype).ok_or_else(|| { vortex_err!( - InvalidArgument: "Aggregate function {} cannot be applied to dtype {}", + "Aggregate function {} cannot be applied to dtype {}", vtable.id(), dtype ) })?; let partial_dtype = vtable.partial_dtype(options, &dtype).ok_or_else(|| { vortex_err!( - InvalidArgument: "Aggregate function {} cannot be applied to dtype {}", + "Aggregate function {} cannot be applied to dtype {}", vtable.id(), dtype ) @@ -142,7 +142,7 @@ pub trait AggregateFnVTable: 'static + Sized + Clone + Send + Sync { _metadata: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!(Serde: "Aggregate function {} is not deserializable", self.id()); + vortex_bail!("Aggregate function {} is not deserializable", self.id()); } /// Return whether this stored aggregate can satisfy `requested`. diff --git a/vortex-array/src/array/erased.rs b/vortex-array/src/array/erased.rs index 14389400ada..f630d42a4f8 100644 --- a/vortex-array/src/array/erased.rs +++ b/vortex-array/src/array/erased.rs @@ -219,10 +219,10 @@ impl ArrayRef { return Ok(self.clone()); } - vortex_ensure!(start <= len, OutOfBounds: "OutOfBounds: start {start} > length {}", len); - vortex_ensure!(stop <= len, OutOfBounds: "OutOfBounds: stop {stop} > length {}", len); + vortex_ensure!(start <= len, "OutOfBounds: start {start} > length {}", len); + vortex_ensure!(stop <= len, "OutOfBounds: stop {stop} > length {}", len); - vortex_ensure!(start <= stop, InvalidArgument: "start ({start}) must be <= stop ({stop})"); + vortex_ensure!(start <= stop, "start ({start}) must be <= stop ({stop})"); if start == stop { return Ok(Canonical::empty(self.dtype()).into_array()); @@ -368,10 +368,10 @@ impl ArrayRef { array_sum .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(AssertionFailed: "sum of validity array is null"))? + .ok_or_else(|| vortex_err!("sum of validity array is null"))? } }; - vortex_ensure!(count <= len, InvalidArgument: "Valid count exceeds array length"); + vortex_ensure!(count <= len, "Valid count exceeds array length"); self.statistics() .set(Stat::NullCount, Precision::exact(len - count)); @@ -432,9 +432,8 @@ impl ArrayRef { /// /// Panics if the array is not of the given type. pub fn downcast(self) -> Array { - Self::try_downcast(self).unwrap_or_else( - |_| vortex_panic!(MismatchedTypes: "Failed to downcast to {}", type_name::()), - ) + Self::try_downcast(self) + .unwrap_or_else(|_| vortex_panic!("Failed to downcast to {}", type_name::())) } /// Returns a reference to the typed `ArrayData` if this array matches the given vtable type. @@ -499,7 +498,7 @@ impl ArrayRef { let nslots = slots.len(); vortex_ensure!( slot_idx < nslots, - OutOfBounds: "slot index {} out of bounds for array with {} slots", + "slot index {} out of bounds for array with {} slots", slot_idx, nslots ); @@ -509,13 +508,13 @@ impl ArrayRef { vortex_ensure_eq!( existing.dtype(), replacement.dtype(), - AssertionFailed: "slot {} dtype changed during physical rewrite", + "slot {} dtype changed during physical rewrite", slot_idx ); vortex_ensure_eq!( existing.len(), replacement.len(), - AssertionFailed: "slot {} len changed during physical rewrite", + "slot {} len changed during physical rewrite", slot_idx ); slots[slot_idx] = Some(replacement); @@ -598,26 +597,26 @@ impl ArrayRef { vortex_ensure_eq!( old_slots.len(), slots.len(), - AssertionFailed: "slot count changed during physical rewrite" + "slot count changed during physical rewrite" ); for (idx, (old_slot, new_slot)) in old_slots.iter().zip(slots.iter()).enumerate() { vortex_ensure_eq!( old_slot.is_some(), new_slot.is_some(), - AssertionFailed: "slot {} presence changed during physical rewrite", + "slot {} presence changed during physical rewrite", idx ); if let (Some(old_slot), Some(new_slot)) = (old_slot.as_ref(), new_slot.as_ref()) { vortex_ensure_eq!( old_slot.dtype(), new_slot.dtype(), - AssertionFailed: "slot {} dtype changed during physical rewrite", + "slot {} dtype changed during physical rewrite", idx ); vortex_ensure_eq!( old_slot.len(), new_slot.len(), - AssertionFailed: "slot {} len changed during physical rewrite", + "slot {} len changed during physical rewrite", idx ); } @@ -646,7 +645,7 @@ impl ArrayRef { vortex_ensure_eq!( nbuffers, buffers.len(), - AssertionFailed: "buffer count changed during physical rewrite" + "buffer count changed during physical rewrite" ); for (idx, (old_buffer, new_buffer)) in self .buffer_handles() @@ -657,7 +656,7 @@ impl ArrayRef { vortex_ensure_eq!( old_buffer.len(), new_buffer.len(), - AssertionFailed: "buffer {} length changed during physical rewrite", + "buffer {} length changed during physical rewrite", idx ); } diff --git a/vortex-array/src/array/foreign.rs b/vortex-array/src/array/foreign.rs index a153a5d2ea4..57a0d74ba45 100644 --- a/vortex-array/src/array/foreign.rs +++ b/vortex-array/src/array/foreign.rs @@ -169,7 +169,7 @@ impl VTable for ForeignArray { fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { vortex_bail!( - NotFound: "Cannot execute unknown array encoding '{}'", + "Cannot execute unknown array encoding '{}'", array.encoding_id() ) } diff --git a/vortex-array/src/array/mod.rs b/vortex-array/src/array/mod.rs index 6229f4501f8..fae796e1714 100644 --- a/vortex-array/src/array/mod.rs +++ b/vortex-array/src/array/mod.rs @@ -306,10 +306,10 @@ impl DynArrayData for ArrayData { let view = unsafe { ArrayView::new_unchecked(this, &self.data) }; let validity = >::validity(view)?; if let Validity::Array(array) = &validity { - vortex_ensure_eq!(array.len(), this.len(), InvalidArgument: "Validity array length mismatch"); + vortex_ensure_eq!(array.len(), this.len(), "Validity array length mismatch"); vortex_ensure!( matches!(array.dtype(), DType::Bool(Nullability::NonNullable)), - MismatchedTypes: "Validity array is not non-nullable boolean: {}", + "Validity array is not non-nullable boolean: {}", this.encoding_id(), ); } @@ -327,7 +327,7 @@ impl DynArrayData for ArrayData { ) -> VortexResult<()> { if builder.dtype() != this.dtype() { vortex_panic!( - MismatchedTypes: "Builder dtype mismatch: expected {}, got {}", + "Builder dtype mismatch: expected {}, got {}", this.dtype(), builder.dtype(), ); @@ -452,7 +452,7 @@ impl DynArrayData for ArrayData { vortex_ensure_eq!( reduced.len(), this.len(), - AssertionFailed: "Reduced array length mismatch from {} to {}", + "Reduced array length mismatch from {} to {}", this.encoding_id(), reduced.encoding_id() ); @@ -461,7 +461,7 @@ impl DynArrayData for ArrayData { reduced.dtype() == this.dtype() || (reduced.dtype().eq_ignore_nullability(this.dtype()) && !reduced.dtype().is_nullable()), - AssertionFailed: "Reduced array dtype mismatch from {} ({}) to {} ({})", + "Reduced array dtype mismatch from {} ({}) to {} ({})", this.encoding_id(), this.dtype(), reduced.encoding_id(), @@ -484,14 +484,14 @@ impl DynArrayData for ArrayData { vortex_ensure_eq!( reduced.len(), parent.len(), - AssertionFailed: "Reduced array length mismatch from {} to {}", + "Reduced array length mismatch from {} to {}", parent.encoding_id(), reduced.encoding_id() ); vortex_ensure_eq!( reduced.dtype(), parent.dtype(), - AssertionFailed: "Reduced array dtype mismatch from {} to {}", + "Reduced array dtype mismatch from {} to {}", parent.encoding_id(), reduced.encoding_id() ); @@ -510,13 +510,13 @@ impl DynArrayData for ArrayData { vortex_ensure_eq!( result.array().len(), len, - AssertionFailed: "Result length mismatch for {:?}", + "Result length mismatch for {:?}", self.vtable ); vortex_ensure_eq!( result.array().dtype(), &dtype, - AssertionFailed: "Executed canonical dtype mismatch for {:?}", + "Executed canonical dtype mismatch for {:?}", self.vtable ); } @@ -533,7 +533,7 @@ impl DynArrayData for ArrayData { ctx: &mut ExecutionCtx, ) -> VortexResult { let typed = Array::::try_from_array_ref(this) - .map_err(|_| vortex_err!(AssertionFailed: "Failed to downcast array for execute")) + .map_err(|_| vortex_err!("Failed to downcast array for execute")) .vortex_expect("Failed to downcast array for execute"); V::execute(typed, ctx) } diff --git a/vortex-array/src/array/plugin.rs b/vortex-array/src/array/plugin.rs index cd937d8d4a1..979d644228c 100644 --- a/vortex-array/src/array/plugin.rs +++ b/vortex-array/src/array/plugin.rs @@ -175,7 +175,7 @@ impl ArrayPlugin for V { vortex_ensure_eq!( self.id(), array.encoding_id(), - Serde: "array plugin cannot serialize an in-memory array of another encoding", + "array plugin cannot serialize an in-memory array of another encoding", ); Ok(V::serialize(array.as_::(), session)? .map(|metadata| ArraySerialization::from_array(self.id(), array, metadata))) @@ -189,7 +189,7 @@ impl ArrayPlugin for V { vortex_ensure_eq!( self.id(), parts.serialized_id, - Serde: "array plugin does not recognize the serialized ID", + "array plugin does not recognize the serialized ID", ); Ok(Array::::try_from_parts(V::deserialize( self, diff --git a/vortex-array/src/array/probe/array.rs b/vortex-array/src/array/probe/array.rs index 9356073965d..99661ccf584 100644 --- a/vortex-array/src/array/probe/array.rs +++ b/vortex-array/src/array/probe/array.rs @@ -138,7 +138,7 @@ pub(super) fn check_bounds(array: &ArrayRef, index: usize) -> VortexResult<()> { #[cold] #[inline(never)] fn out_of_bounds(index: usize, len: usize) -> VortexError { - vortex_err!(OutOfBounds: "index {index} out of bounds from 0 to {len}") + vortex_err!("index {index} out of bounds from 0 to {len}") } /// The encoding state type of `V`'s operations vtable. @@ -276,7 +276,7 @@ pub(super) fn child_of(parent: &ArrayRef, slot: usize) -> VortexResult() - .ok_or_else(|| vortex_err!(AssertionFailed: "expected a primitive"))?; + .ok_or_else(|| vortex_err!("expected a primitive"))?; let mut once = ProbeState::once(typed); assert!(once.is_valid(0, &mut ctx)?); @@ -407,7 +407,7 @@ mod tests { let all_valid = PrimitiveArray::from_option_iter([Some(1i32)]).into_array(); let typed = all_valid .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "expected a primitive"))?; + .ok_or_else(|| vortex_err!("expected a primitive"))?; assert!(ProbeState::once(typed).is_valid(0, &mut ctx)?); Ok(()) } @@ -418,16 +418,14 @@ mod tests { let array = struct_of_two_fields()?; let typed = array .as_opt::() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected a struct"))?; + .ok_or_else(|| vortex_err!("expected a struct"))?; let mut state = ProbeState::once(typed); assert!(state.slot(5).is_err()); // Slot 0 is the struct's absent validity. assert!(state.slot(0)?.is_none()); { - let mut field = state - .slot(2)? - .ok_or_else(|| vortex_err!(NotFound: "missing field"))?; + let mut field = state.slot(2)?.ok_or_else(|| vortex_err!("missing field"))?; assert!(matches!(field, ArrayProbe::Once(_))); assert_eq!(field.array().len(), 2); assert_eq!(field.execute_scalar(1, &mut ctx)?, Scalar::from(4i64)); @@ -438,7 +436,7 @@ mod tests { assert!(retained.is_none()); let mut field = children .slot(1)? - .ok_or_else(|| vortex_err!(NotFound: "missing field"))?; + .ok_or_else(|| vortex_err!("missing field"))?; assert_eq!(field.execute_scalar(1, &mut ctx)?, Scalar::from(2i32)); Ok(()) } diff --git a/vortex-array/src/array/probe/repeated.rs b/vortex-array/src/array/probe/repeated.rs index 811604af0d8..da0669f80a9 100644 --- a/vortex-array/src/array/probe/repeated.rs +++ b/vortex-array/src/array/probe/repeated.rs @@ -122,7 +122,7 @@ pub(super) fn is_valid_scalar(scalar: Scalar, index: usize) -> VortexResult( ) -> VortexResult<&mut RepeatedState> { slot.get_or_insert_with(|| Box::new(RepeatedState::::default())) .downcast_mut::>() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Probe state type mismatch")) + .ok_or_else(|| vortex_err!("Probe state type mismatch")) } /// What a [`RepeatedArrayProbe`] keeps for its encoding between reads. @@ -270,7 +270,7 @@ mod tests { let Some(ResolvedValidity::Array(validity)) = &repeated_state::<()>(&mut probe.state)?.validity else { - return Err(vortex_err!(AssertionFailed: "validity slot should hold a probe")); + return Err(vortex_err!("validity slot should hold a probe")); }; assert!(validity.state.is_some()); assert!(probe.execute_scalar(1, &mut ctx)?.is_null()); @@ -298,16 +298,14 @@ mod tests { let array = struct_of_two_fields()?; let typed = array .as_opt::() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected a struct"))?; + .ok_or_else(|| vortex_err!("expected a struct"))?; let mut repeated = RepeatedState::<()>::default(); { let mut state = ProbeState::repeated(typed, &mut repeated); assert!(state.slot(5).is_err()); assert!(state.slot(0)?.is_none()); assert!(state.retained().is_some()); - let mut field = state - .slot(2)? - .ok_or_else(|| vortex_err!(NotFound: "missing field"))?; + let mut field = state.slot(2)?.ok_or_else(|| vortex_err!("missing field"))?; assert!(matches!(field, ArrayProbe::Repeated(_))); assert_eq!(field.execute_scalar(1, &mut ctx)?, Scalar::from(4i64)); assert_eq!(field.execute_scalar(0, &mut ctx)?, Scalar::from(3i64)); @@ -317,7 +315,7 @@ mod tests { assert!(repeated.slots[1].is_none()); let child = repeated.slots[2] .as_ref() - .ok_or_else(|| vortex_err!(NotFound: "missing child probe"))?; + .ok_or_else(|| vortex_err!("missing child probe"))?; assert_eq!(child.array().len(), 2); Ok(()) } diff --git a/vortex-array/src/array/vtable/mod.rs b/vortex-array/src/array/vtable/mod.rs index 89f9c4f6137..e4a23ebe16c 100644 --- a/vortex-array/src/array/vtable/mod.rs +++ b/vortex-array/src/array/vtable/mod.rs @@ -243,7 +243,7 @@ pub fn with_empty_buffers( ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - InvalidArgument: "Array {} expects 0 buffers, got {}", + "Array {} expects 0 buffers, got {}", array.encoding_id(), buffers.len() ); @@ -263,7 +263,7 @@ pub fn unsupported_buffer_replacement( _buffers: &[BufferHandle], ) -> VortexResult> { vortex_bail!( - InvalidArgument: "Array {} does not support in-memory buffer replacement", + "Array {} does not support in-memory buffer replacement", array.encoding_id() ) } @@ -331,7 +331,7 @@ pub fn patches_child(patches: &Patches, idx: usize) -> ArrayRef { .as_ref() .vortex_expect("patch_chunk_offsets child out of bounds") .clone(), - _ => vortex_panic!(OutOfBounds: "patches child index {idx} out of bounds"), + _ => vortex_panic!("patches child index {idx} out of bounds"), } } @@ -342,6 +342,6 @@ pub fn patches_child_name(idx: usize) -> &'static str { 0 => "patch_indices", 1 => "patch_values", 2 => "patch_chunk_offsets", - _ => vortex_panic!(OutOfBounds: "patches child name index {idx} out of bounds"), + _ => vortex_panic!("patches child name index {idx} out of bounds"), } } diff --git a/vortex-array/src/array/vtable/operations.rs b/vortex-array/src/array/vtable/operations.rs index c8ee269a4f0..0ffbeef953a 100644 --- a/vortex-array/src/array/vtable/operations.rs +++ b/vortex-array/src/array/vtable/operations.rs @@ -85,7 +85,7 @@ impl OperationsVTable for NotSupported { _ctx: &mut ExecutionCtx, ) -> VortexResult { vortex_bail!( - InvalidArgument: "Legacy scalar_at operation is not supported for {} arrays", + "Legacy scalar_at operation is not supported for {} arrays", array.encoding_id() ) } diff --git a/vortex-array/src/arrays/bool/array.rs b/vortex-array/src/arrays/bool/array.rs index ad9e270cf8e..d72a4b439e5 100644 --- a/vortex-array/src/arrays/bool/array.rs +++ b/vortex-array/src/arrays/bool/array.rs @@ -268,18 +268,18 @@ impl BoolData { len: usize, validity: Validity, ) -> VortexResult { - vortex_ensure!(offset < 8, InvalidArgument: "BitBuffer offset must be <8, got {}", offset); + vortex_ensure!(offset < 8, "BitBuffer offset must be <8, got {}", offset); if let Some(validity_len) = validity.maybe_len() { vortex_ensure_eq!( validity_len, len, - InvalidArgument: "BoolArray validity length does not match array length", + "BoolArray validity length does not match array length", ); } vortex_ensure!( bits.len() * 8 >= (len + offset), - InvalidArgument: "provided BufferHandle with offset {offset} len {len} had size {} bits", + "provided BufferHandle with offset {offset} len {len} had size {} bits", bits.len() * 8, ); @@ -305,7 +305,7 @@ impl BoolData { pub(super) fn validate(bits: &BitBuffer, validity: &Validity) -> VortexResult<()> { vortex_ensure!( bits.offset() < 8, - InvalidArgument: "BitBuffer offset must be <8, got {}", + "BitBuffer offset must be <8, got {}", bits.offset() ); @@ -313,7 +313,7 @@ impl BoolData { vortex_ensure_eq!( validity_len, bits.len(), - InvalidArgument: "BoolArray validity length does not match array length", + "BoolArray validity length does not match array length", ); } diff --git a/vortex-array/src/arrays/bool/compute/boolean.rs b/vortex-array/src/arrays/bool/compute/boolean.rs index 427442598e3..28d1bbb7f52 100644 --- a/vortex-array/src/arrays/bool/compute/boolean.rs +++ b/vortex-array/src/arrays/bool/compute/boolean.rs @@ -28,7 +28,7 @@ impl BooleanKernel for Bool { let rhs = rhs .scalar() .as_bool_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))?; + .ok_or_else(|| vortex_err!("expected boolean scalar"))?; return kleene_boolean_buffer_scalar( lhs.to_bit_buffer(), lhs.validity()?, diff --git a/vortex-array/src/arrays/bool/compute/fill_null.rs b/vortex-array/src/arrays/bool/compute/fill_null.rs index dddc5119493..94966f2e829 100644 --- a/vortex-array/src/arrays/bool/compute/fill_null.rs +++ b/vortex-array/src/arrays/bool/compute/fill_null.rs @@ -24,7 +24,7 @@ impl FillNullKernel for Bool { let fill = fill_value .as_bool() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "Fill value must be non null"))?; + .ok_or_else(|| vortex_err!("Fill value must be non null"))?; Ok(Some(match array.validity()? { Validity::Array(v) => { diff --git a/vortex-array/src/arrays/bool/compute/mask.rs b/vortex-array/src/arrays/bool/compute/mask.rs index a44220a89b6..818dbaebca5 100644 --- a/vortex-array/src/arrays/bool/compute/mask.rs +++ b/vortex-array/src/arrays/bool/compute/mask.rs @@ -75,14 +75,14 @@ mod tests { } fn copy_to_host_sync(&self, _alignment: Alignment) -> VortexResult { - vortex_bail!(InvalidArgument: "mask reduction must not copy device values") + vortex_bail!("mask reduction must not copy device values") } fn copy_to_host( &self, _alignment: Alignment, ) -> VortexResult>> { - vortex_bail!(InvalidArgument: "mask reduction must not copy device values") + vortex_bail!("mask reduction must not copy device values") } fn slice(&self, _range: Range) -> Arc { diff --git a/vortex-array/src/arrays/bool/compute/take.rs b/vortex-array/src/arrays/bool/compute/take.rs index 4bccdf9b9a9..a19b994bf5c 100644 --- a/vortex-array/src/arrays/bool/compute/take.rs +++ b/vortex-array/src/arrays/bool/compute/take.rs @@ -132,13 +132,14 @@ fn take_bit_slices_constant_length( where S: UnsignedPType, { - let computed_len = starts.len().checked_mul(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + let computed_len = starts + .len() + .checked_mul(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; vortex_ensure_eq!( computed_len, output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); let mut values = BitBufferMut::with_capacity(output_len); @@ -170,7 +171,7 @@ where vortex_ensure_eq!( values.len(), output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); Ok(values.freeze()) } diff --git a/vortex-array/src/arrays/bool/test_harness.rs b/vortex-array/src/arrays/bool/test_harness.rs index fa4a9cf70ec..66bfd26771c 100644 --- a/vortex-array/src/arrays/bool/test_harness.rs +++ b/vortex-array/src/arrays/bool/test_harness.rs @@ -31,7 +31,7 @@ impl BoolArray { .zip(self.to_bit_buffer().iter()) .map(|(valid, value)| { if !valid { - vortex_panic!(AssertionFailed: "trying to get bool values from an array with null elements") + vortex_panic!("trying to get bool values from an array with null elements") } value diff --git a/vortex-array/src/arrays/bool/vtable/mod.rs b/vortex-array/src/arrays/bool/vtable/mod.rs index ab94175b9bc..18fea87307d 100644 --- a/vortex-array/src/arrays/bool/vtable/mod.rs +++ b/vortex-array/src/arrays/bool/vtable/mod.rs @@ -86,7 +86,7 @@ impl VTable for Bool { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.bits.clone(), - _ => vortex_panic!(OutOfBounds: "BoolArray buffer index {idx} out of bounds"), + _ => vortex_panic!("BoolArray buffer index {idx} out of bounds"), } } @@ -102,7 +102,7 @@ impl VTable for Bool { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 1); let mut data = array.data().clone(); data.bits = buffers[0].clone(); Ok(ArrayParts::new( @@ -136,11 +136,11 @@ impl VTable for Bool { slots: &[Option], ) -> VortexResult<()> { let DType::Bool(nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected bool dtype, got {dtype:?}"); + vortex_bail!("Expected bool dtype, got {dtype:?}"); }; vortex_ensure!( data.bits.len() * 8 >= data.meta.offset() + len, - InvalidArgument: "BoolArray buffer with offset {} cannot back outer length {} (buffer bits = {})", + "BoolArray buffer with offset {} cannot back outer length {} (buffer bits = {})", data.meta.offset(), len, data.bits.len() * 8 @@ -151,7 +151,7 @@ impl VTable for Bool { vortex_ensure_eq!( validity_len, len, - InvalidArgument: "BoolArray validity len does not match outer length", + "BoolArray validity len does not match outer length", ); } @@ -169,7 +169,7 @@ impl VTable for Bool { ) -> VortexResult> { let metadata = BoolMetadata::decode(metadata)?; if buffers.len() != 1 { - vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); + vortex_bail!("Expected 1 buffer, got {}", buffers.len()); } let validity = if children.is_empty() { @@ -178,7 +178,7 @@ impl VTable for Bool { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "Expected 0 or 1 child, got {}", children.len()); + vortex_bail!("Expected 0 or 1 child, got {}", children.len()); }; let buffer = buffers[0].clone(); @@ -203,7 +203,7 @@ impl VTable for Bool { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for Bool requires a BoolBuilder"); + vortex_bail!("append_to_builder for Bool requires a BoolBuilder"); }; builder.append_bool_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/chunked/array.rs b/vortex-array/src/arrays/chunked/array.rs index 361ca4a6004..98ace53eadf 100644 --- a/vortex-array/src/arrays/chunked/array.rs +++ b/vortex-array/src/arrays/chunked/array.rs @@ -149,7 +149,7 @@ impl ChunkedData { pub fn validate(chunks: &[ArrayRef], dtype: &DType) -> VortexResult<()> { for chunk in chunks { if chunk.dtype() != dtype { - vortex_bail!(MismatchedTypes: "expected type: {} but instead got {}", dtype, chunk.dtype()); + vortex_bail!("expected type: {} but instead got {}", dtype, chunk.dtype()); } } @@ -172,7 +172,11 @@ impl Array { for chunk in chunks { if VALIDATE && chunk.dtype() != &dtype { - vortex_bail!(MismatchedTypes: "expected type: {} but instead got {}", &dtype, chunk.dtype()); + vortex_bail!( + "expected type: {} but instead got {}", + &dtype, + chunk.dtype() + ); } len += chunk.len(); chunk_offsets.push(len); diff --git a/vortex-array/src/arrays/chunked/compute/take.rs b/vortex-array/src/arrays/chunked/compute/take.rs index 52a6a3eb7c4..5602d051b23 100644 --- a/vortex-array/src/arrays/chunked/compute/take.rs +++ b/vortex-array/src/arrays/chunked/compute/take.rs @@ -97,7 +97,12 @@ fn take_chunked_via_sort( if let Some(&(index, _)) = pairs.last() { let index = usize::try_from(index)?; if index >= array.len() { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", index, 0, array.len()); + vortex_bail!( + "index {} out of bounds from {} to {}", + index, + 0, + array.len() + ); } } @@ -209,7 +214,12 @@ fn take_chunked( let index = usize::try_from(index)?; if index >= array.len() { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", index, 0, array.len()); + vortex_bail!( + "index {} out of bounds from {} to {}", + index, + 0, + array.len() + ); } let still_sorted = last_index.is_none_or(|last_index| index >= last_index); @@ -314,7 +324,11 @@ fn take_chunked_sorted( } if cursor != indices_values.len() { vortex_bail!( - OutOfBounds: "index {} out of bounds from {} to {}", usize::try_from(indices_values[cursor])?, 0, array.as_ref().len()); + "index {} out of bounds from {} to {}", + usize::try_from(indices_values[cursor])?, + 0, + array.as_ref().len() + ); } if chunks.len() == 1 { @@ -431,13 +445,18 @@ fn take_piecewise_chunked( } let end = start .checked_add(length) - .ok_or_else(|| vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"))?; + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; if end > array_len { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", end - 1, 0, array_len); + vortex_bail!( + "index {} out of bounds from {} to {}", + end - 1, + 0, + array_len + ); } - total_len = total_len.checked_add(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + total_len = total_len + .checked_add(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; // Locate the chunk containing `start`; `<=` skips empty chunks sharing the same offset. let mut chunk_idx = chunk_offsets.partition_point(|&offset| offset <= start) - 1; @@ -480,7 +499,7 @@ fn take_piecewise_chunked( vortex_ensure_eq!( total_len, output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); // Chunks visited in order: the per-chunk gathers already concatenate into the result. diff --git a/vortex-array/src/arrays/chunked/vtable/canonical.rs b/vortex-array/src/arrays/chunked/vtable/canonical.rs index 0d42aa41126..5d6d35d0dae 100644 --- a/vortex-array/src/arrays/chunked/vtable/canonical.rs +++ b/vortex-array/src/arrays/chunked/vtable/canonical.rs @@ -114,7 +114,7 @@ fn pack_variant_chunks( for chunk in &variant_chunks[1..] { vortex_ensure!( chunk.shredded().is_none(), - NotImplemented: "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" + "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" ); } None @@ -127,13 +127,13 @@ fn pack_variant_chunks( for chunk in &variant_chunks[1..] { let shredded = chunk.shredded().ok_or_else(|| { vortex_err!( - NotImplemented: "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" + "cannot canonicalize ChunkedArray: chunks disagree on shredded presence" ) })?; vortex_ensure_eq!( shredded.dtype(), &shredded_dtype, - MismatchedTypes: "cannot canonicalize ChunkedArray: shredded dtype mismatch", + "cannot canonicalize ChunkedArray: shredded dtype mismatch", ); shredded_chunks.push(shredded.clone()); } @@ -367,7 +367,7 @@ mod tests { match canonical { Canonical::Variant(array) => Ok(array), other => { - vortex_bail!(MismatchedTypes: "expected Variant canonical array, got {other:?}") + vortex_bail!("expected Variant canonical array, got {other:?}") } } } @@ -428,7 +428,7 @@ mod tests { let variant = into_variant(chunked.execute::(&mut ctx)?)?; let shredded = variant .shredded() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected shredded child"))?; + .ok_or_else(|| vortex_err!("expected shredded child"))?; for (index, value) in [1, 2, 3].into_iter().enumerate() { assert_eq!( @@ -552,7 +552,7 @@ mod tests { let fsl = match canonical { Canonical::FixedSizeList(fsl) => fsl, other => { - vortex_bail!(MismatchedTypes: "expected FixedSizeList canonical array, got {other:?}") + vortex_bail!("expected FixedSizeList canonical array, got {other:?}") } }; diff --git a/vortex-array/src/arrays/chunked/vtable/mod.rs b/vortex-array/src/arrays/chunked/vtable/mod.rs index 05cb07d14fc..cfd8b94cb90 100644 --- a/vortex-array/src/arrays/chunked/vtable/mod.rs +++ b/vortex-array/src/arrays/chunked/vtable/mod.rs @@ -86,7 +86,7 @@ impl VTable for Chunked { ) -> VortexResult<()> { vortex_ensure!( !slots.is_empty(), - InvalidArgument: "ChunkedArray must have at least a chunk offsets slot" + "ChunkedArray must have at least a chunk offsets slot" ); let chunk_offsets = slots[ChunkedSlots::CHUNK_OFFSETS] .as_ref() @@ -94,17 +94,17 @@ impl VTable for Chunked { vortex_ensure_eq!( chunk_offsets.dtype(), &DType::Primitive(PType::U64, Nullability::NonNullable), - MismatchedTypes: "ChunkedArray chunk offsets must be non-nullable u64", + "ChunkedArray chunk offsets must be non-nullable u64", ); vortex_ensure_eq!( chunk_offsets.len(), data.chunk_offsets.len(), - InvalidArgument: "ChunkedArray chunk offsets slot length does not match cached offsets length", + "ChunkedArray chunk offsets slot length does not match cached offsets length", ); vortex_ensure_eq!( data.chunk_offsets.len(), slots.len() - ChunkedSlots::CHUNKS_OFFSET + 1, - InvalidArgument: "ChunkedArray must have one more chunk offset than chunks", + "ChunkedArray must have one more chunk offset than chunks", ); vortex_ensure_eq!( data.chunk_offsets @@ -112,7 +112,7 @@ impl VTable for Chunked { .copied() .vortex_expect("chunked arrays always have a leading 0 offset"), len, - InvalidArgument: "ChunkedArray length does not match outer length", + "ChunkedArray length does not match outer length", ); for (idx, (start, end)) in data .chunk_offsets @@ -127,12 +127,12 @@ impl VTable for Chunked { vortex_ensure_eq!( chunk.dtype(), dtype, - MismatchedTypes: "ChunkedArray chunk dtype does not match outer dtype", + "ChunkedArray chunk dtype does not match outer dtype", ); vortex_ensure_eq!( chunk.len(), end - start, - InvalidArgument: "ChunkedArray chunk {idx} len does not match offsets span", + "ChunkedArray chunk {idx} len does not match offsets span", ); } Ok(()) @@ -143,11 +143,11 @@ impl VTable for Chunked { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ChunkedArray buffer index {idx} out of bounds") + vortex_panic!("ChunkedArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "ChunkedArray buffer_name index {idx} out of bounds") + vortex_panic!("ChunkedArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -176,12 +176,12 @@ impl VTable for Chunked { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "ChunkedArray expects empty metadata, got {} bytes", + "ChunkedArray expects empty metadata, got {} bytes", metadata.len() ); } if children.is_empty() { - vortex_bail!(InvalidArgument: "Chunked array needs at least one child"); + vortex_bail!("Chunked array needs at least one child"); } let nchunks = children.len() - 1; @@ -200,7 +200,7 @@ impl VTable for Chunked { .copied() .map(|offset| { usize::try_from(offset) - .map_err(|_| vortex_err!(Overflow: "chunk offset {offset} exceeds usize range")) + .map_err(|_| vortex_err!("chunk offset {offset} exceeds usize range")) }) .collect::>>()?; let mut slots = SmallVec::with_capacity(children.len()); @@ -250,7 +250,7 @@ impl VTable for Chunked { match array.dtype() { DType::Union(..) => { vortex_bail!( - NotImplemented: "TODO(connor)[Union]: canonicalize chunked Union arrays by packing type IDs \ + "TODO(connor)[Union]: canonicalize chunked Union arrays by packing type IDs \ and every sparse child along identical chunk boundaries" ) } diff --git a/vortex-array/src/arrays/chunked/vtable/operations.rs b/vortex-array/src/arrays/chunked/vtable/operations.rs index ef9c7f9b8e5..f228228acf4 100644 --- a/vortex-array/src/arrays/chunked/vtable/operations.rs +++ b/vortex-array/src/arrays/chunked/vtable/operations.rs @@ -25,7 +25,7 @@ impl OperationsVTable for Chunked { let slot = ChunkedSlots::CHUNKS_OFFSET + chunk_index; state .slot(slot)? - .ok_or_else(|| vortex_err!(InvalidArgument: "Chunked chunk slot {slot} is missing"))? + .ok_or_else(|| vortex_err!("Chunked chunk slot {slot} is missing"))? .execute_scalar(chunk_offset, ctx) } diff --git a/vortex-array/src/arrays/constant/compute/uncompressed_size.rs b/vortex-array/src/arrays/constant/compute/uncompressed_size.rs index 1f2cc803674..380adde03ab 100644 --- a/vortex-array/src/arrays/constant/compute/uncompressed_size.rs +++ b/vortex-array/src/arrays/constant/compute/uncompressed_size.rs @@ -41,9 +41,7 @@ mod tests { acc.finish()? .as_primitive() .typed_value::() - .ok_or_else( - || vortex_err!(AssertionFailed: "uncompressed size result should not be null"), - ) + .ok_or_else(|| vortex_err!("uncompressed size result should not be null")) } #[test] diff --git a/vortex-array/src/arrays/constant/vtable/canonical.rs b/vortex-array/src/arrays/constant/vtable/canonical.rs index cd70452d5a9..bbea85c4077 100644 --- a/vortex-array/src/arrays/constant/vtable/canonical.rs +++ b/vortex-array/src/arrays/constant/vtable/canonical.rs @@ -333,7 +333,7 @@ fn flat_elements( DType::Bool(nullability) => { let bits = BitBuffer::from_iter(elements.iter().map(|element| match element { Some(ScalarValue::Bool(value)) => *value, - Some(_) => vortex_panic!(AssertionFailed: "bool list holds a non-bool element"), + Some(_) => vortex_panic!("bool list holds a non-bool element"), None => false, })); BoolArray::new(bits, element_validity(elements, *nullability)).into_array() @@ -345,7 +345,7 @@ fn flat_elements( Some(ScalarValue::Primitive(value)) => value .cast::() .vortex_expect("list element of the list's element ptype"), - Some(_) => vortex_panic!(AssertionFailed: "primitive list holds a non-primitive element"), + Some(_) => vortex_panic!("primitive list holds a non-primitive element"), None => T::default(), } })); @@ -362,7 +362,7 @@ fn flat_elements( Some(ScalarValue::Decimal(value)) => value .cast::() .vortex_expect("list element fits the list's decimal type"), - Some(_) => vortex_panic!(AssertionFailed: "decimal list holds a non-decimal element"), + Some(_) => vortex_panic!("decimal list holds a non-decimal element"), None => T::default(), } })); @@ -385,7 +385,7 @@ fn flat_elements( None => builder.append_null(), Some(ScalarValue::Utf8(value)) => builder.append_value(value.as_bytes()), Some(ScalarValue::Binary(value)) => builder.append_value(value.as_slice()), - Some(_) => vortex_panic!(AssertionFailed: "byte list holds a non-byte element"), + Some(_) => vortex_panic!("byte list holds a non-byte element"), } } builder.finish() @@ -1200,7 +1200,7 @@ mod tests { fn date_elements() -> ArrayRef { let date = Scalar::extension::(TimeUnit::Days, Scalar::from(Some(42i32))); let DType::Extension(ext_dtype) = date.dtype().clone() else { - vortex_panic!(AssertionFailed: "a date is an extension value"); + vortex_panic!("a date is an extension value"); }; ExtensionArray::new( ext_dtype, diff --git a/vortex-array/src/arrays/constant/vtable/mod.rs b/vortex-array/src/arrays/constant/vtable/mod.rs index 29150b24138..3b55071ffb8 100644 --- a/vortex-array/src/arrays/constant/vtable/mod.rs +++ b/vortex-array/src/arrays/constant/vtable/mod.rs @@ -96,7 +96,7 @@ impl VTable for Constant { vortex_ensure_eq!( data.scalar.dtype(), dtype, - MismatchedTypes: "ConstantArray scalar dtype does not match outer dtype", + "ConstantArray scalar dtype does not match outer dtype", ); Ok(()) } @@ -110,7 +110,7 @@ impl VTable for Constant { 0 => BufferHandle::new_host( ScalarValue::to_proto_bytes::>(array.scalar.value()).into(), ), - _ => vortex_panic!(OutOfBounds: "ConstantArray buffer index {idx} out of bounds"), + _ => vortex_panic!("ConstantArray buffer index {idx} out of bounds"), } } @@ -130,7 +130,7 @@ impl VTable for Constant { } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { - vortex_panic!(OutOfBounds: "ConstantArray slot_name index {idx} out of bounds") + vortex_panic!("ConstantArray slot_name index {idx} out of bounds") } fn serialize( @@ -152,7 +152,7 @@ impl VTable for Constant { _children: &dyn ArrayChildren, session: &VortexSession, ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 1); let buffer = buffers[0].clone().try_to_host_sync()?; let bytes: &[u8] = buffer.as_ref(); diff --git a/vortex-array/src/arrays/datetime/mod.rs b/vortex-array/src/arrays/datetime/mod.rs index d4eb347f1ff..25913deb8b2 100644 --- a/vortex-array/src/arrays/datetime/mod.rs +++ b/vortex-array/src/arrays/datetime/mod.rs @@ -176,10 +176,10 @@ impl TryFrom for TemporalData { fn try_from(value: ArrayRef) -> Result { let ext = value .as_opt::() - .ok_or_else(|| vortex_err!(InvalidArgument: "array must be an ExtensionArray"))?; + .ok_or_else(|| vortex_err!("array must be an ExtensionArray"))?; if !ext.ext_dtype().is::() { vortex_bail!( - MismatchedTypes: "array extension dtype {} is not a temporal type", + "array extension dtype {} is not a temporal type", ext.ext_dtype() ); } @@ -208,7 +208,7 @@ impl TryFrom for TemporalData { fn try_from(ext: ExtensionArray) -> Result { if !ext.ext_dtype().is::() { vortex_bail!( - MismatchedTypes: "array extension dtype {} is not a temporal type", + "array extension dtype {} is not a temporal type", ext.ext_dtype() ); } diff --git a/vortex-array/src/arrays/decimal/array.rs b/vortex-array/src/arrays/decimal/array.rs index 4bd549f055a..9269e7c83ea 100644 --- a/vortex-array/src/arrays/decimal/array.rs +++ b/vortex-array/src/arrays/decimal/array.rs @@ -302,14 +302,14 @@ impl DecimalData { let byte_width = values_type.byte_width(); vortex_ensure!( buffer.len().is_multiple_of(byte_width), - InvalidArgument: "decimal buffer size {} is not divisible by element width {}", + "decimal buffer size {} is not divisible by element width {}", buffer.len(), byte_width, ); match_each_decimal_value_type!(values_type, |D| { vortex_ensure!( buffer.is_aligned_to(Alignment::of::()), - InvalidArgument: "decimal buffer alignment {:?} is invalid for values type {:?}", + "decimal buffer alignment {:?} is invalid for values type {:?}", buffer.alignment(), D::DECIMAL_TYPE, ); @@ -360,7 +360,7 @@ impl DecimalData { pub fn buffer(&self) -> Buffer { if self.values_type != T::DECIMAL_TYPE { vortex_panic!( - MismatchedTypes: "Cannot extract Buffer<{:?}> for DecimalArray with values_type {:?}", + "Cannot extract Buffer<{:?}> for DecimalArray with values_type {:?}", T::DECIMAL_TYPE, self.values_type, ); @@ -593,7 +593,7 @@ where { if !ValuesDVT::DECIMAL_TYPE.is_compatible_decimal_value_type(decimal_dtype) { vortex_panic!( - Overflow: "patch_typed: {:?} cannot represent every value in {}.", + "patch_typed: {:?} cannot represent every value in {}.", ValuesDVT::DECIMAL_TYPE, decimal_dtype ) diff --git a/vortex-array/src/arrays/decimal/compute/cast.rs b/vortex-array/src/arrays/decimal/compute/cast.rs index cbe747acfa5..29b38ce9406 100644 --- a/vortex-array/src/arrays/decimal/compute/cast.rs +++ b/vortex-array/src/arrays/decimal/compute/cast.rs @@ -51,7 +51,7 @@ impl CastReduce for Decimal { }; let DType::Decimal(from_decimal_dtype, _) = array.dtype() else { vortex_panic!( - MismatchedTypes: "DecimalArray must have decimal dtype, got {:?}", + "DecimalArray must have decimal dtype, got {:?}", array.dtype() ); }; @@ -90,7 +90,7 @@ impl CastKernel for Decimal { ) -> VortexResult> { let DType::Decimal(from_decimal_dtype, _) = array.dtype() else { vortex_panic!( - MismatchedTypes: "DecimalArray must have decimal dtype, got {:?}", + "DecimalArray must have decimal dtype, got {:?}", array.dtype() ); }; @@ -318,7 +318,7 @@ where .and_then(|value| { value.cast::().ok_or_else(|| { vortex_err!( - InvalidArgument: "decimal value cannot be represented as {} after casting to {}", + "decimal value cannot be represented as {} after casting to {}", T::DECIMAL_TYPE, to_decimal_dtype ) @@ -334,7 +334,7 @@ where (from {from_decimal_dtype} to {to_decimal_dtype})" ); vortex_err!( - InvalidArgument: "decimal value cannot be represented as {} after casting from {} to {}", + "decimal value cannot be represented as {} after casting from {} to {}", T::DECIMAL_TYPE, from_decimal_dtype, to_decimal_dtype @@ -461,7 +461,7 @@ pub fn upcast_decimal_values( // Only allow upcasting (widening) if to_values_type < from_values_type { vortex_bail!( - InvalidArgument: "Cannot downcast decimal values from {:?} to {:?}. Only upcasting is supported.", + "Cannot downcast decimal values from {:?} to {:?}. Only upcasting is supported.", from_values_type, to_values_type ); diff --git a/vortex-array/src/arrays/decimal/compute/rules.rs b/vortex-array/src/arrays/decimal/compute/rules.rs index 805bee61102..8f1d09ea92a 100644 --- a/vortex-array/src/arrays/decimal/compute/rules.rs +++ b/vortex-array/src/arrays/decimal/compute/rules.rs @@ -133,14 +133,14 @@ mod tests { } fn copy_to_host_sync(&self, _alignment: Alignment) -> VortexResult { - vortex_bail!(InvalidArgument: "decimal slicing must not copy device values to the host") + vortex_bail!("decimal slicing must not copy device values to the host") } fn copy_to_host( &self, _alignment: Alignment, ) -> VortexResult>> { - vortex_bail!(InvalidArgument: "decimal slicing must not copy device values to the host") + vortex_bail!("decimal slicing must not copy device values to the host") } fn slice(&self, range: Range) -> Arc { @@ -202,7 +202,7 @@ mod tests { .as_device() .as_any() .downcast_ref::() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected TestDeviceBuffer"))? + .ok_or_else(|| vortex_err!("expected TestDeviceBuffer"))? .0; assert_eq!(actual_bytes, &expected_bytes); assert_eq!(actual_bytes.as_ptr(), expected_bytes.as_ptr()); diff --git a/vortex-array/src/arrays/decimal/utils.rs b/vortex-array/src/arrays/decimal/utils.rs index 73bd6ec944c..3c7304e6fda 100644 --- a/vortex-array/src/arrays/decimal/utils.rs +++ b/vortex-array/src/arrays/decimal/utils.rs @@ -59,7 +59,7 @@ pub fn converted_buffer( .find(|&(_, v)| W::from(*v).is_none()) .vortex_expect("overflow scan found an overflowing value"); vortex_bail!( - Overflow: "decimal value {v} at index {i} does not fit {}", + "decimal value {v} at index {i} does not fit {}", W::DECIMAL_TYPE ); } @@ -71,7 +71,7 @@ pub fn converted_buffer( for (i, v) in src.iter().enumerate() { if values.value(i) && W::from(*v).is_none() { vortex_bail!( - Overflow: "decimal value {v} at index {i} does not fit {}", + "decimal value {v} at index {i} does not fit {}", W::DECIMAL_TYPE ); } diff --git a/vortex-array/src/arrays/decimal/vtable/mod.rs b/vortex-array/src/arrays/decimal/vtable/mod.rs index 0407161abe2..f3f0c9494a3 100644 --- a/vortex-array/src/arrays/decimal/vtable/mod.rs +++ b/vortex-array/src/arrays/decimal/vtable/mod.rs @@ -128,12 +128,12 @@ impl VTable for Decimal { slots: &[Option], ) -> VortexResult<()> { let DType::Decimal(_, nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected decimal dtype, got {dtype:?}"); + vortex_bail!("Expected decimal dtype, got {dtype:?}"); }; vortex_ensure_eq!( data.len(), len, - InvalidArgument: "DecimalArray length does not match outer length", + "DecimalArray length does not match outer length", ); let validity = crate::array::child_to_validity(slots[DecimalSlots::VALIDITY].as_ref(), *nullability); @@ -141,7 +141,7 @@ impl VTable for Decimal { vortex_ensure_eq!( validity_len, len, - InvalidArgument: "DecimalArray validity len does not match outer length", + "DecimalArray validity len does not match outer length", ); } @@ -163,7 +163,7 @@ impl VTable for Decimal { let validity = fixed_width::deserialize_validity(dtype.nullability(), len, children)?; let Some(decimal_dtype) = dtype.as_decimal_opt() else { - vortex_bail!(MismatchedTypes: "Expected Decimal dtype, got {:?}", dtype) + vortex_bail!("Expected Decimal dtype, got {:?}", dtype) }; let slots = DecimalData::make_slots(&validity, len); @@ -171,7 +171,7 @@ impl VTable for Decimal { // Check and reinterpret-cast the buffer vortex_ensure!( values.is_aligned_to(Alignment::of::()), - InvalidArgument: "DecimalArray buffer not aligned for values type {:?}", + "DecimalArray buffer not aligned for values type {:?}", D::DECIMAL_TYPE ); DecimalData::try_new_handle(values, metadata.values_type(), *decimal_dtype) @@ -199,7 +199,7 @@ impl VTable for Decimal { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for Decimal requires a DecimalBuilder"); + vortex_bail!("append_to_builder for Decimal requires a DecimalBuilder"); }; builder.append_decimal_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/dict/array.rs b/vortex-array/src/arrays/dict/array.rs index 80aba23d40a..69d5be3a39e 100644 --- a/vortex-array/src/arrays/dict/array.rs +++ b/vortex-array/src/arrays/dict/array.rs @@ -116,7 +116,7 @@ impl DictData { /// It is an error to provide a nullable `codes` with non-nullable `values`. pub(crate) fn try_new(codes_dtype: &DType) -> VortexResult { if !codes_dtype.is_int() { - vortex_bail!(MismatchedTypes: "expected type: int but instead got {}", codes_dtype); + vortex_bail!("expected type: int but instead got {}", codes_dtype); } Ok(unsafe { Self::new_unchecked() }) @@ -138,7 +138,7 @@ pub trait DictArrayExt: TypedArrayRef + DictArraySlotsExt { let referenced_mask = self.compute_referenced_values_mask(true, ctx)?; let all_referenced = referenced_mask.true_count() == referenced_mask.len(); - vortex_ensure!(all_referenced, InvalidArgument: "value in dict not referenced"); + vortex_ensure!(all_referenced, "value in dict not referenced"); } Ok(()) @@ -409,7 +409,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!(AssertionFailed: "Expected indices from mask") + vortex_panic!("Expected indices from mask") }; assert_eq!(indices, [0, 2, 4]); } @@ -432,7 +432,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!(AssertionFailed: "Expected indices from mask") + vortex_panic!("Expected indices from mask") }; assert_eq!(indices, [0]); } @@ -459,7 +459,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!(AssertionFailed: "Expected indices from mask") + vortex_panic!("Expected indices from mask") }; assert_eq!(indices, [2, 4]); } @@ -482,7 +482,7 @@ mod test { .execute_mask(dict.as_ref().len(), &mut SESSION.create_execution_ctx()) .unwrap(); let AllOr::Some(indices) = mask.indices() else { - vortex_panic!(AssertionFailed: "Expected indices from mask") + vortex_panic!("Expected indices from mask") }; assert_eq!(indices, [0, 2, 4]); } diff --git a/vortex-array/src/arrays/dict/vtable/mod.rs b/vortex-array/src/arrays/dict/vtable/mod.rs index 475d242dd2e..a2ba1487a59 100644 --- a/vortex-array/src/arrays/dict/vtable/mod.rs +++ b/vortex-array/src/arrays/dict/vtable/mod.rs @@ -104,13 +104,13 @@ impl VTable for Dict { let view = DictSlotsView::from_slots(slots); let codes = view.codes; let values = view.values; - vortex_ensure_eq!(codes.len(), len, InvalidArgument: "DictArray codes length mismatch"); + vortex_ensure_eq!(codes.len(), len, "DictArray codes length mismatch"); vortex_ensure_eq!( values .dtype() .union_nullability(codes.dtype().nullability()), *dtype, - MismatchedTypes: "DictArray dtype does not match codes/values dtype", + "DictArray dtype does not match codes/values dtype", ); Ok(()) } @@ -120,7 +120,7 @@ impl VTable for Dict { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "DictArray buffer index {idx} out of bounds") + vortex_panic!("DictArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -144,7 +144,7 @@ impl VTable for Dict { codes_ptype: PType::try_from(array.codes().dtype())? as i32, values_len: u32::try_from(array.values().len()).map_err(|_| { vortex_err!( - Overflow: "Dictionary values size {} overflowed u32", + "Dictionary values size {} overflowed u32", array.values().len() ) })?, @@ -167,7 +167,7 @@ impl VTable for Dict { let metadata = DictMetadata::decode(metadata)?; if children.len() != 2 { vortex_bail!( - InvalidArgument: "Expected 2 children for dict encoding, found {}", + "Expected 2 children for dict encoding, found {}", children.len() ) } diff --git a/vortex-array/src/arrays/dict/vtable/operations.rs b/vortex-array/src/arrays/dict/vtable/operations.rs index 1e4aa4f429b..139a23ef05e 100644 --- a/vortex-array/src/arrays/dict/vtable/operations.rs +++ b/vortex-array/src/arrays/dict/vtable/operations.rs @@ -24,7 +24,7 @@ impl OperationsVTable for Dict { let dtype = state.array().dtype().clone(); let code = state .slot(DictSlots::CODES)? - .ok_or_else(|| vortex_err!(InvalidArgument: "Dict codes slot is missing"))? + .ok_or_else(|| vortex_err!("Dict codes slot is missing"))? .execute_scalar(index, ctx)?; let Some(dict_index) = code.as_primitive().as_::() else { return Ok(Scalar::null(dtype)); @@ -32,7 +32,7 @@ impl OperationsVTable for Dict { Ok(state .slot(DictSlots::VALUES)? - .ok_or_else(|| vortex_err!(InvalidArgument: "Dict values slot is missing"))? + .ok_or_else(|| vortex_err!("Dict values slot is missing"))? .execute_scalar(dict_index, ctx)? .cast(&dtype) .vortex_expect("Array dtype will only differ by nullability")) diff --git a/vortex-array/src/arrays/extension/array.rs b/vortex-array/src/arrays/extension/array.rs index 2412b051d27..841d35dbbea 100644 --- a/vortex-array/src/arrays/extension/array.rs +++ b/vortex-array/src/arrays/extension/array.rs @@ -53,7 +53,7 @@ impl Array { vortex_ensure_eq!( ext_dtype.storage_dtype(), storage_array.dtype(), - MismatchedTypes: "Tried to create an `ExtensionArray` with an incompatible storage array" + "Tried to create an `ExtensionArray` with an incompatible storage array" ); let dtype = DType::Extension(ext_dtype); diff --git a/vortex-array/src/arrays/extension/vtable/mod.rs b/vortex-array/src/arrays/extension/vtable/mod.rs index 75598e99ea5..6069d945efe 100644 --- a/vortex-array/src/arrays/extension/vtable/mod.rs +++ b/vortex-array/src/arrays/extension/vtable/mod.rs @@ -106,18 +106,18 @@ impl VTable for Extension { vortex_ensure_eq!( storage.len(), len, - InvalidArgument: "ExtensionArray length does not match outer length", + "ExtensionArray length does not match outer length", ); let ext_dtype = dtype .as_extension_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "not an extension dtype"))?; + .ok_or_else(|| vortex_err!("not an extension dtype"))?; let actual_dtype = DType::Extension(ext_dtype.clone()); vortex_ensure_eq!( &actual_dtype, dtype, - MismatchedTypes: "ExtensionArray dtype does not match outer dtype", + "ExtensionArray dtype does not match outer dtype", ); Ok(()) @@ -128,7 +128,7 @@ impl VTable for Extension { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ExtensionArray buffer index {idx} out of bounds") + vortex_panic!("ExtensionArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -162,15 +162,15 @@ impl VTable for Extension { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "ExtensionArray expects empty metadata, got {} bytes", + "ExtensionArray expects empty metadata, got {} bytes", metadata.len() ); } let DType::Extension(ext_dtype) = dtype else { - vortex_bail!(MismatchedTypes: "Not an extension DType"); + vortex_bail!("Not an extension DType"); }; if children.len() != 1 { - vortex_bail!(MismatchedTypes: "Expected 1 child, got {}", children.len()); + vortex_bail!("Expected 1 child, got {}", children.len()); } let storage = children.get(0, ext_dtype.storage_dtype(), len)?; Ok(ArrayParts::new( @@ -196,7 +196,7 @@ impl VTable for Extension { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for Extension requires an ExtensionBuilder"); + vortex_bail!("append_to_builder for Extension requires an ExtensionBuilder"); }; builder.append_extension_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/extension/vtable/operations.rs b/vortex-array/src/arrays/extension/vtable/operations.rs index 92e4f75668c..14d21988dd7 100644 --- a/vortex-array/src/arrays/extension/vtable/operations.rs +++ b/vortex-array/src/arrays/extension/vtable/operations.rs @@ -24,7 +24,7 @@ impl OperationsVTable for Extension { let ext_dtype = state.array().ext_dtype().clone(); let storage = state .slot(ExtensionSlots::STORAGE)? - .ok_or_else(|| vortex_err!(InvalidArgument: "Extension storage slot is missing"))? + .ok_or_else(|| vortex_err!("Extension storage slot is missing"))? .execute_scalar(index, ctx)?; Ok(Scalar::extension_ref(ext_dtype, storage)) } diff --git a/vortex-array/src/arrays/filter/array.rs b/vortex-array/src/arrays/filter/array.rs index 5b8edd1da62..e7c1f4efb1a 100644 --- a/vortex-array/src/arrays/filter/array.rs +++ b/vortex-array/src/arrays/filter/array.rs @@ -51,7 +51,7 @@ impl FilterData { vortex_ensure_eq!( array_len, mask.len(), - InvalidArgument: "FilterArray array and mask lengths must match", + "FilterArray array and mask lengths must match", ); Ok(Self { mask }) diff --git a/vortex-array/src/arrays/filter/execute/take.rs b/vortex-array/src/arrays/filter/execute/take.rs index edc32c37493..0a4b0d70238 100644 --- a/vortex-array/src/arrays/filter/execute/take.rs +++ b/vortex-array/src/arrays/filter/execute/take.rs @@ -134,7 +134,7 @@ impl TakeExecute for Filter { } let DType::Primitive(ptype, nullability) = indices.dtype() else { - vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) + vortex_bail!("Invalid indices dtype: {}", indices.dtype()) }; if should_materialize_big_take(array, indices) { diff --git a/vortex-array/src/arrays/filter/execute/take/rank.rs b/vortex-array/src/arrays/filter/execute/take/rank.rs index 061f991ca10..7743c1df02c 100644 --- a/vortex-array/src/arrays/filter/execute/take/rank.rs +++ b/vortex-array/src/arrays/filter/execute/take/rank.rs @@ -60,7 +60,12 @@ fn sequential_take_len_typed( } if ranks.len() > filtered_len { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", ranks.len() - 1, 0, filtered_len); + vortex_bail!( + "index {} out of bounds from {} to {}", + ranks.len() - 1, + 0, + filtered_len + ); } Ok(Some(ranks.len())) @@ -141,7 +146,12 @@ pub(in crate::arrays::filter) fn validate_rank( ) -> VortexResult { let rank: usize = rank.as_(); if rank >= filtered_len { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", rank, 0, filtered_len); + vortex_bail!( + "index {} out of bounds from {} to {}", + rank, + 0, + filtered_len + ); } Ok(rank) } diff --git a/vortex-array/src/arrays/filter/vtable.rs b/vortex-array/src/arrays/filter/vtable.rs index 68f94c40562..b7642784fce 100644 --- a/vortex-array/src/arrays/filter/vtable.rs +++ b/vortex-array/src/arrays/filter/vtable.rs @@ -82,7 +82,7 @@ impl VTable for Filter { ) -> VortexResult<()> { vortex_ensure!( slots[FilterSlots::CHILD].is_some(), - InvalidArgument: "FilterArray child slot must be present" + "FilterArray child slot must be present" ); let child = slots[FilterSlots::CHILD] .as_ref() @@ -90,17 +90,17 @@ impl VTable for Filter { vortex_ensure_eq!( child.dtype(), dtype, - MismatchedTypes: "FilterArray dtype does not match outer dtype", + "FilterArray dtype does not match outer dtype", ); vortex_ensure_eq!( data.len(), len, - InvalidArgument: "FilterArray length does not match outer length", + "FilterArray length does not match outer length", ); vortex_ensure_eq!( child.len(), data.mask.len(), - InvalidArgument: "FilterArray child length does not match mask length", + "FilterArray child length does not match mask length", ); Ok(()) } @@ -110,7 +110,7 @@ impl VTable for Filter { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "FilterArray has no buffers") + vortex_panic!("FilterArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -134,7 +134,7 @@ impl VTable for Filter { _session: &VortexSession, ) -> VortexResult>> { // TODO(joe): make this configurable - vortex_bail!(Serde: "Filter array is not serializable") + vortex_bail!("Filter array is not serializable") } fn deserialize( @@ -147,7 +147,7 @@ impl VTable for Filter { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "Filter array is not serializable") + vortex_bail!("Filter array is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/arrays/fixed_size_list/array.rs b/vortex-array/src/arrays/fixed_size_list/array.rs index 6f35e5c91a4..bae1829f67a 100644 --- a/vortex-array/src/arrays/fixed_size_list/array.rs +++ b/vortex-array/src/arrays/fixed_size_list/array.rs @@ -188,7 +188,7 @@ impl FixedSizeListData { vortex_ensure_eq!( len, validity_len, - InvalidArgument: "validity length does not match fixed-size list array size", + "validity length does not match fixed-size list array size", ); } @@ -197,7 +197,7 @@ impl FixedSizeListData { if list_size == 0 { vortex_ensure!( elements.is_empty(), - InvalidArgument: "a degenerate (`list_size == 0`) `FixedSizeList` should have no underlying elements" + "a degenerate (`list_size == 0`) `FixedSizeList` should have no underlying elements" ); return Ok(()); } @@ -205,7 +205,7 @@ impl FixedSizeListData { vortex_ensure_eq!( len * list_size as usize, elements.len(), - InvalidArgument: "the `elements` array has the incorrect number of elements to construct a \ + "the `elements` array has the incorrect number of elements to construct a \ `FixedSizeList[{list_size}] array of length {len}", ); diff --git a/vortex-array/src/arrays/fixed_size_list/compute/take.rs b/vortex-array/src/arrays/fixed_size_list/compute/take.rs index 36a51a52075..7fb7d6c0da8 100644 --- a/vortex-array/src/arrays/fixed_size_list/compute/take.rs +++ b/vortex-array/src/arrays/fixed_size_list/compute/take.rs @@ -68,14 +68,14 @@ fn take_empty_fsl( let indices_validity = indices.validity()?.execute_mask(new_len, ctx)?; vortex_ensure!( indices_validity.all_false(), - InvalidArgument: "cannot take valid indices from an empty FixedSizeList" + "cannot take valid indices from an empty FixedSizeList" ); } let list_size = array.list_size() as usize; let elements_len = new_len.checked_mul(list_size).ok_or_else(|| { vortex_err!( - Overflow: "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" + "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" ) })?; let new_elements = default_elements(array, elements_len, ctx.allocator()); @@ -102,10 +102,10 @@ fn take_non_empty_fsl( debug_assert!(!array.is_empty()); let DType::Primitive(ptype, _) = indices.dtype() else { - vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) + vortex_bail!("Invalid indices dtype: {}", indices.dtype()) }; if !ptype.is_int() { - vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()); + vortex_bail!("Invalid indices dtype: {}", indices.dtype()); } if array.list_size() == 0 { @@ -141,7 +141,7 @@ fn take_piecewise_fsl( let new_len = indices.as_ref().len(); let elements_len = new_len.checked_mul(list_size).ok_or_else(|| { vortex_err!( - Overflow: "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" + "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" ) })?; @@ -175,20 +175,25 @@ fn take_piecewise_fsl( } let end = start .checked_add(length) - .ok_or_else(|| vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"))?; + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; if end > array_len { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", end - 1, 0, array_len); + vortex_bail!( + "index {} out of bounds from {} to {}", + end - 1, + 0, + array_len + ); } - total_len = total_len.checked_add(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + total_len = total_len + .checked_add(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; element_starts.push(u64::try_from(start * list_size)?); element_lengths.push(u64::try_from(length * list_size)?); } vortex_ensure_eq!( total_len, new_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); let new_elements = @@ -233,7 +238,7 @@ fn take_non_empty_degenerate_fsl( debug_assert_eq!(array.list_size(), 0); vortex_ensure!( array.elements().is_empty(), - InvalidArgument: "degenerate list must have empty elements" + "degenerate list must have empty elements" ); let indices_array = indices.clone().execute::(ctx)?; @@ -293,7 +298,7 @@ fn take_non_empty_non_degenerate_elements( let new_len = indices.len(); let elements_len = new_len.checked_mul(list_size).ok_or_else(|| { vortex_err!( - Overflow: "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" + "FixedSizeList take output length overflow: {new_len} lists of size {list_size}" ) })?; @@ -308,7 +313,12 @@ fn take_non_empty_non_degenerate_elements( let data_idx: usize = data_idx.as_(); if data_idx >= array_len { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", data_idx, 0, array_len); + vortex_bail!( + "index {} out of bounds from {} to {}", + data_idx, + 0, + array_len + ); } Ok((data_idx * list_size) as u64) }) @@ -332,7 +342,12 @@ fn bounds_check_valid_indices( if is_index_valid { let data_idx = data_idx.as_(); if data_idx >= array_len { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", data_idx, 0, array_len); + vortex_bail!( + "index {} out of bounds from {} to {}", + data_idx, + 0, + array_len + ); } } } diff --git a/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs b/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs index 63cdbe3ad85..0e140a47998 100644 --- a/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs +++ b/vortex-array/src/arrays/fixed_size_list/vtable/mod.rs @@ -76,11 +76,11 @@ impl VTable for FixedSizeList { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "FixedSizeListArray buffer index {idx} out of bounds") + vortex_panic!("FixedSizeListArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "FixedSizeListArray buffer_name index {idx} out of bounds") + vortex_panic!("FixedSizeListArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -113,9 +113,9 @@ impl VTable for FixedSizeList { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), FixedSizeListSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), FixedSizeListSlots::COUNT); let DType::FixedSizeList(_, list_size, nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected `DType::FixedSizeList`, got {dtype:?}"); + vortex_bail!("Expected `DType::FixedSizeList`, got {dtype:?}"); }; let elements = slots[FixedSizeListSlots::ELEMENTS] .as_ref() @@ -126,7 +126,7 @@ impl VTable for FixedSizeList { } else { elements.len() / *list_size as usize == len }, - InvalidArgument: "FixedSizeListArray length {} does not match outer length {}", + "FixedSizeListArray length {} does not match outer length {}", len, len ); @@ -136,7 +136,7 @@ impl VTable for FixedSizeList { vortex_ensure_eq!( &actual_dtype, dtype, - MismatchedTypes: "FixedSizeListArray dtype does not match outer dtype", + "FixedSizeListArray dtype does not match outer dtype", ); Ok(()) @@ -154,22 +154,22 @@ impl VTable for FixedSizeList { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "FixedSizeListArray expects empty metadata, got {} bytes", + "FixedSizeListArray expects empty metadata, got {} bytes", metadata.len() ); } vortex_ensure!( buffers.is_empty(), - InvalidArgument: "`FixedSizeList::build` expects no buffers" + "`FixedSizeList::build` expects no buffers" ); let DType::FixedSizeList(element_dtype, list_size, _) = &dtype else { - vortex_bail!(MismatchedTypes: "Expected `DType::FixedSizeList`, got {:?}", dtype); + vortex_bail!("Expected `DType::FixedSizeList`, got {:?}", dtype); }; let validity = { if children.len() > 2 { - vortex_bail!(InvalidArgument: "`FixedSizeList::build` method expected 1 or 2 children") + vortex_bail!("`FixedSizeList::build` method expected 1 or 2 children") } if children.len() == 2 { @@ -210,7 +210,7 @@ impl VTable for FixedSizeList { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for FixedSizeList requires a FixedSizeListBuilder"); + vortex_bail!("append_to_builder for FixedSizeList requires a FixedSizeListBuilder"); }; builder.append_fixed_size_list_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/fixed_width/array.rs b/vortex-array/src/arrays/fixed_width/array.rs index 82a8535e6b2..e6eac415664 100644 --- a/vortex-array/src/arrays/fixed_width/array.rs +++ b/vortex-array/src/arrays/fixed_width/array.rs @@ -51,11 +51,11 @@ pub(crate) fn with_values( ) -> VortexResult> { let expected_len = len .checked_mul(V::byte_width(array)) - .ok_or_else(|| vortex_err!(Overflow: "Fixed-width values buffer length overflows usize"))?; + .ok_or_else(|| vortex_err!("Fixed-width values buffer length overflows usize"))?; vortex_ensure_eq!( values.len(), expected_len, - InvalidArgument: "Fixed-width values buffer length does not match expected length", + "Fixed-width values buffer length does not match expected length", ); V::with_values(array, values, len, validity) } diff --git a/vortex-array/src/arrays/fixed_width/take/mod.rs b/vortex-array/src/arrays/fixed_width/take/mod.rs index 169ebcc6ac8..2cf9f1f950b 100644 --- a/vortex-array/src/arrays/fixed_width/take/mod.rs +++ b/vortex-array/src/arrays/fixed_width/take/mod.rs @@ -120,10 +120,10 @@ pub(crate) fn take( } let DType::Primitive(ptype, nullability) = indices.dtype() else { - vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) + vortex_bail!("Invalid indices dtype: {}", indices.dtype()) }; if !ptype.is_int() { - vortex_bail!(InvalidArgument: "Invalid indices dtype: {}", indices.dtype()) + vortex_bail!("Invalid indices dtype: {}", indices.dtype()) } let indices_validity = indices.validity()?; diff --git a/vortex-array/src/arrays/fixed_width/take/records.rs b/vortex-array/src/arrays/fixed_width/take/records.rs index 6706af2d256..692707db9da 100644 --- a/vortex-array/src/arrays/fixed_width/take/records.rs +++ b/vortex-array/src/arrays/fixed_width/take/records.rs @@ -34,7 +34,7 @@ pub(super) fn take_byte_records( let output_len = indices .len() .checked_mul(byte_width) - .ok_or_else(|| vortex_err!(Overflow: "Fixed-width take output length overflows usize"))?; + .ok_or_else(|| vortex_err!("Fixed-width take output length overflows usize"))?; let mut result = BufferMut::::with_capacity_in(output_len, allocator.clone()); for index in indices { let index = index.as_(); diff --git a/vortex-array/src/arrays/fixed_width/take/slices.rs b/vortex-array/src/arrays/fixed_width/take/slices.rs index 989d88135e4..480e0096360 100644 --- a/vortex-array/src/arrays/fixed_width/take/slices.rs +++ b/vortex-array/src/arrays/fixed_width/take/slices.rs @@ -44,13 +44,14 @@ pub(super) fn take_slices_constant_length( output_len: usize, allocator: &BufferAllocatorRef, ) -> VortexResult { - let computed_len = starts.len().checked_mul(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + let computed_len = starts + .len() + .checked_mul(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; vortex_ensure_eq!( computed_len, output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); copy_slices( values, @@ -72,16 +73,16 @@ fn copy_slices( ) -> VortexResult { let input_byte_len = record_count .checked_mul(byte_width) - .ok_or_else(|| vortex_err!(Overflow: "Fixed-width values buffer length overflows usize"))?; + .ok_or_else(|| vortex_err!("Fixed-width values buffer length overflows usize"))?; vortex_ensure_eq!( values.len(), input_byte_len, - InvalidArgument: "Fixed-width values buffer length does not match record count", + "Fixed-width values buffer length does not match record count", ); - let output_byte_len = output_len.checked_mul(byte_width).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + let output_byte_len = output_len + .checked_mul(byte_width) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; let mut result = BufferMut::::with_capacity_aligned_in( output_byte_len, values.alignment(), @@ -91,12 +92,12 @@ fn copy_slices( let mut cursor = 0usize; for (start, length) in slices { - let end = start.checked_add(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray slice end overflows usize"), - )?; + let end = start + .checked_add(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray slice end overflows usize"))?; vortex_ensure!( end <= record_count, - OutOfBounds: "PiecewiseSequenceArray slice {start}..{end} exceeds array length {record_count}" + "PiecewiseSequenceArray slice {start}..{end} exceeds array length {record_count}" ); // These multiplications cannot overflow because `end <= record_count` and the complete // values buffer length was checked above. @@ -112,7 +113,7 @@ fn copy_slices( vortex_ensure_eq!( result.len(), output_byte_len, - AssertionFailed: "PiecewiseSequenceArray expanded byte length does not match declared byte length", + "PiecewiseSequenceArray expanded byte length does not match declared byte length", ); Ok(result.freeze().into_byte_buffer()) } diff --git a/vortex-array/src/arrays/fixed_width/vtable.rs b/vortex-array/src/arrays/fixed_width/vtable.rs index 21e209e75e6..b0994013a66 100644 --- a/vortex-array/src/arrays/fixed_width/vtable.rs +++ b/vortex-array/src/arrays/fixed_width/vtable.rs @@ -14,7 +14,7 @@ use crate::validity::Validity; pub(crate) fn buffer(array_name: &str, values: &BufferHandle, idx: usize) -> BufferHandle { match idx { 0 => values.clone(), - _ => vortex_panic!(OutOfBounds: "{array_name} buffer index {idx} out of bounds"), + _ => vortex_panic!("{array_name} buffer index {idx} out of bounds"), } } @@ -26,7 +26,7 @@ pub(crate) fn buffer_name(idx: usize) -> Option { } pub(crate) fn single_buffer(buffers: &[BufferHandle]) -> VortexResult { - vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 1); Ok(buffers[0].clone()) } @@ -38,6 +38,6 @@ pub(crate) fn deserialize_validity( match children.len() { 0 => Ok(Validity::from(nullability)), 1 => Ok(Validity::Array(children.get(0, &Validity::DTYPE, len)?)), - child_count => vortex_bail!(MismatchedTypes: "Expected 0 or 1 child, got {child_count}"), + child_count => vortex_bail!("Expected 0 or 1 child, got {child_count}"), } } diff --git a/vortex-array/src/arrays/interleave/execute/bool.rs b/vortex-array/src/arrays/interleave/execute/bool.rs index cbb32a8b649..e6f1aa5cbe3 100644 --- a/vortex-array/src/arrays/interleave/execute/bool.rs +++ b/vortex-array/src/arrays/interleave/execute/bool.rs @@ -99,18 +99,18 @@ fn validate_selectors, R: AsPrimitive>( vortex_ensure_eq!( rows.len(), len, - InvalidArgument: "interleave row_indices length does not match array_indices length", + "interleave row_indices length does not match array_indices length", ); for i in 0..len { let branch = branches[i].as_(); vortex_ensure!( branch < value_bits.len(), - OutOfBounds: "interleave array index out of bounds" + "interleave array index out of bounds" ); vortex_ensure!( rows[i].as_() < value_bits[branch].len(), - OutOfBounds: "interleave row index out of bounds" + "interleave row index out of bounds" ); } diff --git a/vortex-array/src/arrays/interleave/execute/mod.rs b/vortex-array/src/arrays/interleave/execute/mod.rs index d951cf4422d..558db9e3309 100644 --- a/vortex-array/src/arrays/interleave/execute/mod.rs +++ b/vortex-array/src/arrays/interleave/execute/mod.rs @@ -31,7 +31,7 @@ pub(super) fn execute( primitive::execute(array, ctx) } else { vortex_panic!( - NotImplemented: "interleave execution is not implemented for value dtype {}", + "interleave execution is not implemented for value dtype {}", array.dtype() ) } diff --git a/vortex-array/src/arrays/interleave/execute/primitive.rs b/vortex-array/src/arrays/interleave/execute/primitive.rs index bbc8db56170..c405df102df 100644 --- a/vortex-array/src/arrays/interleave/execute/primitive.rs +++ b/vortex-array/src/arrays/interleave/execute/primitive.rs @@ -116,16 +116,16 @@ where vortex_ensure_eq!( rows.len(), branches.len(), - InvalidArgument: "interleave row_indices length does not match array_indices length", + "interleave row_indices length does not match array_indices length", ); let mut output = BufferMut::with_capacity_in(branches.len(), allocator.clone()); output.try_extend_trusted(branches.iter().zip(rows).map(|(branch, row)| { let Some(source) = values.get((*branch).as_()) else { - vortex_bail!(OutOfBounds: "interleave array index out of bounds"); + vortex_bail!("interleave array index out of bounds"); }; let row = (*row).as_(); - vortex_ensure!(row < source.len, OutOfBounds: "interleave row index out of bounds"); + vortex_ensure!(row < source.len, "interleave row index out of bounds"); Ok(source.data[row & source.row_mask]) }))?; Ok(output.freeze()) diff --git a/vortex-array/src/arrays/interleave/mod.rs b/vortex-array/src/arrays/interleave/mod.rs index 28635ea1b1e..d5cb8085dbc 100644 --- a/vortex-array/src/arrays/interleave/mod.rs +++ b/vortex-array/src/arrays/interleave/mod.rs @@ -93,7 +93,7 @@ impl Interleave { ) -> VortexResult { vortex_ensure!( values.len() >= 2, - InvalidArgument: "interleave requires at least 2 values, got {}", + "interleave requires at least 2 values, got {}", values.len() ); @@ -107,12 +107,12 @@ impl Interleave { DType::Primitive(ptype, nullability) if ptype.is_unsigned_int() => { vortex_ensure!( !nullability.is_nullable(), - InvalidArgument: "interleave {name} must be non-nullable, got {}", + "interleave {name} must be non-nullable, got {}", selector.dtype() ); } other => vortex_bail!( - InvalidArgument: "interleave {name} must be a non-nullable unsigned integer, got {other}" + "interleave {name} must be a non-nullable unsigned integer, got {other}" ), } } @@ -120,7 +120,7 @@ impl Interleave { vortex_ensure_eq!( array_indices.len(), row_indices.len(), - InvalidArgument: "interleave selectors must have equal length", + "interleave selectors must have equal length", ); let base_dtype = values[0].dtype(); @@ -128,7 +128,7 @@ impl Interleave { for value in values { vortex_ensure!( value.dtype().eq_ignore_nullability(base_dtype), - MismatchedTypes: "interleave values must share a dtype up to nullability: {} vs {}", + "interleave values must share a dtype up to nullability: {} vs {}", base_dtype, value.dtype() ); @@ -159,11 +159,11 @@ impl VTable for Interleave { vortex_ensure_eq!( slots.len(), data.num_values + InterleaveSlots::FIXED_COUNT, - InvalidArgument: "InterleaveArray expects values + array_indices + row_indices slots", + "InterleaveArray expects values + array_indices + row_indices slots", ); vortex_ensure!( slots.iter().all(|s| s.is_some()), - InvalidArgument: "InterleaveArray slots must all be present" + "InterleaveArray slots must all be present" ); let array_indices = slots[InterleaveSlots::ARRAY_INDICES] @@ -183,12 +183,12 @@ impl VTable for Interleave { vortex_ensure_eq!( dtype, &expected_dtype, - MismatchedTypes: "InterleaveArray dtype does not match the dtype implied by its children", + "InterleaveArray dtype does not match the dtype implied by its children", ); vortex_ensure_eq!( len, array_indices.len(), - InvalidArgument: "InterleaveArray length does not match array_indices length", + "InterleaveArray length does not match array_indices length", ); Ok(()) } @@ -198,7 +198,7 @@ impl VTable for Interleave { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "InterleaveArray has no buffers") + vortex_panic!("InterleaveArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -221,7 +221,7 @@ impl VTable for Interleave { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_bail!(Serde: "Interleave array is not serializable") + vortex_bail!("Interleave array is not serializable") } fn deserialize( @@ -233,7 +233,7 @@ impl VTable for Interleave { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "Interleave array is not serializable") + vortex_bail!("Interleave array is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/arrays/list/array.rs b/vortex-array/src/arrays/list/array.rs index f516150bcce..e4b6e7efa54 100644 --- a/vortex-array/src/arrays/list/array.rs +++ b/vortex-array/src/arrays/list/array.rs @@ -205,13 +205,13 @@ impl ListData { // Offsets must have at least one element vortex_ensure!( !offsets.is_empty(), - InvalidArgument: "Offsets must have at least one element, [0] for an empty list" + "Offsets must have at least one element, [0] for an empty list" ); // Offsets must be of integer type, and cannot go lower than 0. vortex_ensure!( offsets.dtype().is_int() && !offsets.dtype().is_nullable(), - InvalidArgument: "offsets have invalid type {}", + "offsets have invalid type {}", offsets.dtype() ); @@ -220,9 +220,9 @@ impl ListData { // Offsets must be sorted (but not strictly sorted, zero-length lists are allowed) if let Some(is_sorted) = offsets.statistics().compute_is_sorted(ctx) { - vortex_ensure!(is_sorted, InvalidArgument: "offsets must be sorted"); + vortex_ensure!(is_sorted, "offsets must be sorted"); } else { - vortex_bail!(InvalidArgument: "offsets must report is_sorted statistic"); + vortex_bail!("offsets must report is_sorted statistic"); } // Validate that offsets min is non-negative, and max does not exceed the length of @@ -244,16 +244,16 @@ impl ListData { vortex_ensure!( min >= 0, - InvalidArgument: "offsets minimum {min} outside valid range [0, {max}]" + "offsets minimum {min} outside valid range [0, {max}]" ); vortex_ensure!( max <= P::try_from(elements.len()).unwrap_or_else(|_| vortex_panic!( - Overflow: "Offsets type {} must be able to fit elements length {}", + "Offsets type {} must be able to fit elements length {}",

::PTYPE, elements.len() )), - InvalidArgument: "Max offset {max} is beyond the length of the elements array {}", + "Max offset {max} is beyond the length of the elements array {}", elements.len() ); } @@ -261,7 +261,7 @@ impl ListData { } else { // TODO(aduffy): fallback to slower validation pathway? vortex_bail!( - InvalidArgument: "offsets array with encoding {} must support min_max compute function", + "offsets array with encoding {} must support min_max compute function", offsets.encoding_id() ); }; @@ -271,7 +271,7 @@ impl ListData { vortex_ensure_eq!( validity_len, offsets.len() - 1, - InvalidArgument: "validity length does not match array size", + "validity length does not match array size", ); } @@ -301,7 +301,7 @@ pub trait ListArrayExt: ListArraySlotsExt { fn offset_at(&self, index: usize, ctx: &mut ExecutionCtx) -> VortexResult { vortex_ensure!( index <= self.len(), - OutOfBounds: "Index {index} out of bounds 0..={}", + "Index {index} out of bounds 0..={}", self.len() ); @@ -314,9 +314,7 @@ pub trait ListArrayExt: ListArraySlotsExt { .execute_scalar(index, ctx)? .as_primitive() .as_::() - .ok_or_else( - || vortex_error::vortex_err!(Overflow: "offset value does not fit in usize"), - ) + .ok_or_else(|| vortex_error::vortex_err!("offset value does not fit in usize")) } } diff --git a/vortex-array/src/arrays/list/compute/filter.rs b/vortex-array/src/arrays/list/compute/filter.rs index 087c343140c..95f9fd57993 100644 --- a/vortex-array/src/arrays/list/compute/filter.rs +++ b/vortex-array/src/arrays/list/compute/filter.rs @@ -219,7 +219,7 @@ mod tests { #[test] fn element_mask_excludes_unselected_prefix_and_suffix() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [2]) else { - vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") + vortex_bail!("a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20010, 40010, 60010, 80010, 100010]; @@ -236,7 +236,7 @@ mod tests { #[test] fn element_mask_retains_gaps_between_selected_lists() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [1, 3]) else { - vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") + vortex_bail!("a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20010, 40010, 60010, 80010, 100010]; @@ -257,7 +257,7 @@ mod tests { #[test] fn element_range_preserves_complete_range_for_short_lists() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [2]) else { - vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") + vortex_bail!("a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20, 30, 40, 50, 60]; @@ -275,7 +275,7 @@ mod tests { #[test] fn element_range_requires_minimum_savings() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(2, [0]) else { - vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") + vortex_bail!("a partially selective mask uses Mask::Values") }; let offsets = [0u32, 512, 1024]; @@ -289,7 +289,7 @@ mod tests { #[test] fn element_range_requires_sufficient_savings_ratio() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_slices(100, vec![(0, 96)]) else { - vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") + vortex_bail!("a partially selective mask uses Mask::Values") }; let offsets = (0..=100).map(|index| index * 1000).collect::>(); @@ -303,7 +303,7 @@ mod tests { #[test] fn element_range_crops_at_sufficient_savings_ratio() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_slices(100, vec![(0, 95)]) else { - vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") + vortex_bail!("a partially selective mask uses Mask::Values") }; let offsets = (0..=100).map(|index| index * 1000).collect::>(); @@ -317,7 +317,7 @@ mod tests { #[test] fn element_mask_preserves_complete_range_for_edge_spanning_selection() -> VortexResult<()> { let Mask::Values(selection) = Mask::from_indices(5, [0, 4]) else { - vortex_bail!(AssertionFailed: "a partially selective mask uses Mask::Values") + vortex_bail!("a partially selective mask uses Mask::Values") }; let offsets = [10u32, 20010, 40010, 60010, 80010, 100010]; diff --git a/vortex-array/src/arrays/list/compute/take.rs b/vortex-array/src/arrays/list/compute/take.rs index aff159c153e..591e1cf638d 100644 --- a/vortex-array/src/arrays/list/compute/take.rs +++ b/vortex-array/src/arrays/list/compute/take.rs @@ -93,7 +93,7 @@ fn take_with_piecewise_elements::with_capacity(offsets_capacity); let mut element_starts = BufferMut::::with_capacity(indices.len()); let mut element_lengths = BufferMut::::with_capacity(indices.len()); @@ -119,7 +119,7 @@ fn take_with_piecewise_elements(current_offset)); element_starts.push(start as u64); element_lengths.push(length as u64); @@ -324,13 +324,14 @@ where S: UnsignedPType, Offset: UnsignedPType, { - let computed_len = starts.len().checked_mul(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + let computed_len = starts + .len() + .checked_mul(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; vortex_ensure_eq!( computed_len, output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); let all_valid = data_validity.all_true(); let total_elements = if all_valid { @@ -389,14 +390,14 @@ where let mut computed_len = 0usize; for &length in lengths { let length: usize = length.as_(); - computed_len = computed_len.checked_add(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + computed_len = computed_len + .checked_add(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; } vortex_ensure_eq!( computed_len, output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); let all_valid = data_validity.all_true(); let total_elements = if all_valid { @@ -471,7 +472,7 @@ where let element_end: usize = offset_range[length].as_(); total = total .checked_add(element_end - element_start) - .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; } Ok(total) } @@ -496,7 +497,7 @@ where let additional = valid_piece_elements_len(offsets, data_validity, start, length)?; total = total .checked_add(additional) - .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; } Ok(total) } @@ -520,7 +521,7 @@ where let element_end: usize = offset_range[length].as_(); total = total .checked_add(element_end - element_start) - .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; } Ok(total) } @@ -543,7 +544,7 @@ where let additional = valid_piece_elements_len(offsets, data_validity, start, length)?; total = total .checked_add(additional) - .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; } Ok(total) } @@ -567,7 +568,7 @@ where let element_end: usize = window[1].as_(); total = total .checked_add(element_end - element_start) - .ok_or_else(|| vortex_err!(Overflow: "List take output elements length overflow"))?; + .ok_or_else(|| vortex_err!("List take output elements length overflow"))?; } Ok(total) } @@ -587,7 +588,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; let mut new_offsets = BufferMut::::with_capacity(offsets_capacity); let mut element_starts = BufferMut::::with_capacity(starts.len()); let mut element_lengths = BufferMut::::with_capacity(starts.len()); @@ -650,7 +651,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; let mut gather = ValidPieceGather { new_offsets: BufferMut::::with_capacity(offsets_capacity), element_starts: BufferMut::::with_capacity(output_len), @@ -703,7 +704,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; let mut new_offsets = BufferMut::::with_capacity(offsets_capacity); let mut element_starts = BufferMut::::with_capacity(starts.len()); let mut element_lengths = BufferMut::::with_capacity(lengths.len()); @@ -768,7 +769,7 @@ where { let offsets_capacity = output_len .checked_add(1) - .ok_or_else(|| vortex_err!(Overflow: "List take offsets length overflow"))?; + .ok_or_else(|| vortex_err!("List take offsets length overflow"))?; let mut gather = ValidPieceGather { new_offsets: BufferMut::::with_capacity(offsets_capacity), element_starts: BufferMut::::with_capacity(output_len), diff --git a/vortex-array/src/arrays/list/vtable/mod.rs b/vortex-array/src/arrays/list/vtable/mod.rs index fbe91491dae..d04dd4bca07 100644 --- a/vortex-array/src/arrays/list/vtable/mod.rs +++ b/vortex-array/src/arrays/list/vtable/mod.rs @@ -78,11 +78,11 @@ impl VTable for List { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ListArray buffer index {idx} out of bounds") + vortex_panic!("ListArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "ListArray buffer_name index {idx} out of bounds") + vortex_panic!("ListArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -121,7 +121,7 @@ impl VTable for List { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), ListSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), ListSlots::COUNT); let elements = slots[ListSlots::ELEMENTS] .as_ref() .vortex_expect("ListArray elements slot"); @@ -131,14 +131,14 @@ impl VTable for List { vortex_ensure_eq!( offsets.len().saturating_sub(1), len, - InvalidArgument: "ListArray length does not match outer length", + "ListArray length does not match outer length", ); let actual_dtype = DType::List(Arc::new(elements.dtype().clone()), dtype.nullability()); vortex_ensure_eq!( &actual_dtype, dtype, - MismatchedTypes: "ListArray dtype does not match outer dtype", + "ListArray dtype does not match outer dtype", ); Ok(()) @@ -161,11 +161,11 @@ impl VTable for List { let validity = children.get(2, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "Expected 2 or 3 children, got {}", children.len()); + vortex_bail!("Expected 2 or 3 children, got {}", children.len()); }; let DType::List(element_dtype, _) = &dtype else { - vortex_bail!(MismatchedTypes: "Expected List dtype, got {:?}", dtype); + vortex_bail!("Expected List dtype, got {:?}", dtype); }; let elements = children.get( 0, @@ -215,7 +215,7 @@ impl VTable for List { match match_each_list_builder!(&mut *builder, |b| b.append_list_array(array, ctx)) { Some(result) => result, None => vortex_bail!( - MismatchedTypes: "cannot append a List array of dtype {} to a {} builder", + "cannot append a List array of dtype {} to a {} builder", array.dtype(), builder.dtype() ), diff --git a/vortex-array/src/arrays/listview/array.rs b/vortex-array/src/arrays/listview/array.rs index a5db3984e5c..bebd5df30fe 100644 --- a/vortex-array/src/arrays/listview/array.rs +++ b/vortex-array/src/arrays/listview/array.rs @@ -237,12 +237,12 @@ impl ListViewData { // Check that offsets and sizes are integer arrays and non-nullable. vortex_ensure!( offsets.dtype().is_int() && !offsets.dtype().is_nullable(), - MismatchedTypes: "offsets must be non-nullable integer array, got {}", + "offsets must be non-nullable integer array, got {}", offsets.dtype() ); vortex_ensure!( sizes.dtype().is_int() && !sizes.dtype().is_nullable(), - MismatchedTypes: "sizes must be non-nullable integer array, got {}", + "sizes must be non-nullable integer array, got {}", sizes.dtype() ); @@ -250,7 +250,7 @@ impl ListViewData { vortex_ensure_eq!( offsets.len(), sizes.len(), - InvalidArgument: "offsets and sizes must have the same length", + "offsets and sizes must have the same length", ); // If a validity array is present, it must be the same length as the `ListViewArray`. @@ -258,7 +258,7 @@ impl ListViewData { vortex_ensure_eq!( validity_len, offsets.len(), - InvalidArgument: "validity length does not match array size", + "validity length does not match array size", ); } @@ -521,7 +521,7 @@ pub trait ListViewArrayExt: ListViewArraySlotsExt { let n_lists = self.len(); vortex_ensure!( n_lists > 0, - InvalidArgument: "referenced_element_bounds requires a non-empty array" + "referenced_element_bounds requires a non-empty array" ); if self.is_zero_copy_to_list() { @@ -682,33 +682,33 @@ where let offset = offsets_slice[i]; let size = sizes_slice[i]; - vortex_ensure!(offset >= O::zero(), InvalidArgument: "cannot have negative offsets"); - vortex_ensure!(size >= S::zero(), InvalidArgument: "cannot have negative size"); + vortex_ensure!(offset >= O::zero(), "cannot have negative offsets"); + vortex_ensure!(size >= S::zero(), "cannot have negative size"); - let offset_u64 = offset.to_u64().ok_or_else( - || vortex_err!(Overflow: "offset[{i}] = {offset:?} cannot be converted to u64"), - )?; + let offset_u64 = offset + .to_u64() + .ok_or_else(|| vortex_err!("offset[{i}] = {offset:?} cannot be converted to u64"))?; - let size_u64 = size.to_u64().ok_or_else( - || vortex_err!(Overflow: "size[{i}] = {size:?} cannot be converted to u64"), - )?; + let size_u64 = size + .to_u64() + .ok_or_else(|| vortex_err!("size[{i}] = {size:?} cannot be converted to u64"))?; // Check for overflow when adding offset + size. let end = offset_u64.checked_add(size_u64).ok_or_else(|| { - vortex_err!(Overflow: "offset[{i}] ({offset_u64}) + size[{i}] ({size_u64}) would overflow u64") + vortex_err!("offset[{i}] ({offset_u64}) + size[{i}] ({size_u64}) would overflow u64") })?; if offset_u64 == elements_len { vortex_ensure_eq!( size_u64, 0, - InvalidArgument: "views to the end of the elements array (length {elements_len}) must have size 0", + "views to the end of the elements array (length {elements_len}) must have size 0", ); } vortex_ensure!( end <= elements_len, - OutOfBounds: "offset[{i}] + size[{i}] = {offset_u64} + {size_u64} = {end} \ + "offset[{i}] + size[{i}] = {offset_u64} + {size_u64} = {end} \ exceeds elements length {elements_len}", ); } @@ -728,7 +728,7 @@ fn validate_zctl( let offsets_sorted = match_each_integer_ptype!(offsets_primitive.ptype(), |P| { offsets_primitive.as_slice::

().is_sorted() }); - vortex_ensure!(offsets_sorted, InvalidArgument: "offsets must be sorted"); + vortex_ensure!(offsets_sorted, "offsets must be sorted"); // Validate that offset[i] + size[i] <= offset[i+1] for all items // This ensures views are non-overlapping and properly ordered for zero-copy-to-list @@ -746,7 +746,7 @@ fn validate_zctl( // Check that this view starts at or after the previous view ended vortex_ensure!( offset >= max_end, - InvalidArgument: "Zero-copy-to-list requires views to be non-overlapping and ordered: \ + "Zero-copy-to-list requires views to be non-overlapping and ordered: \ view[{}] starts at {} but previous views extend to {}", i, offset, @@ -824,7 +824,7 @@ fn validate_zctl( element_references[first_ref..=last_ref] .iter() .all(|&references| references != 0), - InvalidArgument: "found gap in elements array between first and last referenced elements" + "found gap in elements array between first and last referenced elements" ); } diff --git a/vortex-array/src/arrays/listview/rebuild.rs b/vortex-array/src/arrays/listview/rebuild.rs index 3946724c4fb..0fe73d4f0ad 100644 --- a/vortex-array/src/arrays/listview/rebuild.rs +++ b/vortex-array/src/arrays/listview/rebuild.rs @@ -116,7 +116,7 @@ impl ListViewArray { ListViewRebuildMode::TrimElements => self.rebuild_trim_elements(ctx), ListViewRebuildMode::MakeExact => self.rebuild_make_exact(ctx), ListViewRebuildMode::OverlapCompression => { - vortex_bail!(NotImplemented: "ListViewRebuildMode::OverlapCompression is not implemented") + vortex_bail!("ListViewRebuildMode::OverlapCompression is not implemented") } } } @@ -429,12 +429,12 @@ where let length: usize = size.as_(); start.checked_add(length).ok_or_else(|| { vortex_err!( - Overflow: "ListView rebuild element range overflow for start {start} and length {length}" + "ListView rebuild element range overflow for start {start} and length {length}" ) })?; elements_len = elements_len .checked_add(length) - .ok_or_else(|| vortex_err!(Overflow: "ListView rebuild elements length overflow"))?; + .ok_or_else(|| vortex_err!("ListView rebuild elements length overflow"))?; new_offsets.push(n_elements); new_sizes.push(size); diff --git a/vortex-array/src/arrays/listview/vtable/mod.rs b/vortex-array/src/arrays/listview/vtable/mod.rs index 21cc7431d6f..9337309c796 100644 --- a/vortex-array/src/arrays/listview/vtable/mod.rs +++ b/vortex-array/src/arrays/listview/vtable/mod.rs @@ -90,11 +90,11 @@ impl VTable for ListView { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ListViewArray buffer index {idx} out of bounds") + vortex_panic!("ListViewArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "ListViewArray buffer_name index {idx} out of bounds") + vortex_panic!("ListViewArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -126,7 +126,7 @@ impl VTable for ListView { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), ListViewSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), ListViewSlots::COUNT); let elements = slots[ListViewSlots::ELEMENTS] .as_ref() .vortex_expect("ListViewArray elements slot"); @@ -138,7 +138,7 @@ impl VTable for ListView { .vortex_expect("ListViewArray sizes slot"); vortex_ensure!( offsets.len() == len && sizes.len() == len, - InvalidArgument: "ListViewArray length {} does not match outer length {}", + "ListViewArray length {} does not match outer length {}", offsets.len(), len ); @@ -147,7 +147,7 @@ impl VTable for ListView { vortex_ensure_eq!( &actual_dtype, dtype, - MismatchedTypes: "ListViewArray dtype does not match outer dtype", + "ListViewArray dtype does not match outer dtype", ); Ok(()) @@ -166,11 +166,11 @@ impl VTable for ListView { let metadata = ListViewMetadata::decode(metadata)?; vortex_ensure!( buffers.is_empty(), - InvalidArgument: "`ListViewArray::build` expects no buffers" + "`ListViewArray::build` expects no buffers" ); let DType::List(element_dtype, _) = dtype else { - vortex_bail!(MismatchedTypes: "Expected List dtype, got {:?}", dtype); + vortex_bail!("Expected List dtype, got {:?}", dtype); }; let validity = if children.len() == 3 { @@ -180,7 +180,7 @@ impl VTable for ListView { Validity::Array(validity) } else { vortex_bail!( - InvalidArgument: "`ListViewArray::build` expects 3 or 4 children, got {}", + "`ListViewArray::build` expects 3 or 4 children, got {}", children.len() ); }; @@ -242,7 +242,7 @@ impl VTable for ListView { match match_each_list_builder!(&mut *builder, |b| b.append_listview_array(array, ctx)) { Some(result) => result, None => vortex_bail!( - MismatchedTypes: "cannot append a ListView array of dtype {} to a {} builder", + "cannot append a ListView array of dtype {} to a {} builder", array.dtype(), builder.dtype() ), diff --git a/vortex-array/src/arrays/map/array.rs b/vortex-array/src/arrays/map/array.rs index 730958d4af3..c60b6521198 100644 --- a/vortex-array/src/arrays/map/array.rs +++ b/vortex-array/src/arrays/map/array.rs @@ -173,20 +173,20 @@ pub(super) fn validate_entries( ) -> VortexResult<()> { vortex_ensure!( entries.is::(), - MismatchedTypes: "MapArray entries must use vortex.listview encoding, got {}", + "MapArray entries must use vortex.listview encoding, got {}", entries.encoding_id() ); vortex_ensure_eq!( entries.len(), len, - InvalidArgument: "MapArray entries length does not match outer length", + "MapArray entries length does not match outer length", ); let expected_dtype = expected_entries_dtype(map_dtype, nullability); vortex_ensure_eq!( entries.dtype(), &expected_dtype, - MismatchedTypes: "MapArray entries dtype does not match expected dtype", + "MapArray entries dtype does not match expected dtype", ); Ok(()) diff --git a/vortex-array/src/arrays/map/compute/cast.rs b/vortex-array/src/arrays/map/compute/cast.rs index c14bb02cc6b..bfbab6e17e9 100644 --- a/vortex-array/src/arrays/map/compute/cast.rs +++ b/vortex-array/src/arrays/map/compute/cast.rs @@ -29,7 +29,7 @@ fn prepare_map_cast_target( if target_map_dtype.keys_sorted() && !array.keys_sorted() { vortex_bail!( - MismatchedTypes: "Cannot cast {} to {dtype}: source does not assert sorted map keys", + "Cannot cast {} to {dtype}: source does not assert sorted map keys", array.dtype() ); } diff --git a/vortex-array/src/arrays/map/compute/mod.rs b/vortex-array/src/arrays/map/compute/mod.rs index be2a49eac24..ea0be66f0e4 100644 --- a/vortex-array/src/arrays/map/compute/mod.rs +++ b/vortex-array/src/arrays/map/compute/mod.rs @@ -22,7 +22,7 @@ use crate::dtype::MapDType; fn rebuild_map_from_array(map_dtype: MapDType, entries: ArrayRef) -> VortexResult { let map_entries = entries.try_downcast::().map_err(|arr| { vortex_err!( - MismatchedTypes: "Map entries operation expected vortex.listview/ListView, got {}", + "Map entries operation expected vortex.listview/ListView, got {}", arr.encoding_id() ) })?; diff --git a/vortex-array/src/arrays/map/vtable/mod.rs b/vortex-array/src/arrays/map/vtable/mod.rs index 7a76a7dbb68..17980991d3a 100644 --- a/vortex-array/src/arrays/map/vtable/mod.rs +++ b/vortex-array/src/arrays/map/vtable/mod.rs @@ -67,10 +67,10 @@ impl VTable for Map { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), MapSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), MapSlots::COUNT); let DType::Map(map_dtype, nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected map dtype, got {dtype}"); + vortex_bail!("Expected map dtype, got {dtype}"); }; let slots = MapSlotsView::from_slots(slots); validate_entries(map_dtype, *nullability, len, slots.entries) @@ -81,7 +81,7 @@ impl VTable for Map { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "MapArray buffer index {idx} out of bounds") + vortex_panic!("MapArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -114,23 +114,23 @@ impl VTable for Map { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "MapArray expects empty metadata, got {} bytes", + "MapArray expects empty metadata, got {} bytes", metadata.len() ); } - vortex_ensure!(buffers.is_empty(), InvalidArgument: "MapArray expects no buffers"); + vortex_ensure!(buffers.is_empty(), "MapArray expects no buffers"); let DType::Map(map_dtype, nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected map dtype, got {dtype}"); + vortex_bail!("Expected map dtype, got {dtype}"); }; - vortex_ensure_eq!(children.len(), MapSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(children.len(), MapSlots::COUNT); let expected_entries_dtype = DType::List(std::sync::Arc::new(map_dtype.entries_dtype()), *nullability); let entries = children.get(MapSlots::ENTRIES, &expected_entries_dtype, len)?; vortex_ensure!( entries.is::(), - MismatchedTypes: "MapArray entries must use vortex.listview encoding, got {}", + "MapArray entries must use vortex.listview encoding, got {}", entries.encoding_id() ); @@ -160,7 +160,7 @@ impl VTable for Map { match match_each_map_builder!(&mut *builder, |b| b.append_map_array(array, ctx)) { Some(result) => result, None => vortex_bail!( - MismatchedTypes: "cannot append a Map array of dtype {} to a {} builder", + "cannot append a Map array of dtype {} to a {} builder", array.dtype(), builder.dtype() ), diff --git a/vortex-array/src/arrays/masked/array.rs b/vortex-array/src/arrays/masked/array.rs index 3987327d589..f1243c8f1a9 100644 --- a/vortex-array/src/arrays/masked/array.rs +++ b/vortex-array/src/arrays/masked/array.rs @@ -55,17 +55,17 @@ impl MaskedData { validity: Validity, ) -> VortexResult { if matches!(validity, Validity::NonNullable) { - vortex_bail!(InvalidArgument: "MaskedArray must have nullable validity, got {validity:?}") + vortex_bail!("MaskedArray must have nullable validity, got {validity:?}") } if !child_all_valid { - vortex_bail!(InvalidArgument: "MaskedArray children must not have nulls"); + vortex_bail!("MaskedArray children must not have nulls"); } if let Some(validity_len) = validity.maybe_len() && validity_len != child_len { - vortex_bail!(InvalidArgument: "Validity must be the same length as a MaskedArray's child"); + vortex_bail!("Validity must be the same length as a MaskedArray's child"); } // MaskedArray's nullability is determined solely by its validity, not the child's dtype. diff --git a/vortex-array/src/arrays/masked/vtable/mod.rs b/vortex-array/src/arrays/masked/vtable/mod.rs index d22057f7429..507223a94a0 100644 --- a/vortex-array/src/arrays/masked/vtable/mod.rs +++ b/vortex-array/src/arrays/masked/vtable/mod.rs @@ -81,16 +81,16 @@ impl VTable for Masked { ) -> VortexResult<()> { vortex_ensure!( slots[MaskedSlots::CHILD].is_some(), - InvalidArgument: "MaskedArray child slot must be present" + "MaskedArray child slot must be present" ); let child = slots[MaskedSlots::CHILD] .as_ref() .vortex_expect("validated child slot"); - vortex_ensure_eq!(child.len(), len, InvalidArgument: "MaskedArray child length mismatch"); + vortex_ensure_eq!(child.len(), len, "MaskedArray child length mismatch"); vortex_ensure_eq!( child.dtype().as_nullable(), *dtype, - MismatchedTypes: "MaskedArray dtype does not match child and validity", + "MaskedArray dtype does not match child and validity", ); Ok(()) } @@ -100,7 +100,7 @@ impl VTable for Masked { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "MaskedArray has no buffers") + vortex_panic!("MaskedArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -134,17 +134,17 @@ impl VTable for Masked { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "MaskedArray expects empty metadata, got {} bytes", + "MaskedArray expects empty metadata, got {} bytes", metadata.len() ); } if !buffers.is_empty() { - vortex_bail!(MismatchedTypes: "Expected 0 buffer, got {}", buffers.len()); + vortex_bail!("Expected 0 buffer, got {}", buffers.len()); } vortex_ensure!( children.len() == 1 || children.len() == 2, - InvalidArgument: "`MaskedArray::build` expects 1 or 2 children, got {}", + "`MaskedArray::build` expects 1 or 2 children, got {}", children.len() ); diff --git a/vortex-array/src/arrays/masked/vtable/operations.rs b/vortex-array/src/arrays/masked/vtable/operations.rs index 4450380579d..6215bdcc7f2 100644 --- a/vortex-array/src/arrays/masked/vtable/operations.rs +++ b/vortex-array/src/arrays/masked/vtable/operations.rs @@ -25,7 +25,7 @@ impl OperationsVTable for Masked { } Ok(state .slot(MaskedSlots::CHILD)? - .ok_or_else(|| vortex_err!(InvalidArgument: "Masked child slot is missing"))? + .ok_or_else(|| vortex_err!("Masked child slot is missing"))? .execute_scalar(index, ctx)? .into_nullable()) } diff --git a/vortex-array/src/arrays/null/compute/cast.rs b/vortex-array/src/arrays/null/compute/cast.rs index 33827f8f639..be9da91131e 100644 --- a/vortex-array/src/arrays/null/compute/cast.rs +++ b/vortex-array/src/arrays/null/compute/cast.rs @@ -16,7 +16,7 @@ use crate::scalar_fn::fns::cast::CastReduce; impl CastReduce for Null { fn cast(array: ArrayView<'_, Null>, dtype: &DType) -> VortexResult> { if !dtype.is_nullable() { - vortex_bail!(MismatchedTypes: "Cannot cast Null to {}", dtype); + vortex_bail!("Cannot cast Null to {}", dtype); } if dtype == &DType::Null { return Ok(Some(array.array().clone())); diff --git a/vortex-array/src/arrays/null/compute/take.rs b/vortex-array/src/arrays/null/compute/take.rs index 9839c8c3193..d006e168c0b 100644 --- a/vortex-array/src/arrays/null/compute/take.rs +++ b/vortex-array/src/arrays/null/compute/take.rs @@ -27,7 +27,12 @@ impl TakeExecute for Null { match_each_integer_ptype!(indices.ptype(), |T| { for index in indices.as_slice::() { if (*index as usize) >= array.len() { - vortex_bail!(OutOfBounds: "index {} out of bounds from {} to {}", *index as usize, 0, array.len()); + vortex_bail!( + "index {} out of bounds from {} to {}", + *index as usize, + 0, + array.len() + ); } } }); diff --git a/vortex-array/src/arrays/null/mod.rs b/vortex-array/src/arrays/null/mod.rs index aeff3cf1499..6c0160c4e15 100644 --- a/vortex-array/src/arrays/null/mod.rs +++ b/vortex-array/src/arrays/null/mod.rs @@ -64,7 +64,7 @@ impl VTable for Null { _len: usize, _slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(*dtype, DType::Null, MismatchedTypes: "NullArray dtype must be DType::Null"); + vortex_ensure_eq!(*dtype, DType::Null, "NullArray dtype must be DType::Null"); Ok(()) } @@ -73,7 +73,7 @@ impl VTable for Null { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "NullArray buffer index {idx} out of bounds") + vortex_panic!("NullArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -89,7 +89,7 @@ impl VTable for Null { } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { - vortex_panic!(OutOfBounds: "NullArray slot_name index {idx} out of bounds") + vortex_panic!("NullArray slot_name index {idx} out of bounds") } fn serialize( @@ -111,7 +111,7 @@ impl VTable for Null { ) -> VortexResult> { vortex_ensure!( metadata.is_empty(), - Serde: "NullArray expects empty metadata, got {} bytes", + "NullArray expects empty metadata, got {} bytes", metadata.len() ); Ok(ArrayParts::new( @@ -141,7 +141,7 @@ impl VTable for Null { _ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for Null requires a NullBuilder"); + vortex_bail!("append_to_builder for Null requires a NullBuilder"); }; builder.append_nulls(array.len()); Ok(()) diff --git a/vortex-array/src/arrays/patched/array.rs b/vortex-array/src/arrays/patched/array.rs index 17ddecfda62..48e679efb86 100644 --- a/vortex-array/src/arrays/patched/array.rs +++ b/vortex-array/src/arrays/patched/array.rs @@ -82,17 +82,17 @@ impl PatchedData { vortex_ensure_eq!( slots.inner.dtype(), dtype, - MismatchedTypes: "PatchedArray base dtype does not match outer dtype", + "PatchedArray base dtype does not match outer dtype", ); vortex_ensure_eq!( slots.inner.len(), len, - InvalidArgument: "PatchedArray base len does not match outer len", + "PatchedArray base len does not match outer len", ); vortex_ensure_eq!( slots.patch_indices.len(), slots.patch_values.len(), - InvalidArgument: "PatchedArray patch indices len does not match patch values len", + "PatchedArray patch indices len does not match patch values len", ); Ok(()) } @@ -129,12 +129,12 @@ pub trait PatchedArrayExt: PatchedArraySlotsExt { let start = start .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(Overflow: "could not cast lane_offset to usize"))?; + .ok_or_else(|| vortex_err!("could not cast lane_offset to usize"))?; let stop = stop .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(Overflow: "could not cast lane_offset to usize"))?; + .ok_or_else(|| vortex_err!("could not cast lane_offset to usize"))?; Ok(start..stop) } @@ -180,22 +180,22 @@ impl Patched { ) -> VortexResult> { vortex_ensure!( inner.dtype().eq_with_nullability_superset(patches.dtype()), - MismatchedTypes: "array DType must match patches DType" + "array DType must match patches DType" ); vortex_ensure!( inner.dtype().is_primitive(), - NotImplemented: "Creating PatchedArray from Patches only supported for primitive arrays" + "Creating PatchedArray from Patches only supported for primitive arrays" ); vortex_ensure!( patches.num_patches() <= u32::MAX as usize, - Overflow: "PatchedArray does not support > u32::MAX patch values" + "PatchedArray does not support > u32::MAX patch values" ); vortex_ensure!( patches.values().all_valid(ctx)?, - InvalidArgument: "PatchedArray cannot be built from Patches with nulls" + "PatchedArray cannot be built from Patches with nulls" ); let values_ptype = patches.dtype().as_ptype(); diff --git a/vortex-array/src/arrays/patched/compute/compare.rs b/vortex-array/src/arrays/patched/compute/compare.rs index e66ced14f00..800783b11c5 100644 --- a/vortex-array/src/arrays/patched/compute/compare.rs +++ b/vortex-array/src/arrays/patched/compute/compare.rs @@ -273,7 +273,7 @@ mod tests { let lhs = Patched::from_array_and_patches(lhs, &patches, &mut ctx)? .into_array() .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "expected patched array"))?; + .map_err(|_| vortex_err!("expected patched array"))?; let rhs = ConstantArray::new(subnormal, 512).into_array(); @@ -283,7 +283,7 @@ mod tests { CompareOperator::Eq, &mut ctx, )? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected compare result"))?; + .ok_or_else(|| vortex_err!("expected compare result"))?; let expected = BoolArray::from_indices(512, [510], Validity::NonNullable).into_array(); @@ -309,7 +309,7 @@ mod tests { let lhs = Patched::from_array_and_patches(lhs, &patches, &mut ctx)? .into_array() .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "expected patched array"))?; + .map_err(|_| vortex_err!("expected patched array"))?; let rhs = ConstantArray::new(0.0f32, 10).into_array(); @@ -319,7 +319,7 @@ mod tests { CompareOperator::Eq, &mut ctx, )? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected compare result"))?; + .ok_or_else(|| vortex_err!("expected compare result"))?; let expected = BoolArray::from_indices(10, [7], Validity::NonNullable).into_array(); diff --git a/vortex-array/src/arrays/patched/vtable/mod.rs b/vortex-array/src/arrays/patched/vtable/mod.rs index e4392ec8c3f..01c71d52997 100644 --- a/vortex-array/src/arrays/patched/vtable/mod.rs +++ b/vortex-array/src/arrays/patched/vtable/mod.rs @@ -123,11 +123,11 @@ impl VTable for Patched { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "invalid buffer index for PatchedArray: {idx}"); + vortex_panic!("invalid buffer index for PatchedArray: {idx}"); } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "invalid buffer index for PatchedArray: {idx}"); + vortex_panic!("invalid buffer index for PatchedArray: {idx}"); } fn with_buffers( diff --git a/vortex-array/src/arrays/piecewise_sequence/mod.rs b/vortex-array/src/arrays/piecewise_sequence/mod.rs index 2cda9884f0f..843fe7a01cc 100644 --- a/vortex-array/src/arrays/piecewise_sequence/mod.rs +++ b/vortex-array/src/arrays/piecewise_sequence/mod.rs @@ -48,12 +48,12 @@ pub(crate) fn check_index_arrays( vortex_ensure_eq!( starts.len(), lengths.len(), - InvalidArgument: "PiecewiseSequenceArray starts length does not match lengths length", + "PiecewiseSequenceArray starts length does not match lengths length", ); vortex_ensure_eq!( starts.len(), multipliers.len(), - InvalidArgument: "PiecewiseSequenceArray starts length does not match multipliers length", + "PiecewiseSequenceArray starts length does not match multipliers length", ); Ok(()) } @@ -110,12 +110,12 @@ pub(crate) fn constant_unsigned_usize(array: &ConstantArray) -> usize { fn check_index_array(name: &str, array: &ArrayRef) -> VortexResult<()> { vortex_ensure!( array.dtype().is_unsigned_int(), - MismatchedTypes: "PiecewiseSequenceArray {name} must have unsigned integer dtype, got {}", + "PiecewiseSequenceArray {name} must have unsigned integer dtype, got {}", array.dtype() ); vortex_ensure!( !array.dtype().is_nullable(), - InvalidArgument: "PiecewiseSequenceArray {name} must be non-nullable, got {}", + "PiecewiseSequenceArray {name} must be non-nullable, got {}", array.dtype() ); Ok(()) @@ -144,23 +144,23 @@ where let multiplier: usize = multiplier.as_(); if length != 0 { let last_offset = length - 1; - let last_delta = last_offset.checked_mul(multiplier).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), - )?; - start.checked_add(last_delta).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), - )?; + let last_delta = last_offset + .checked_mul(multiplier) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; + start + .checked_add(last_delta) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; } - computed_len = computed_len.checked_add(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + computed_len = computed_len + .checked_add(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; values.extend((0..length).map(|offset| (start + offset * multiplier) as u64)); } if computed_len != output_len { vortex_bail!( - AssertionFailed: "PiecewiseSequenceArray expanded length {computed_len} does not match declared length {output_len}" + "PiecewiseSequenceArray expanded length {computed_len} does not match declared length {output_len}" ); } Ok(values) diff --git a/vortex-array/src/arrays/piecewise_sequence/vtable.rs b/vortex-array/src/arrays/piecewise_sequence/vtable.rs index 98c0c2da8f1..db5b33a1081 100644 --- a/vortex-array/src/arrays/piecewise_sequence/vtable.rs +++ b/vortex-array/src/arrays/piecewise_sequence/vtable.rs @@ -64,23 +64,19 @@ impl VTable for PiecewiseSequence { vortex_ensure_eq!( dtype, &DType::from(PType::U64), - MismatchedTypes: "PiecewiseSequenceArray dtype must be u64", + "PiecewiseSequenceArray dtype must be u64", ); - vortex_ensure_eq!( - slots.len(), - PiecewiseSequenceSlots::NAMES.len(), - InvalidArgument - ); - let starts = slots[PiecewiseSequenceSlots::STARTS].as_ref().ok_or_else( - || vortex_err!(InvalidArgument: "PiecewiseSequenceArray starts slot must be present"), - )?; - let lengths = slots[PiecewiseSequenceSlots::LENGTHS].as_ref().ok_or_else( - || vortex_err!(InvalidArgument: "PiecewiseSequenceArray lengths slot must be present"), - )?; + vortex_ensure_eq!(slots.len(), PiecewiseSequenceSlots::NAMES.len()); + let starts = slots[PiecewiseSequenceSlots::STARTS] + .as_ref() + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray starts slot must be present"))?; + let lengths = slots[PiecewiseSequenceSlots::LENGTHS] + .as_ref() + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray lengths slot must be present"))?; let multipliers = slots[PiecewiseSequenceSlots::MULTIPLIERS] .as_ref() .ok_or_else(|| { - vortex_err!(InvalidArgument: "PiecewiseSequenceArray multipliers slot must be present") + vortex_err!("PiecewiseSequenceArray multipliers slot must be present") })?; check_index_arrays(starts, lengths, multipliers) } @@ -90,7 +86,7 @@ impl VTable for PiecewiseSequence { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "PiecewiseSequenceArray has no buffers") + vortex_panic!("PiecewiseSequenceArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -125,7 +121,7 @@ impl VTable for PiecewiseSequence { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "PiecewiseSequenceArray is not serializable") + vortex_bail!("PiecewiseSequenceArray is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { @@ -193,15 +189,15 @@ where if remaining < length { let start: usize = start.as_(); let multiplier: usize = multiplier.as_(); - let offset = remaining.checked_mul(multiplier).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), - )?; - let value = start.checked_add(offset).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray range overflows usize"), - )?; + let offset = remaining + .checked_mul(multiplier) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; + let value = start + .checked_add(offset) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray range overflows usize"))?; return Ok(value as u64); } remaining -= length; } - vortex_bail!(OutOfBounds: "PiecewiseSequenceArray index {index} out of bounds") + vortex_bail!("PiecewiseSequenceArray index {index} out of bounds") } diff --git a/vortex-array/src/arrays/primitive/array/cast.rs b/vortex-array/src/arrays/primitive/array/cast.rs index e5a1c68dc66..6733c0e4ebd 100644 --- a/vortex-array/src/arrays/primitive/array/cast.rs +++ b/vortex-array/src/arrays/primitive/array/cast.rs @@ -18,7 +18,7 @@ impl PrimitiveData { pub fn as_slice(&self) -> &[T] { if T::PTYPE != self.ptype() { vortex_panic!( - MismatchedTypes: "Attempted to get slice of type {} from array of type {}", + "Attempted to get slice of type {} from array of type {}", T::PTYPE, self.ptype() ) diff --git a/vortex-array/src/arrays/primitive/array/conversion.rs b/vortex-array/src/arrays/primitive/array/conversion.rs index 8a3161e173d..444b79dfe41 100644 --- a/vortex-array/src/arrays/primitive/array/conversion.rs +++ b/vortex-array/src/arrays/primitive/array/conversion.rs @@ -43,7 +43,7 @@ impl PrimitiveArray { pub fn to_buffer(&self) -> Buffer { if T::PTYPE != self.ptype() { vortex_panic!( - MismatchedTypes: "Attempted to get buffer of type {} from array of type {}", + "Attempted to get buffer of type {} from array of type {}", T::PTYPE, self.ptype() ) diff --git a/vortex-array/src/arrays/primitive/array/mod.rs b/vortex-array/src/arrays/primitive/array/mod.rs index c2d575594d7..28cee4d21d6 100644 --- a/vortex-array/src/arrays/primitive/array/mod.rs +++ b/vortex-array/src/arrays/primitive/array/mod.rs @@ -327,7 +327,6 @@ impl PrimitiveData { && buffer.len() != len { return Err(vortex_err!( - InvalidArgument: "Buffer and validity length mismatch: buffer={}, validity={}", buffer.len(), len @@ -531,7 +530,7 @@ impl PrimitiveData { pub fn to_buffer(&self) -> Buffer { if T::PTYPE != self.ptype() { vortex_panic!( - MismatchedTypes: "Attempted to get buffer of type {} from array of type {}", + "Attempted to get buffer of type {} from array of type {}", T::PTYPE, self.ptype() ) @@ -543,7 +542,7 @@ impl PrimitiveData { pub fn into_buffer(self) -> Buffer { if T::PTYPE != self.ptype() { vortex_panic!( - MismatchedTypes: "Attempted to get buffer of type {} from array of type {}", + "Attempted to get buffer of type {} from array of type {}", T::PTYPE, self.ptype() ) @@ -565,7 +564,7 @@ impl PrimitiveData { pub fn try_into_buffer_mut(self) -> Result, Buffer> { if T::PTYPE != self.ptype() { vortex_panic!( - MismatchedTypes: "Attempted to get buffer_mut of type {} from array of type {}", + "Attempted to get buffer_mut of type {} from array of type {}", T::PTYPE, self.ptype() ) diff --git a/vortex-array/src/arrays/primitive/compute/cast.rs b/vortex-array/src/arrays/primitive/compute/cast.rs index 5ecd1ba88f6..022d2216d2c 100644 --- a/vortex-array/src/arrays/primitive/compute/cast.rs +++ b/vortex-array/src/arrays/primitive/compute/cast.rs @@ -107,8 +107,9 @@ impl CastKernel for Primitive { if same_rep { if !values_fit_in(array, new_ptype, ctx, true) { vortex_bail!( - Overflow: "Cannot cast {} to {} — values exceed target range", - src_ptype, new_ptype, + "Cannot cast {} to {} — values exceed target range", + src_ptype, + new_ptype, ); } return Ok(Some(reinterpret(array, new_ptype, new_validity))); @@ -132,8 +133,9 @@ fn cast_to_decimal( ) -> VortexResult { if !array.ptype().is_int() { vortex_bail!( - MismatchedTypes: "Cannot cast floating primitive {} to decimal {}", - array.ptype(), decimal_dtype + "Cannot cast floating primitive {} to decimal {}", + array.ptype(), + decimal_dtype ); } @@ -399,7 +401,7 @@ where #[cold] #[inline(never)] fn scale_factor_error(scale: i8) -> VortexError { - vortex_err!(Overflow: "Cannot create decimal scale factor for scale {scale}") + vortex_err!("Cannot create decimal scale factor for scale {scale}") } fn decimal_value_fits_precision( @@ -450,7 +452,7 @@ where { let Some(value) = ::from(value) else { return vortex_err!( - Overflow: "primitive value cannot be represented while casting to {}", + "primitive value cannot be represented while casting to {}", decimal_dtype ); }; @@ -465,7 +467,7 @@ where "primitive-to-decimal fast path rejected a value that the scalar cast accepts" ); vortex_err!( - Overflow: "primitive value cannot be represented while casting to {}", + "primitive value cannot be represented while casting to {}", decimal_dtype ) } @@ -484,8 +486,9 @@ where { let overflow = || { vortex_err!( - Overflow: "Cannot cast {} to {} — value exceeds target range", - F::PTYPE, T::PTYPE, + "Cannot cast {} to {} — value exceeds target range", + F::PTYPE, + T::PTYPE, ) }; @@ -664,7 +667,6 @@ mod test { use rstest::rstest; use vortex_buffer::BitBuffer; use vortex_buffer::buffer; - use vortex_error::VortexErrorKind; use vortex_error::VortexResult; use vortex_mask::Mask; use vortex_session::VortexSession; @@ -1093,7 +1095,6 @@ mod test { .map(|c| c.into_array()) }) .unwrap_err(); - assert_eq!(error.kind(), VortexErrorKind::Overflow); assert!(error.to_string().contains("values exceed target range")); } @@ -1109,7 +1110,6 @@ mod test { }) .unwrap_err(); - assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); assert!( err.to_string() .contains("Cannot cast array with invalid values to non-nullable type.") @@ -1173,7 +1173,10 @@ mod test { .map(|c| c.into_array()) }) .unwrap_err(); - assert_eq!(err.kind(), VortexErrorKind::Overflow); + assert!( + err.to_string().contains("values exceed target range"), + "{err}" + ); } /// All-null array cast between same-width types should succeed without diff --git a/vortex-array/src/arrays/primitive/compute/zip.rs b/vortex-array/src/arrays/primitive/compute/zip.rs index b6d574aacd9..a653f01099e 100644 --- a/vortex-array/src/arrays/primitive/compute/zip.rs +++ b/vortex-array/src/arrays/primitive/compute/zip.rs @@ -40,7 +40,7 @@ impl ZipKernel for Primitive { if if_true.ptype() != if_false.ptype() { vortex_bail!( - InvalidArgument: "zip requires if_true and if_false to share a primitive type, got {} and {}", + "zip requires if_true and if_false to share a primitive type, got {} and {}", if_true.ptype(), if_false.ptype() ); diff --git a/vortex-array/src/arrays/primitive/vtable/mod.rs b/vortex-array/src/arrays/primitive/vtable/mod.rs index 071d8552283..df4006626a2 100644 --- a/vortex-array/src/arrays/primitive/vtable/mod.rs +++ b/vortex-array/src/arrays/primitive/vtable/mod.rs @@ -112,12 +112,12 @@ impl VTable for Primitive { slots: &[Option], ) -> VortexResult<()> { let DType::Primitive(_, nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected primitive dtype, got {dtype:?}"); + vortex_bail!("Expected primitive dtype, got {dtype:?}"); }; vortex_ensure_eq!( data.len(), len, - InvalidArgument: "PrimitiveArray length does not match outer length", + "PrimitiveArray length does not match outer length", ); let validity = crate::array::child_to_validity(slots[PrimitiveSlots::VALIDITY].as_ref(), *nullability); @@ -125,7 +125,7 @@ impl VTable for Primitive { vortex_ensure_eq!( validity_len, len, - InvalidArgument: "PrimitiveArray validity len does not match outer length", + "PrimitiveArray validity len does not match outer length", ); } @@ -144,7 +144,7 @@ impl VTable for Primitive { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "PrimitiveArray expects empty metadata, got {} bytes", + "PrimitiveArray expects empty metadata, got {} bytes", metadata.len() ); } @@ -156,12 +156,12 @@ impl VTable for Primitive { vortex_ensure!( buffer.is_aligned_to(Alignment::new(ptype.byte_width())), - InvalidArgument: "Misaligned buffer cannot be used to build PrimitiveArray of {ptype}" + "Misaligned buffer cannot be used to build PrimitiveArray of {ptype}" ); if buffer.len() != ptype.byte_width() * len { vortex_bail!( - MismatchedTypes: "Buffer length {} does not match expected length {} for {}, {}", + "Buffer length {} does not match expected length {} for {}, {}", buffer.len(), ptype.byte_width() * len, ptype.byte_width(), @@ -200,7 +200,7 @@ impl VTable for Primitive { } }); - vortex_bail!(InvalidArgument: "append_to_builder for Primitive requires a matching PrimitiveBuilder"); + vortex_bail!("append_to_builder for Primitive requires a matching PrimitiveBuilder"); } fn reduce_parent( diff --git a/vortex-array/src/arrays/scalar_fn/array.rs b/vortex-array/src/arrays/scalar_fn/array.rs index 82f32f74b5c..391ea9a03cd 100644 --- a/vortex-array/src/arrays/scalar_fn/array.rs +++ b/vortex-array/src/arrays/scalar_fn/array.rs @@ -143,7 +143,7 @@ impl Array { #[inline] fn infer_len(slots: &[Option]) -> VortexResult { let Some(child) = slots.first().and_then(Option::as_ref) else { - vortex_bail!(InvalidArgument: "ScalarFnArray length cannot be inferred without children"); + vortex_bail!("ScalarFnArray length cannot be inferred without children"); }; Ok(child.len()) } @@ -159,7 +159,7 @@ impl Array { pub(super) fn validate_not_literal(scalar_fn: &ScalarFnRef) -> VortexResult<()> { vortex_ensure!( !scalar_fn.is::(), - InvalidArgument: "ScalarFnArray cannot wrap a literal, use ConstantArray instead" + "ScalarFnArray cannot wrap a literal, use ConstantArray instead" ); Ok(()) } @@ -169,7 +169,7 @@ impl Array { let arity = scalar_fn.signature().arity(); vortex_ensure!( arity.matches(child_count), - InvalidArgument: "ScalarFnArray requires {arity} children, got {child_count}" + "ScalarFnArray requires {arity} children, got {child_count}" ); Ok(()) } @@ -179,7 +179,7 @@ impl Array { for child in slots.iter().flatten() { vortex_ensure!( child.len() == len, - InvalidArgument: "ScalarFnArray must have children equal to the array length" + "ScalarFnArray must have children equal to the array length" ); } Ok(()) diff --git a/vortex-array/src/arrays/scalar_fn/plugin.rs b/vortex-array/src/arrays/scalar_fn/plugin.rs index eafbb4c93c7..4a4a7d3d5ab 100644 --- a/vortex-array/src/arrays/scalar_fn/plugin.rs +++ b/vortex-array/src/arrays/scalar_fn/plugin.rs @@ -83,7 +83,7 @@ impl ArrayPlugin for ScalarFnArrayPlugi vortex_ensure_eq!( parts.serialized_id, self.id(), - Serde: "scalar function array plugin does not recognize serialized ID", + "scalar function array plugin does not recognize serialized ID", ); let len = parts.len; let scalar_parts = ::deserialize( diff --git a/vortex-array/src/arrays/scalar_fn/rules.rs b/vortex-array/src/arrays/scalar_fn/rules.rs index 3f2b21a8610..5383a614bd6 100644 --- a/vortex-array/src/arrays/scalar_fn/rules.rs +++ b/vortex-array/src/arrays/scalar_fn/rules.rs @@ -203,13 +203,13 @@ mod tests { let mask = Mask::from_iter((0..100).map(|index| index % 20 == 0)); let values = mask .values() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected mask values"))?; + .ok_or_else(|| vortex_err!("expected mask values"))?; assert!(values.cached_indices().is_none()); let parent = FilterArray::try_new(array.clone().into_array(), mask.clone())?; let result = ScalarFilterPushdownRule .reduce_parent(array.as_view(), parent.as_view(), 0)? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected filter pushdown"))?; + .ok_or_else(|| vortex_err!("expected filter pushdown"))?; assert_eq!(values.cached_indices().is_some(), nchildren > 1); let scalar_fn = result.as_::(); @@ -239,7 +239,7 @@ mod tests { let result = ScalarFilterPushdownRule .reduce_parent(array.as_::(), parent.as_view(), 0)? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected filter pushdown"))?; + .ok_or_else(|| vortex_err!("expected filter pushdown"))?; assert_eq!(result.as_::().nchildren(), 0); assert_eq!(result.len(), 2); diff --git a/vortex-array/src/arrays/scalar_fn/vtable/mod.rs b/vortex-array/src/arrays/scalar_fn/vtable/mod.rs index df74447618a..43df40e1d2f 100644 --- a/vortex-array/src/arrays/scalar_fn/vtable/mod.rs +++ b/vortex-array/src/arrays/scalar_fn/vtable/mod.rs @@ -87,7 +87,7 @@ impl VTable for ScalarFn { vortex_ensure_eq!( scalar_fn.id(), self.id, - MismatchedTypes: "ScalarFnArray data scalar_fn does not match vtable", + "ScalarFnArray data scalar_fn does not match vtable", ); Array::::validate_not_literal(scalar_fn)?; @@ -96,18 +96,18 @@ impl VTable for ScalarFn { vortex_ensure_eq!( missing_children, 0, - InvalidArgument: "ScalarFnArray requires every child slot to be present", + "ScalarFnArray requires every child slot to be present", ); let arity = scalar_fn.signature().arity(); vortex_ensure!( arity.matches(slots.len()), - InvalidArgument: "ScalarFnArray requires {arity} children, got {}", + "ScalarFnArray requires {arity} children, got {}", slots.len() ); vortex_ensure!( slots.iter().flatten().all(|c| c.len() == len), - InvalidArgument: "All child arrays must have the same length as the scalar function array" + "All child arrays must have the same length as the scalar function array" ); let child_dtypes = slots @@ -118,7 +118,7 @@ impl VTable for ScalarFn { vortex_ensure_eq!( scalar_fn.return_dtype(&child_dtypes)?, *dtype, - MismatchedTypes: "ScalarFnArray dtype does not match scalar function return dtype", + "ScalarFnArray dtype does not match scalar function return dtype", ); Ok(()) } @@ -128,7 +128,7 @@ impl VTable for ScalarFn { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ScalarFnArray buffer index {idx} out of bounds") + vortex_panic!("ScalarFnArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -160,7 +160,7 @@ impl VTable for ScalarFn { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "Deserialization of ScalarFnVTable metadata is not supported"); + vortex_bail!("Deserialization of ScalarFnVTable metadata is not supported"); } fn slot_name(array: ArrayView<'_, Self>, idx: usize) -> String { diff --git a/vortex-array/src/arrays/scalar_fn/vtable/validity.rs b/vortex-array/src/arrays/scalar_fn/vtable/validity.rs index 5f0b341b427..71c5a2985b4 100644 --- a/vortex-array/src/arrays/scalar_fn/vtable/validity.rs +++ b/vortex-array/src/arrays/scalar_fn/vtable/validity.rs @@ -81,7 +81,7 @@ impl VTable for ScalarFnValidity { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "ScalarFnValidity has no buffers") + vortex_panic!("ScalarFnValidity has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -112,7 +112,7 @@ impl VTable for ScalarFnValidity { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "ScalarFnValidity deserialize not supported"); + vortex_bail!("ScalarFnValidity deserialize not supported"); } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { diff --git a/vortex-array/src/arrays/slice/array.rs b/vortex-array/src/arrays/slice/array.rs index 1947064e412..c9250213c21 100644 --- a/vortex-array/src/arrays/slice/array.rs +++ b/vortex-array/src/arrays/slice/array.rs @@ -40,7 +40,7 @@ impl SliceData { fn try_new(child_len: usize, range: Range) -> VortexResult { if range.end > child_len { vortex_panic!( - OutOfBounds: "SliceArray range out of bounds: range {:?} exceeds child array length {}", + "SliceArray range out of bounds: range {:?} exceeds child array length {}", range, child_len ); diff --git a/vortex-array/src/arrays/slice/vtable.rs b/vortex-array/src/arrays/slice/vtable.rs index 27ac72813c9..3b2351a065c 100644 --- a/vortex-array/src/arrays/slice/vtable.rs +++ b/vortex-array/src/arrays/slice/vtable.rs @@ -81,7 +81,7 @@ impl VTable for Slice { ) -> VortexResult<()> { vortex_ensure!( slots[SliceSlots::CHILD].is_some(), - InvalidArgument: "SliceArray child slot must be present" + "SliceArray child slot must be present" ); let child = slots[SliceSlots::CHILD] .as_ref() @@ -89,16 +89,16 @@ impl VTable for Slice { vortex_ensure_eq!( child.dtype(), dtype, - MismatchedTypes: "SliceArray dtype does not match outer dtype", + "SliceArray dtype does not match outer dtype", ); vortex_ensure_eq!( data.len(), len, - InvalidArgument: "SliceArray length does not match outer length", + "SliceArray length does not match outer length", ); vortex_ensure!( data.range.end <= child.len(), - InvalidArgument: "SliceArray range {:?} exceeds child length {}", + "SliceArray range {:?} exceeds child length {}", data.range, child.len() ); @@ -110,7 +110,7 @@ impl VTable for Slice { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "SliceArray has no buffers") + vortex_panic!("SliceArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -134,7 +134,7 @@ impl VTable for Slice { _session: &VortexSession, ) -> VortexResult>> { // TODO(joe): make this configurable - vortex_bail!(Serde: "Slice array is not serializable") + vortex_bail!("Slice array is not serializable") } fn deserialize( @@ -147,7 +147,7 @@ impl VTable for Slice { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "Slice array is not serializable") + vortex_bail!("Slice array is not serializable") } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { @@ -180,7 +180,7 @@ impl OperationsVTable for Slice { let child_index = state.array().range.start + index; state .slot(SliceSlots::CHILD)? - .ok_or_else(|| vortex_err!(InvalidArgument: "Slice child slot is missing"))? + .ok_or_else(|| vortex_err!("Slice child slot is missing"))? .execute_scalar(child_index, ctx) } diff --git a/vortex-array/src/arrays/struct_/array.rs b/vortex-array/src/arrays/struct_/array.rs index 6a001c186dc..6d3052f1b25 100644 --- a/vortex-array/src/arrays/struct_/array.rs +++ b/vortex-array/src/arrays/struct_/array.rs @@ -253,7 +253,7 @@ pub trait StructArrayExt: StructArraySlotsExt { let name = name.as_ref(); self.unmasked_field_by_name_opt(name).ok_or_else(|| { vortex_err!( - NotFound: "Field {name} not found in struct array with names {:?}", + "Field {name} not found in struct array with names {:?}", self.names() ) }) @@ -366,7 +366,7 @@ impl Array { let len = fields .first() .map(|f| f.len()) - .ok_or_else(|| vortex_err!(InvalidArgument: "StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; + .ok_or_else(|| vortex_err!("StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; Self::try_new(FieldNames::from_iter(names), fields, len, validity) } @@ -382,7 +382,7 @@ impl Array { let len = fields .first() .map(ArrayRef::len) - .ok_or_else(|| vortex_err!(InvalidArgument: "StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; + .ok_or_else(|| vortex_err!("StructArray cannot be constructed from an empty slice of arrays because the length is unspecified"))?; Self::try_new( FieldNames::from_iter(names), @@ -407,7 +407,7 @@ impl Array { let idx = self .struct_fields() .find(f_name.as_ref()) - .ok_or_else(|| vortex_err!(NotFound: "Unknown field {f_name}"))?; + .ok_or_else(|| vortex_err!("Unknown field {f_name}"))?; names.push(self.names()[idx].clone()); children.push(self.unmasked_field(idx).clone()); @@ -496,7 +496,7 @@ impl Array { { let mut it = chunks.into_iter(); let Some(first) = it.next() else { - vortex_bail!(InvalidArgument: "cannot concat empty iterator of arrays"); + vortex_bail!("cannot concat empty iterator of arrays"); }; let first_dtype = first.borrow().dtype().clone(); let struct_fields = first_dtype.as_struct_fields().clone(); @@ -508,7 +508,7 @@ impl Array { let chunk = chunk.borrow(); if &first_dtype != chunk.dtype() { vortex_bail!( - MismatchedTypes: "cannot concatenate struct arrays with differing dtypes: {}, {}", + "cannot concatenate struct arrays with differing dtypes: {}, {}", first_dtype, chunk.dtype(), ); diff --git a/vortex-array/src/arrays/struct_/compute/cast.rs b/vortex-array/src/arrays/struct_/compute/cast.rs index 3e5e84dfabe..e73ea26446b 100644 --- a/vortex-array/src/arrays/struct_/compute/cast.rs +++ b/vortex-array/src/arrays/struct_/compute/cast.rs @@ -103,7 +103,7 @@ pub(crate) fn struct_cast_fields( // If the field is nullable, we add a new ConstantArray field with the type. vortex_ensure!( target_type.is_nullable(), - InvalidArgument: "CAST for struct only supports added nullable fields" + "CAST for struct only supports added nullable fields" ); cast_fields.push( diff --git a/vortex-array/src/arrays/struct_/compute/rules.rs b/vortex-array/src/arrays/struct_/compute/rules.rs index bc0c4bd8004..f7bcd750030 100644 --- a/vortex-array/src/arrays/struct_/compute/rules.rs +++ b/vortex-array/src/arrays/struct_/compute/rules.rs @@ -95,7 +95,7 @@ impl ArrayParentReduceRule for StructGetItemRule { .unmasked_field_by_name_opt(field_name) .ok_or_else(|| { vortex_err!( - NotFound: "Field '{}' missing from struct array {}", + "Field '{}' missing from struct array {}", field_name, child.struct_fields().names() ) diff --git a/vortex-array/src/arrays/struct_/vtable/mod.rs b/vortex-array/src/arrays/struct_/vtable/mod.rs index 4e2b4c661c2..d258d82ad6e 100644 --- a/vortex-array/src/arrays/struct_/vtable/mod.rs +++ b/vortex-array/src/arrays/struct_/vtable/mod.rs @@ -63,13 +63,13 @@ impl VTable for Struct { slots: &[Option], ) -> VortexResult<()> { let DType::Struct(struct_dtype, nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected struct dtype, found {:?}", dtype) + vortex_bail!("Expected struct dtype, found {:?}", dtype) }; let expected_slots = struct_dtype.nfields() + 1; if slots.len() != expected_slots { vortex_bail!( - InvalidArgument: "StructArray has {} slots but expected {}", + "StructArray has {} slots but expected {}", slots.len(), expected_slots ); @@ -80,7 +80,7 @@ impl VTable for Struct { && validity_len != len { vortex_bail!( - InvalidArgument: "StructArray validity length {} does not match outer length {}", + "StructArray validity length {} does not match outer length {}", validity_len, len ); @@ -93,19 +93,19 @@ impl VTable for Struct { for (idx, (slot, field_dtype)) in field_slots.iter().zip(struct_dtype.fields()).enumerate() { - let field = slot.as_ref().ok_or_else( - || vortex_error::vortex_err!(NotFound: "StructArray missing field slot {idx}"), - )?; + let field = slot + .as_ref() + .ok_or_else(|| vortex_error::vortex_err!("StructArray missing field slot {idx}"))?; if field.len() != len { vortex_bail!( - InvalidArgument: "StructArray field {idx} has length {} but expected {}", + "StructArray field {idx} has length {} but expected {}", field.len(), len ); } if field.dtype() != &field_dtype { vortex_bail!( - InvalidArgument: "StructArray field {idx} has dtype {} but expected {}", + "StructArray field {idx} has dtype {} but expected {}", field.dtype(), field_dtype ); @@ -116,11 +116,11 @@ impl VTable for Struct { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "StructArray buffer index {idx} out of bounds") + vortex_panic!("StructArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "StructArray buffer_name index {idx} out of bounds") + vortex_panic!("StructArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -150,12 +150,12 @@ impl VTable for Struct { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "StructArray expects empty metadata, got {} bytes", + "StructArray expects empty metadata, got {} bytes", metadata.len() ); } let DType::Struct(struct_dtype, nullability) = dtype else { - vortex_bail!(MismatchedTypes: "Expected struct dtype, found {:?}", dtype) + vortex_bail!("Expected struct dtype, found {:?}", dtype) }; let (validity, non_data_children) = if children.len() == struct_dtype.nfields() { @@ -165,7 +165,7 @@ impl VTable for Struct { (Validity::Array(validity), 1_usize) } else { vortex_bail!( - InvalidArgument: "Expected {} or {} children, found {}", + "Expected {} or {} children, found {}", struct_dtype.nfields(), struct_dtype.nfields() + 1, children.len() @@ -211,7 +211,7 @@ impl VTable for Struct { ctx: &mut ExecutionCtx, ) -> VortexResult<()> { let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for Struct requires a StructBuilder"); + vortex_bail!("append_to_builder for Struct requires a StructBuilder"); }; builder.append_struct_array(&array.into_owned(), ctx) } diff --git a/vortex-array/src/arrays/struct_/vtable/operations.rs b/vortex-array/src/arrays/struct_/vtable/operations.rs index 94a701477aa..80086b35007 100644 --- a/vortex-array/src/arrays/struct_/vtable/operations.rs +++ b/vortex-array/src/arrays/struct_/vtable/operations.rs @@ -32,7 +32,7 @@ impl OperationsVTable for Struct { let slot = StructSlots::FIELDS_OFFSET + field; let value = state .slot(slot)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Struct field slot {slot} is absent"))? + .ok_or_else(|| vortex_err!("Struct field slot {slot} is absent"))? .execute_scalar(index, ctx)?; field_values.push(value.into_value()); } diff --git a/vortex-array/src/arrays/union/array.rs b/vortex-array/src/arrays/union/array.rs index e9c089c1b55..bd897f916e9 100644 --- a/vortex-array/src/arrays/union/array.rs +++ b/vortex-array/src/arrays/union/array.rs @@ -105,7 +105,7 @@ pub trait UnionArrayExt: UnionArraySlotsExt { let name = name.as_ref(); self.child_by_name_opt(name).ok_or_else(|| { vortex_err!( - NotFound: "Variant {name} not found in union array with names {:?}", + "Variant {name} not found in union array with names {:?}", self.variants().names() ) }) @@ -144,7 +144,7 @@ impl Array { ) -> VortexResult { vortex_ensure!( matches!(type_ids.dtype(), DType::Primitive(PType::U8, _)), - MismatchedTypes: "UnionArray type_ids must be u8, got {}", + "UnionArray type_ids must be u8, got {}", type_ids.dtype() ); @@ -186,9 +186,9 @@ impl Array { /// /// Returns an error if `scalar` does not have a union dtype. pub fn constant(scalar: &Scalar, len: usize) -> VortexResult { - let union = scalar.as_union_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected a union scalar, got {}", scalar.dtype()), - )?; + let union = scalar + .as_union_opt() + .ok_or_else(|| vortex_err!("Expected a union scalar, got {}", scalar.dtype()))?; let variants = union.variants().clone(); let nullability = union.nullability(); diff --git a/vortex-array/src/arrays/union/tests/mod.rs b/vortex-array/src/arrays/union/tests/mod.rs index b4f9e5d1780..9a677da7366 100644 --- a/vortex-array/src/arrays/union/tests/mod.rs +++ b/vortex-array/src/arrays/union/tests/mod.rs @@ -293,7 +293,7 @@ fn constant_union_canonicalizes_to_sparse_union() -> VortexResult<()> { let unselected = canonical .iter_children() .find(|child| child.dtype() == &unselected_dtype) - .ok_or_else(|| vortex_err!(NotFound: "No child with dtype {unselected_dtype}"))?; + .ok_or_else(|| vortex_err!("No child with dtype {unselected_dtype}"))?; assert_eq!( unselected.execute_scalar(0, &mut ctx)?, Scalar::default_value(&unselected_dtype) diff --git a/vortex-array/src/arrays/union/tests/take.rs b/vortex-array/src/arrays/union/tests/take.rs index 016fe353670..ba0de72c01f 100644 --- a/vortex-array/src/arrays/union/tests/take.rs +++ b/vortex-array/src/arrays/union/tests/take.rs @@ -152,7 +152,7 @@ fn take_from_empty_union_is_all_null() -> VortexResult<()> { .execute::(&mut SESSION.create_execution_ctx())? .into_union(); let via_reduce = ::take(empty.as_::(), &indices)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Union take must never decline"))? + .ok_or_else(|| vortex_err!("Union take must never decline"))? .as_::() .into_owned(); diff --git a/vortex-array/src/arrays/union/vtable/mod.rs b/vortex-array/src/arrays/union/vtable/mod.rs index 8b1babe0904..7800f9430d2 100644 --- a/vortex-array/src/arrays/union/vtable/mod.rs +++ b/vortex-array/src/arrays/union/vtable/mod.rs @@ -65,7 +65,7 @@ impl VTable for Union { let type_ids = slots .get(UnionSlots::TYPE_IDS) .and_then(Option::as_ref) - .ok_or_else(|| vortex_err!(NotFound: "UnionArray is missing its type_ids slot"))?; + .ok_or_else(|| vortex_err!("UnionArray is missing its type_ids slot"))?; let variant_arrays = slots .get(UnionSlots::CHILDREN_OFFSET..) .unwrap_or_default() @@ -73,7 +73,7 @@ impl VTable for Union { .enumerate() .map(|(index, slot)| { slot.as_ref() - .ok_or_else(|| vortex_err!(NotFound: "UnionArray is missing child {index}")) + .ok_or_else(|| vortex_err!("UnionArray is missing child {index}")) }) .collect::>>()?; @@ -85,11 +85,11 @@ impl VTable for Union { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "UnionArray buffer index {idx} out of bounds") + vortex_panic!("UnionArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { - vortex_panic!(OutOfBounds: "UnionArray buffer_name index {idx} out of bounds") + vortex_panic!("UnionArray buffer_name index {idx} out of bounds") } fn with_buffers( @@ -116,16 +116,12 @@ impl VTable for Union { children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_ensure!(metadata.is_empty(), Serde: "UnionArray expects empty metadata"); - vortex_ensure!(buffers.is_empty(), InvalidArgument: "UnionArray expects no buffers"); + vortex_ensure!(metadata.is_empty(), "UnionArray expects empty metadata"); + vortex_ensure!(buffers.is_empty(), "UnionArray expects no buffers"); let DType::Union(variants, nullability) = dtype else { - vortex_bail!(InvalidArgument: "Expected union dtype, found {dtype}") + vortex_bail!("Expected union dtype, found {dtype}") }; - vortex_ensure_eq!( - children.len(), - UnionSlots::CHILDREN_OFFSET + variants.len(), - InvalidArgument - ); + vortex_ensure_eq!(children.len(), UnionSlots::CHILDREN_OFFSET + variants.len()); let type_ids = children.get( UnionSlots::TYPE_IDS, @@ -162,7 +158,7 @@ impl VTable for Union { _builder: &mut dyn ArrayBuilder, _ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement append_to_builder for Union arrays") + vortex_bail!("TODO(connor)[Union]: implement append_to_builder for Union arrays") } fn reduce_parent( diff --git a/vortex-array/src/arrays/union/vtable/operations.rs b/vortex-array/src/arrays/union/vtable/operations.rs index 5f3dc88ec7b..78b9759ab1c 100644 --- a/vortex-array/src/arrays/union/vtable/operations.rs +++ b/vortex-array/src/arrays/union/vtable/operations.rs @@ -27,11 +27,11 @@ impl OperationsVTable for Union { }; let Some(child_index) = array.variants().tag_to_child_index(type_id) else { - vortex_panic!(NotFound: "Unknown UnionArray type ID {type_id}") + vortex_panic!("Unknown UnionArray type ID {type_id}") }; let child = array .child(child_index) - .ok_or_else(|| vortex_err!(NotFound: "UnionArray is missing child {child_index}"))?; + .ok_or_else(|| vortex_err!("UnionArray is missing child {child_index}"))?; let child_scalar = child.execute_scalar(index, ctx)?; Scalar::union( diff --git a/vortex-array/src/arrays/union/vtable/validate.rs b/vortex-array/src/arrays/union/vtable/validate.rs index 634cfb1eb3e..8e232600939 100644 --- a/vortex-array/src/arrays/union/vtable/validate.rs +++ b/vortex-array/src/arrays/union/vtable/validate.rs @@ -16,24 +16,24 @@ pub(super) fn validate_union_components( len: usize, ) -> VortexResult<()> { let DType::Union(variants, nullability) = dtype else { - vortex_bail!(InvalidArgument: "Expected union dtype, found {dtype}") + vortex_bail!("Expected union dtype, found {dtype}") }; vortex_ensure_eq!( variant_arrays.len(), variants.len(), - InvalidArgument: "UnionArray variant slot count does not match variant count", + "UnionArray variant slot count does not match variant count", ); let expected_union_type_ids_dtype = union_type_ids_dtype(*nullability); vortex_ensure_eq!( type_ids.dtype(), &expected_union_type_ids_dtype, - MismatchedTypes: "UnionArray type_ids has unexpected dtype", + "UnionArray type_ids has unexpected dtype", ); vortex_ensure_eq!( type_ids.len(), len, - InvalidArgument: "UnionArray type_ids length does not match outer length", + "UnionArray type_ids length does not match outer length", ); for (index, (variant_dtype, child)) in @@ -42,12 +42,12 @@ pub(super) fn validate_union_components( vortex_ensure_eq!( child.len(), len, - InvalidArgument: "UnionArray child {index} length does not match outer length", + "UnionArray child {index} length does not match outer length", ); vortex_ensure_eq!( child.dtype(), &variant_dtype, - MismatchedTypes: "UnionArray child {index} has unexpected dtype", + "UnionArray child {index} has unexpected dtype", ); } diff --git a/vortex-array/src/arrays/validation_tests.rs b/vortex-array/src/arrays/validation_tests.rs index ad10bff8158..3c59d1a02c2 100644 --- a/vortex-array/src/arrays/validation_tests.rs +++ b/vortex-array/src/arrays/validation_tests.rs @@ -14,7 +14,6 @@ mod tests { use vortex_buffer::Buffer; use vortex_buffer::ByteBuffer; use vortex_buffer::buffer; - use vortex_error::VortexErrorKind; use vortex_session::VortexSession; use crate::IntoArray; @@ -42,7 +41,11 @@ mod tests { let chunk2 = buffer![4i64, 5, 6].into_array(); let result = ChunkedArray::try_new(vec![chunk1, chunk2], PType::I32.into()); - assert_eq!(result.unwrap_err().kind(), VortexErrorKind::MismatchedTypes); + let err = result.unwrap_err().to_string(); + assert!( + err.contains("expected type: i32 but instead got i64"), + "{err}" + ); } #[test] @@ -53,7 +56,11 @@ mod tests { let decimal_dtype = crate::dtype::DecimalDType::new(10, 2); let result = DecimalArray::try_new(buffer, decimal_dtype, validity); - assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); + let err = result.unwrap_err().to_string(); + assert!( + err.contains("DecimalArray validity len does not match outer length"), + "{err}" + ); } #[test] @@ -63,7 +70,11 @@ mod tests { let validity = Validity::from_iter([true, false]); // Length 2, buffer is length 3. let result = PrimitiveArray::try_new(buffer, validity); - assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); + let err = result.unwrap_err().to_string(); + assert!( + err.contains("Buffer and validity length mismatch: buffer=3, validity=2"), + "{err}" + ); } #[test] @@ -74,7 +85,11 @@ mod tests { let offsets = buffer![0i64, 2, 5].into_array(); // 5 > 3. let result = ListArray::try_new(elements, offsets, Validity::NonNullable, &mut ctx); - assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); + let err = result.unwrap_err().to_string(); + assert!( + err.contains("Max offset 5 is beyond the length of the elements array 3"), + "{err}" + ); } #[test] @@ -83,7 +98,11 @@ mod tests { let elements = buffer![1i32, 2, 3, 4, 5].into_array(); // 5 elements. let result = FixedSizeListArray::try_new(elements, 2, Validity::NonNullable, 3); // Expects 2 * 3 = 6. - assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); + let err = result.unwrap_err().to_string(); + assert!( + err.contains("the `elements` array has the incorrect number of elements"), + "{err}" + ); } #[test] @@ -122,7 +141,11 @@ mod tests { &mut SESSION.create_execution_ctx(), ); - assert_eq!(result.unwrap_err().kind(), VortexErrorKind::OutOfBounds); + let err = result.unwrap_err().to_string(); + assert!( + err.contains("view at index 0 references invalid buffer: 1 out of bounds"), + "{err}" + ); } #[test] @@ -134,7 +157,11 @@ mod tests { let names = ["a", "b"]; let result = StructArray::try_new(names.into(), fields, 3, Validity::NonNullable); - assert_eq!(result.unwrap_err().kind(), VortexErrorKind::InvalidArgument); + let err = result.unwrap_err().to_string(); + assert!( + err.contains("StructArray field 1 has length 2 but expected 3"), + "{err}" + ); } #[rstest::rstest] diff --git a/vortex-array/src/arrays/varbin/array.rs b/vortex-array/src/arrays/varbin/array.rs index cfcdcfe412b..768e1790e23 100644 --- a/vortex-array/src/arrays/varbin/array.rs +++ b/vortex-array/src/arrays/varbin/array.rs @@ -236,21 +236,21 @@ impl VarBinData { // Check offsets are non-nullable integer vortex_ensure!( offsets.dtype().is_int() && !offsets.dtype().is_nullable(), - MismatchedTypes: "expected type: non nullable int but instead got {}", + "expected type: non nullable int but instead got {}", offsets.dtype() ); // Check dtype is Binary or Utf8 vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - MismatchedTypes: "expected type: utf8 or binary but instead got {}", + "expected type: utf8 or binary but instead got {}", dtype ); // Check nullability matches vortex_ensure!( dtype.is_nullable() != matches!(validity, Validity::NonNullable), - InvalidArgument: "incorrect validity {:?} for dtype {}", + "incorrect validity {:?} for dtype {}", validity, dtype ); @@ -258,7 +258,7 @@ impl VarBinData { // Check offsets has at least one element vortex_ensure!( !offsets.is_empty(), - InvalidArgument: "Offsets must have at least one element" + "Offsets must have at least one element" ); // Check validity length @@ -266,7 +266,7 @@ impl VarBinData { vortex_ensure_eq!( validity_len, offsets.len() - 1, - InvalidArgument: "Validity length doesn't match array length", + "Validity length doesn't match array length", ); } @@ -293,15 +293,15 @@ impl VarBinData { ) -> VortexResult<()> { // Offsets must be sorted (but not strictly sorted, empty values are allowed) let Some(is_sorted) = offsets.statistics().compute_is_sorted(ctx) else { - vortex_bail!(InvalidArgument: "offsets must report is_sorted statistic"); + vortex_bail!("offsets must report is_sorted statistic"); }; - vortex_ensure!(is_sorted, InvalidArgument: "offsets must be sorted"); + vortex_ensure!(is_sorted, "offsets must be sorted"); // Validate that offsets min is non-negative, and max does not exceed the length of // the bytes buffer. let Some(min_max) = min_max(offsets, ctx, NumericalAggregateOpts::default())? else { vortex_bail!( - InvalidArgument: "offsets array with encoding {} must support min_max compute function", + "offsets array with encoding {} must support min_max compute function", offsets.encoding_id() ); }; @@ -322,13 +322,13 @@ impl VarBinData { vortex_ensure!( min >= 0, - InvalidArgument: "offsets minimum {min} outside valid range [0, {max}]" + "offsets minimum {min} outside valid range [0, {max}]" ); // An offset type too narrow for the bytes length cannot exceed it. vortex_ensure!( P::try_from(bytes_len).ok().is_none_or(|len| max <= len), - InvalidArgument: "Max offset {max} is beyond the length of the bytes buffer {bytes_len}" + "Max offset {max} is beyond the length of the bytes buffer {bytes_len}" ); } }); @@ -346,7 +346,7 @@ impl VarBinData { let validate_at = |i: usize, start: usize, end: usize| -> VortexResult<()> { let string_bytes = bytes.get(start..end).ok_or_else(|| { vortex_err!( - InvalidArgument: "offsets {start}..{end} at index {i} are out of order or out of bounds for bytes of length {}", + "offsets {start}..{end} at index {i} are out of order or out of bounds for bytes of length {}", bytes.len() ) })?; @@ -354,7 +354,7 @@ impl VarBinData { #[expect(clippy::unwrap_used)] // run validation using `compat` package to get more detailed error message let err = simdutf8::compat::from_utf8(string_bytes).unwrap_err(); - vortex_err!(InvalidArgument: "invalid utf-8: {err} at index {i}") + vortex_err!("invalid utf-8: {err} at index {i}") })?; Ok(()) }; @@ -379,7 +379,7 @@ impl VarBinData { let last_offset: usize = offsets_slice[offsets_slice.len() - 1].as_(); vortex_ensure!( last_offset <= bytes.len(), - InvalidArgument: "Last offset {} exceeds bytes length {}", + "Last offset {} exceeds bytes length {}", last_offset, bytes.len() ); diff --git a/vortex-array/src/arrays/varbin/builder.rs b/vortex-array/src/arrays/varbin/builder.rs index b2a78511b3c..d929c97ca58 100644 --- a/vortex-array/src/arrays/varbin/builder.rs +++ b/vortex-array/src/arrays/varbin/builder.rs @@ -157,7 +157,7 @@ impl VarBinBuilder { pub fn append_n_values(&mut self, value: impl AsRef<[u8]>, n: usize) -> VortexResult<()> { let value = value.as_ref(); let Some(num_bytes) = value.len().checked_mul(n) else { - vortex_bail!(Overflow: "Byte count overflow: {} values of {} bytes", n, value.len()); + vortex_bail!("Byte count overflow: {} values of {} bytes", n, value.len()); }; // Checking the total up front is what keeps `push_value` below from panicking. self.check_offset_limit(self.data.len(), num_bytes)?; @@ -197,7 +197,7 @@ impl VarBinBuilder { vortex_ensure_eq!( scalar.dtype(), &self.dtype, - MismatchedTypes: "VarBinBuilder scalar dtype does not match builder dtype", + "VarBinBuilder scalar dtype does not match builder dtype", ); match &self.dtype { DType::Utf8(_) => match scalar.as_utf8().value() { @@ -209,7 +209,7 @@ impl VarBinBuilder { None => self.push_nulls(n), }, dtype => { - vortex_bail!(MismatchedTypes: "VarBinBuilder cannot append scalar of dtype {dtype}") + vortex_bail!("VarBinBuilder cannot append scalar of dtype {dtype}") } } Ok(()) @@ -280,7 +280,7 @@ impl VarBinBuilder { usize: AsPrimitive, { let Some(capacity) = num_bytes.checked_add(slack) else { - vortex_bail!(Overflow: "Decoded size overflow: {num_bytes} + {slack}"); + vortex_bail!("Decoded size overflow: {num_bytes} + {slack}"); }; // Checked before decoding: an `i32` builder that the decoded bytes would overflow should // not pay for the decompression first. @@ -292,7 +292,7 @@ impl VarBinBuilder { vortex_ensure_eq!( written, num_bytes, - InvalidArgument: "Decoded byte count does not match expected byte count", + "Decoded byte count does not match expected byte count", ); // The decoded bytes live in spare capacity until `set_len` below, so an invalid `lengths` @@ -494,12 +494,12 @@ impl VarBinBuilder { let mut previous = 0usize; for slot in spare.iter_mut() { let Some(end) = end_offsets.next() else { - vortex_bail!(InvalidArgument: "End offset count is less than the validity length {count}"); + vortex_bail!("End offset count is less than the validity length {count}"); }; let end = end.as_(); vortex_ensure!( end >= previous && end <= num_bytes, - InvalidArgument: "End offsets must be monotonically increasing within {num_bytes} bytes, \ + "End offsets must be monotonically increasing within {num_bytes} bytes, \ got {end} after {previous}" ); slot.write((data_start + end).as_()); @@ -507,12 +507,12 @@ impl VarBinBuilder { } vortex_ensure!( end_offsets.next().is_none(), - InvalidArgument: "End offset count exceeds the validity length {count}" + "End offset count exceeds the validity length {count}" ); vortex_ensure_eq!( previous, num_bytes, - InvalidArgument: "Final end offset does not match the value byte count", + "Final end offset does not match the value byte count", ); // SAFETY: the loop initialized the first `count` spare slots. @@ -574,7 +574,7 @@ impl VarBinBuilder { vortex_ensure_eq!( data.len(), data_start + num_bytes, - InvalidArgument: "Value slices byte count does not match expected byte count", + "Value slices byte count does not match expected byte count", ); // SAFETY: every branch above initialized all `count` spare slots. @@ -585,11 +585,11 @@ impl VarBinBuilder { /// Checks that an offset past `num_bytes` more bytes is representable as an `O`. fn check_offset_limit(&self, data_start: usize, num_bytes: usize) -> VortexResult<()> { let Some(limit) = data_start.checked_add(num_bytes) else { - vortex_bail!(Overflow: "Byte offset overflow: {data_start} + {num_bytes}"); + vortex_bail!("Byte offset overflow: {data_start} + {num_bytes}"); }; vortex_ensure!( u64::try_from(limit).is_ok_and(|limit| limit <= O::max_value_as_u64()), - Overflow: "Byte offset {limit} does not fit in {}", + "Byte offset {limit} does not fit in {}", std::any::type_name::() ); Ok(()) @@ -702,7 +702,7 @@ macro_rules! __match_varbin_builder_arms { #[inline(never)] fn offset_overflow(data_len: usize, value_len: usize, offset_type: &'static str) -> ! { vortex_panic!( - Overflow: "Failed to convert sum of {data_len} and {value_len} to offset of type {offset_type}" + "Failed to convert sum of {data_len} and {value_len} to offset of type {offset_type}" ) } diff --git a/vortex-array/src/arrays/varbin/compute/compare.rs b/vortex-array/src/arrays/varbin/compute/compare.rs index 907b97f6be1..ab2abce91c9 100644 --- a/vortex-array/src/arrays/varbin/compute/compare.rs +++ b/vortex-array/src/arrays/varbin/compute/compare.rs @@ -51,7 +51,7 @@ impl CompareKernel for VarBin { .vortex_expect("RHS should not be null") .as_str() .as_bytes(), - _ => vortex_bail!(MismatchedTypes: "VarBinArray can only have type of Binary or Utf8"), + _ => vortex_bail!("VarBinArray can only have type of Binary or Utf8"), }; let buffer = if rhs_bytes.is_empty() { diff --git a/vortex-array/src/arrays/varbin/compute/filter.rs b/vortex-array/src/arrays/varbin/compute/filter.rs index c3399067bd3..47f740b46ac 100644 --- a/vortex-array/src/arrays/varbin/compute/filter.rs +++ b/vortex-array/src/arrays/varbin/compute/filter.rs @@ -116,13 +116,13 @@ where if valid { let s = offsets[idx + start].to_usize().ok_or_else(|| { vortex_err!( - Overflow: "Failed to convert offset to usize: {}", + "Failed to convert offset to usize: {}", offsets[idx + start] ) })?; let e = offsets[idx + start + 1].to_usize().ok_or_else(|| { vortex_err!( - Overflow: "Failed to convert offset to usize: {}", + "Failed to convert offset to usize: {}", offsets[idx + start + 1] ) })?; @@ -150,12 +150,12 @@ where B: OffsetBuilderPType, usize: AsPrimitive, { - let offset_start = offsets[start].to_usize().ok_or_else( - || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[start]), - )?; - let offset_end = offsets[end].to_usize().ok_or_else( - || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[end]), - )?; + let offset_start = offsets[start] + .to_usize() + .ok_or_else(|| vortex_err!("Failed to convert offset to usize: {}", offsets[start]))?; + let offset_end = offsets[end] + .to_usize() + .ok_or_else(|| vortex_err!("Failed to convert offset to usize: {}", offsets[end]))?; let new_data = &data[offset_start..offset_end]; let new_offsets = offsets[start..end + 1] .iter() @@ -199,12 +199,12 @@ fn filter_select_var_bin_by_index_primitive_offset VortexResult { let value_at = |idx: usize| -> VortexResult<&[u8]> { - let start = offsets[idx].to_usize().ok_or_else( - || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[idx]), - )?; - let end = offsets[idx + 1].to_usize().ok_or_else( - || vortex_err!(Overflow: "Failed to convert offset to usize: {}", offsets[idx + 1]), - )?; + let start = offsets[idx] + .to_usize() + .ok_or_else(|| vortex_err!("Failed to convert offset to usize: {}", offsets[idx]))?; + let end = offsets[idx + 1].to_usize().ok_or_else(|| { + vortex_err!("Failed to convert offset to usize: {}", offsets[idx + 1]) + })?; Ok(&data[start..end]) }; diff --git a/vortex-array/src/arrays/varbin/compute/take.rs b/vortex-array/src/arrays/varbin/compute/take.rs index bde9573261a..d6993d18fc8 100644 --- a/vortex-array/src/arrays/varbin/compute/take.rs +++ b/vortex-array/src/arrays/varbin/compute/take.rs @@ -366,9 +366,9 @@ fn take( let mut current_offset = 0usize; for &idx in indices { - let idx = idx.to_usize().unwrap_or_else( - || vortex_panic!(Overflow: "Failed to convert index to usize: {}", idx), - ); + let idx = idx + .to_usize() + .unwrap_or_else(|| vortex_panic!("Failed to convert index to usize: {}", idx)); let start = offsets[idx]; let stop = offsets[idx + 1]; @@ -381,9 +381,9 @@ fn take( let mut new_data = ByteBufferMut::with_capacity(current_offset); for idx in indices { - let idx = idx.to_usize().unwrap_or_else( - || vortex_panic!(Overflow: "Failed to convert index to usize: {}", idx), - ); + let idx = idx + .to_usize() + .unwrap_or_else(|| vortex_panic!("Failed to convert index to usize: {}", idx)); let start = offsets[idx] .to_usize() .vortex_expect("Failed to cast max offset to usize"); @@ -585,13 +585,14 @@ where S: UnsignedPType, Offset: IntegerPType, { - let computed_len = starts.len().checked_mul(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + let computed_len = starts + .len() + .checked_mul(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; vortex_ensure_eq!( computed_len, output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); let mut new_offsets = Offsets::with_capacity(out_offset_ptype, output_len + 1); @@ -609,24 +610,24 @@ where let byte_end = offset_range[length].as_(); vortex_ensure!( byte_start <= byte_end && byte_end <= data.len(), - InvalidArgument: "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", + "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", data.len() ); for &offset in &offset_range[1..] { let offset = offset.as_(); - let relative = offset.checked_sub(byte_start).ok_or_else( - || vortex_err!(Serde: "VarBin offsets are not monotonic at offset {offset}"), - )?; - let output_offset = output_bytes.checked_add(relative).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), - )?; + let relative = offset.checked_sub(byte_start).ok_or_else(|| { + vortex_err!("VarBin offsets are not monotonic at offset {offset}") + })?; + let output_offset = output_bytes.checked_add(relative).ok_or_else(|| { + vortex_err!("PiecewiseSequence VarBin output byte length overflow") + })?; new_offsets.push(output_offset); } - output_bytes = output_bytes.checked_add(byte_end - byte_start).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), - )?; + output_bytes = output_bytes + .checked_add(byte_end - byte_start) + .ok_or_else(|| vortex_err!("PiecewiseSequence VarBin output byte length overflow"))?; } let mut new_data = ByteBufferMut::with_capacity(output_bytes); @@ -650,7 +651,7 @@ where vortex_ensure_eq!( new_data.len(), output_bytes, - AssertionFailed: "PiecewiseSequenceArray gathered byte length does not match declared byte length", + "PiecewiseSequenceArray gathered byte length does not match declared byte length", ); let offsets = new_offsets.into_array(); @@ -689,29 +690,29 @@ where let byte_end = offset_range[length].as_(); vortex_ensure!( byte_start <= byte_end && byte_end <= data.len(), - InvalidArgument: "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", + "VarBin offsets range {byte_start}..{byte_end} exceeds data length {}", data.len() ); for &offset in &offset_range[1..] { let offset = offset.as_(); - let relative = offset.checked_sub(byte_start).ok_or_else( - || vortex_err!(Serde: "VarBin offsets are not monotonic at offset {offset}"), - )?; - let output_offset = output_bytes.checked_add(relative).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), - )?; + let relative = offset.checked_sub(byte_start).ok_or_else(|| { + vortex_err!("VarBin offsets are not monotonic at offset {offset}") + })?; + let output_offset = output_bytes.checked_add(relative).ok_or_else(|| { + vortex_err!("PiecewiseSequence VarBin output byte length overflow") + })?; new_offsets.push(output_offset); } - output_bytes = output_bytes.checked_add(byte_end - byte_start).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequence VarBin output byte length overflow"), - )?; + output_bytes = output_bytes + .checked_add(byte_end - byte_start) + .ok_or_else(|| vortex_err!("PiecewiseSequence VarBin output byte length overflow"))?; } vortex_ensure_eq!( new_offsets.len(), output_len + 1, - AssertionFailed: "PiecewiseSequenceArray expanded offsets length does not match declared length plus one", + "PiecewiseSequenceArray expanded offsets length does not match declared length plus one", ); let mut new_data = ByteBufferMut::with_capacity(output_bytes); @@ -736,7 +737,7 @@ where vortex_ensure_eq!( new_data.len(), output_bytes, - AssertionFailed: "PiecewiseSequenceArray gathered byte length does not match declared byte length", + "PiecewiseSequenceArray gathered byte length does not match declared byte length", ); let offsets = new_offsets.into_array(); @@ -771,9 +772,9 @@ fn take_nullable( new_offsets.push(current_offset); continue; } - let data_idx_usize = data_idx.to_usize().unwrap_or_else( - || vortex_panic!(Overflow: "Failed to convert index to usize: {}", data_idx), - ); + let data_idx_usize = data_idx + .to_usize() + .unwrap_or_else(|| vortex_panic!("Failed to convert index to usize: {}", data_idx)); if data_validity.value(data_idx_usize) { validity_buffer.append(true); let start = offsets[data_idx_usize]; diff --git a/vortex-array/src/arrays/varbin/vtable/mod.rs b/vortex-array/src/arrays/varbin/vtable/mod.rs index 8eae8b91709..74d8812565f 100644 --- a/vortex-array/src/arrays/varbin/vtable/mod.rs +++ b/vortex-array/src/arrays/varbin/vtable/mod.rs @@ -96,18 +96,18 @@ impl VTable for VarBin { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), VarBinSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), VarBinSlots::COUNT); let offsets = slots[VarBinSlots::OFFSETS] .as_ref() .vortex_expect("VarBinArray offsets slot"); vortex_ensure_eq!( offsets.len().saturating_sub(1), len, - InvalidArgument: "VarBinArray length does not match outer length", + "VarBinArray length does not match outer length", ); vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - MismatchedTypes: "VarBinArray dtype must be binary or utf8, got {dtype}" + "VarBinArray dtype must be binary or utf8, got {dtype}" ); Ok(()) } @@ -115,14 +115,14 @@ impl VTable for VarBin { fn buffer(array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { match idx { 0 => array.bytes_handle().clone(), - _ => vortex_panic!(OutOfBounds: "VarBinArray buffer index {idx} out of bounds"), + _ => vortex_panic!("VarBinArray buffer index {idx} out of bounds"), } } fn buffer_name(_array: ArrayView<'_, Self>, idx: usize) -> Option { match idx { 0 => Some("bytes".to_string()), - _ => vortex_panic!(OutOfBounds: "VarBinArray buffer_name index {idx} out of bounds"), + _ => vortex_panic!("VarBinArray buffer_name index {idx} out of bounds"), } } @@ -131,7 +131,7 @@ impl VTable for VarBin { array: ArrayView<'_, Self>, buffers: &[BufferHandle], ) -> VortexResult> { - vortex_ensure_eq!(buffers.len(), 1, InvalidArgument); + vortex_ensure_eq!(buffers.len(), 1); let mut data = array.data().clone(); data.bytes = buffers[0].clone(); Ok(ArrayParts::new( @@ -172,7 +172,7 @@ impl VTable for VarBin { let validity = children.get(1, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "Expected 1 or 2 children, got {}", children.len()); + vortex_bail!("Expected 1 or 2 children, got {}", children.len()); }; let offsets = children.get( @@ -182,7 +182,7 @@ impl VTable for VarBin { )?; if buffers.len() != 1 { - vortex_bail!(InvalidArgument: "Expected 1 buffer, got {}", buffers.len()); + vortex_bail!("Expected 1 buffer, got {}", buffers.len()); } let bytes = buffers[0].clone().try_to_host_sync()?; @@ -229,7 +229,7 @@ impl VTable for VarBin { // The two arms here are every builder a `Utf8`/`Binary` dtype has: all four // `VarBinBuilder` widths above, and `VarBinViewBuilder` below. let Some(builder) = builder.as_any_mut().downcast_mut::() else { - vortex_bail!(InvalidArgument: "append_to_builder for VarBin requires a variable-binary builder") + vortex_bail!("append_to_builder for VarBin requires a variable-binary builder") }; append_to_varbinview(array, builder, ctx) } diff --git a/vortex-array/src/arrays/varbinview/array.rs b/vortex-array/src/arrays/varbinview/array.rs index 99c0c1b260e..7ecf9163cbf 100644 --- a/vortex-array/src/arrays/varbinview/array.rs +++ b/vortex-array/src/arrays/varbinview/array.rs @@ -177,7 +177,7 @@ impl VarBinViewData { match dtype { DType::Utf8(nullability) => Ok((true, *nullability)), DType::Binary(nullability) => Ok((false, *nullability)), - _ => vortex_bail!(InvalidArgument: "invalid DType {dtype} for `VarBinViewArray`"), + _ => vortex_bail!("invalid DType {dtype} for `VarBinViewArray`"), } } @@ -257,7 +257,7 @@ impl VarBinViewData { let views_nbytes = views.len(); vortex_ensure!( views_nbytes.is_multiple_of(size_of::()), - InvalidArgument: "Expected views buffer length ({views_nbytes}) to be a multiple of {}", + "Expected views buffer length ({views_nbytes}) to be a multiple of {}", size_of::() ); @@ -265,7 +265,7 @@ impl VarBinViewData { if let Some(host) = views.as_host_opt() { vortex_ensure!( host.is_aligned(Alignment::of::()), - InvalidArgument: "Views on host must be 16 byte aligned" + "Views on host must be 16 byte aligned" ); } @@ -392,7 +392,7 @@ impl VarBinViewData { vortex_ensure_eq!( validity.nullability(), nullability, - InvalidArgument: "validity nullability is incompatible with dtype nullability", + "validity nullability is incompatible with dtype nullability", ); Ok(is_utf8) } @@ -496,7 +496,7 @@ impl VarBinViewData { let bytes = view.as_inlined().value(); vortex_ensure!( simdutf8::basic::from_utf8(bytes).is_ok(), - InvalidArgument: "view at index {idx}: inlined bytes failed utf-8 validation" + "view at index {idx}: inlined bytes failed utf-8 validation" ); } return Ok(()); @@ -508,25 +508,25 @@ impl VarBinViewData { let end_offset = start_offset.saturating_add(view.size as usize); let buf = buffers.get(buf_index).ok_or_else(|| - vortex_err!(OutOfBounds: "view at index {idx} references invalid buffer: {buf_index} out of bounds for VarBinViewData with {} buffers", + vortex_err!("view at index {idx} references invalid buffer: {buf_index} out of bounds for VarBinViewData with {} buffers", buffers.len()))?; vortex_ensure!( start_offset < buf.len(), - OutOfBounds: "start offset {start_offset} out of bounds for buffer {buf_index} with size {}", + "start offset {start_offset} out of bounds for buffer {buf_index} with size {}", buf.len(), ); vortex_ensure!( end_offset <= buf.len(), - OutOfBounds: "end offset {end_offset} out of bounds for buffer {buf_index} with size {}", + "end offset {end_offset} out of bounds for buffer {buf_index} with size {}", buf.len(), ); // Make sure the prefix data matches the buffer data. vortex_ensure!( view.prefix == buf[start_offset..start_offset + 4], - InvalidArgument: "VarBinView prefix does not match full string" + "VarBinView prefix does not match full string" ); let Some(buffers_utf8) = buffers_utf8 else { @@ -542,7 +542,7 @@ impl VarBinViewData { vortex_ensure!( valid_utf8, - InvalidArgument: "view at index {idx}: outlined bytes fails utf-8 validation" + "view at index {idx}: outlined bytes fails utf-8 validation" ); Ok(()) @@ -609,7 +609,7 @@ impl VarBinViewData { pub fn buffer(&self, idx: usize) -> &ByteBuffer { if idx >= self.data_buffers().len() { vortex_panic!( - OutOfBounds: "{idx} buffer index out of bounds, there are {} buffers", + "{idx} buffer index out of bounds, there are {} buffers", self.data_buffers().len() ); } diff --git a/vortex-array/src/arrays/varbinview/compute/fill_null.rs b/vortex-array/src/arrays/varbinview/compute/fill_null.rs index 929d4cfbbef..cd3c9bfd10e 100644 --- a/vortex-array/src/arrays/varbinview/compute/fill_null.rs +++ b/vortex-array/src/arrays/varbinview/compute/fill_null.rs @@ -40,9 +40,7 @@ impl FillNullKernel for VarBinView { DType::Binary(_) => fill_value.as_binary().value().cloned(), _ => None, } - .ok_or_else( - || vortex_err!(MismatchedTypes: "Fill value must be a non-null utf8 or binary scalar"), - )?; + .ok_or_else(|| vortex_err!("Fill value must be a non-null utf8 or binary scalar"))?; let Validity::Array(is_valid) = array.validity()? else { unreachable!("checked in entry point"); diff --git a/vortex-array/src/arrays/varbinview/compute/take.rs b/vortex-array/src/arrays/varbinview/compute/take.rs index 659c71e0179..77c0ce44d08 100644 --- a/vortex-array/src/arrays/varbinview/compute/take.rs +++ b/vortex-array/src/arrays/varbinview/compute/take.rs @@ -164,13 +164,14 @@ fn gather_view_slices_constant_length( where S: UnsignedPType, { - let computed_len = starts.len().checked_mul(length).ok_or_else( - || vortex_err!(Overflow: "PiecewiseSequenceArray output length overflows usize"), - )?; + let computed_len = starts + .len() + .checked_mul(length) + .ok_or_else(|| vortex_err!("PiecewiseSequenceArray output length overflows usize"))?; vortex_ensure_eq!( computed_len, output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); let mut views = BufferMut::::with_capacity(output_len); @@ -187,7 +188,7 @@ where vortex_ensure_eq!( views.len(), output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); Ok(views.freeze()) } @@ -217,7 +218,7 @@ where vortex_ensure_eq!( views.len(), output_len, - AssertionFailed: "PiecewiseSequenceArray expanded length does not match declared length", + "PiecewiseSequenceArray expanded length does not match declared length", ); Ok(views.freeze()) } diff --git a/vortex-array/src/arrays/varbinview/compute/zip.rs b/vortex-array/src/arrays/varbinview/compute/zip.rs index 529a6e11b84..fdcfccbd0d5 100644 --- a/vortex-array/src/arrays/varbinview/compute/zip.rs +++ b/vortex-array/src/arrays/varbinview/compute/zip.rs @@ -36,7 +36,7 @@ impl ZipKernel for VarBinView { }; if !if_true.dtype().eq_ignore_nullability(if_false.dtype()) { - vortex_bail!(MismatchedTypes: "input arrays to zip must have the same dtype"); + vortex_bail!("input arrays to zip must have the same dtype"); } let len = if_true.len(); diff --git a/vortex-array/src/arrays/varbinview/tests.rs b/vortex-array/src/arrays/varbinview/tests.rs index d759d1722ab..54435775859 100644 --- a/vortex-array/src/arrays/varbinview/tests.rs +++ b/vortex-array/src/arrays/varbinview/tests.rs @@ -145,7 +145,7 @@ pub fn deserialize_null_views() -> VortexResult<()> { let decoded = decoded .as_opt::() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected VarBinView"))?; + .ok_or_else(|| vortex_err!("expected VarBinView"))?; assert_eq!(decoded.views()[0], views[0]); assert_eq!(decoded.views()[1], BinaryView::empty_view()); assert_arrays_eq!( diff --git a/vortex-array/src/arrays/varbinview/vtable/mod.rs b/vortex-array/src/arrays/varbinview/vtable/mod.rs index 57e54c33ea7..f3d8d4147ed 100644 --- a/vortex-array/src/arrays/varbinview/vtable/mod.rs +++ b/vortex-array/src/arrays/varbinview/vtable/mod.rs @@ -94,15 +94,15 @@ impl VTable for VarBinView { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), VarBinViewSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), VarBinViewSlots::COUNT); vortex_ensure_eq!( data.len(), len, - InvalidArgument: "VarBinViewArray length does not match outer length", + "VarBinViewArray length does not match outer length", ); vortex_ensure!( matches!(dtype, DType::Binary(_) | DType::Utf8(_)), - MismatchedTypes: "VarBinViewArray dtype must be binary or utf8, got {dtype}" + "VarBinViewArray dtype must be binary or utf8, got {dtype}" ); Ok(()) } @@ -114,7 +114,7 @@ impl VTable for VarBinView { } else if idx == ndata { array.views_handle().clone() } else { - vortex_panic!(OutOfBounds: "VarBinViewArray buffer index {idx} out of bounds") + vortex_panic!("VarBinViewArray buffer index {idx} out of bounds") } } @@ -125,7 +125,7 @@ impl VTable for VarBinView { } else if idx == ndata { Some("views".to_string()) } else { - vortex_panic!(OutOfBounds: "VarBinViewArray buffer_name index {idx} out of bounds") + vortex_panic!("VarBinViewArray buffer_name index {idx} out of bounds") } } @@ -135,7 +135,7 @@ impl VTable for VarBinView { buffers: &[BufferHandle], ) -> VortexResult> { let Some((views, data_buffers)) = buffers.split_last() else { - vortex_bail!(MismatchedTypes: "Expected at least 1 buffer, got 0"); + vortex_bail!("Expected at least 1 buffer, got 0"); }; let data = VarBinViewData::try_new_handle( views.clone(), @@ -171,12 +171,12 @@ impl VTable for VarBinView { ) -> VortexResult> { if !metadata.is_empty() { vortex_bail!( - InvalidArgument: "VarBinViewArray expects empty metadata, got {} bytes", + "VarBinViewArray expects empty metadata, got {} bytes", metadata.len() ); } let Some((views_handle, data_handles)) = buffers.split_last() else { - vortex_bail!(MismatchedTypes: "Expected at least 1 buffer, got 0"); + vortex_bail!("Expected at least 1 buffer, got 0"); }; let validity = if children.is_empty() { @@ -185,16 +185,16 @@ impl VTable for VarBinView { let validity = children.get(0, &Validity::DTYPE, len)?; Validity::Array(validity) } else { - vortex_bail!(MismatchedTypes: "Expected 0 or 1 children, got {}", children.len()); + vortex_bail!("Expected 0 or 1 children, got {}", children.len()); }; let views_nbytes = views_handle.len(); let expected_views_nbytes = len .checked_mul(size_of::()) - .ok_or_else(|| vortex_err!(Overflow: "views byte length overflow for len={len}"))?; + .ok_or_else(|| vortex_err!("views byte length overflow for len={len}"))?; if views_nbytes != expected_views_nbytes { vortex_bail!( - MismatchedTypes: "Expected views buffer length {} bytes, got {} bytes", + "Expected views buffer length {} bytes, got {} bytes", expected_views_nbytes, views_nbytes ); @@ -266,7 +266,7 @@ impl VTable for VarBinView { { return result; } - vortex_bail!(InvalidArgument: "append_to_builder for VarBinView requires a variable-binary builder") + vortex_bail!("append_to_builder for VarBinView requires a variable-binary builder") } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/arrays/variant/mod.rs b/vortex-array/src/arrays/variant/mod.rs index 7190581337e..3a44a11019d 100644 --- a/vortex-array/src/arrays/variant/mod.rs +++ b/vortex-array/src/arrays/variant/mod.rs @@ -55,7 +55,7 @@ impl Array { let dtype = core_storage.dtype().clone(); vortex_ensure!( matches!(dtype, DType::Variant(_)), - MismatchedTypes: "VariantArray core_storage dtype must be Variant, found {dtype}" + "VariantArray core_storage dtype must be Variant, found {dtype}" ); let len = core_storage.len(); let stats = core_storage.statistics().to_owned(); @@ -142,7 +142,7 @@ mod tests { fn execute_variant(array: ArrayRef) -> VortexResult { let mut ctx = SESSION.create_execution_ctx(); let Canonical::Variant(variant) = array.execute::(&mut ctx)? else { - return Err(vortex_err!(MismatchedTypes: "expected canonical variant array")); + return Err(vortex_err!("expected canonical variant array")); }; Ok(variant) } @@ -157,7 +157,7 @@ mod tests { let shredded = array .shredded() - .ok_or_else(|| vortex_err!(InvalidArgument: "expected shredded child"))?; + .ok_or_else(|| vortex_err!("expected shredded child"))?; let mut ctx = SESSION.create_execution_ctx(); let expected_shredded_array = if let Some(values) = expected_shredded .iter() @@ -185,9 +185,9 @@ mod tests { let variant = scalar.as_variant(); match expected { Some(expected) => { - let value = variant.value().ok_or_else( - || vortex_err!(InvalidArgument: "expected non-null variant row"), - )?; + let value = variant + .value() + .ok_or_else(|| vortex_err!("expected non-null variant row"))?; assert_eq!(value.as_primitive().typed_value::(), Some(*expected)); } None => assert!(variant.is_null()), @@ -279,9 +279,9 @@ mod tests { let variant = scalar.as_variant(); match expected { Some(expected) => { - let value = variant.value().ok_or_else( - || vortex_err!(InvalidArgument: "expected non-null variant row"), - )?; + let value = variant + .value() + .ok_or_else(|| vortex_err!("expected non-null variant row"))?; assert_eq!(value.as_primitive().typed_value::(), Some(expected)); } None => assert!(variant.is_null()), diff --git a/vortex-array/src/arrays/variant/vtable/mod.rs b/vortex-array/src/arrays/variant/vtable/mod.rs index 58955e1a7f7..9e07169012a 100644 --- a/vortex-array/src/arrays/variant/vtable/mod.rs +++ b/vortex-array/src/arrays/variant/vtable/mod.rs @@ -73,33 +73,33 @@ impl VTable for Variant { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(slots.len(), VariantSlots::COUNT, InvalidArgument); + vortex_ensure_eq!(slots.len(), VariantSlots::COUNT); vortex_ensure!( slots[VariantSlots::CORE_STORAGE].is_some(), - InvalidArgument: "VariantArray core_storage slot must be present" + "VariantArray core_storage slot must be present" ); let core_storage = slots[VariantSlots::CORE_STORAGE] .as_ref() .vortex_expect("validated core_storage slot presence"); vortex_ensure!( matches!(dtype, DType::Variant(_)), - MismatchedTypes: "Expected Variant DType, got {dtype}" + "Expected Variant DType, got {dtype}" ); vortex_ensure_eq!( core_storage.dtype(), dtype, - MismatchedTypes: "VariantArray core_storage dtype does not match outer dtype", + "VariantArray core_storage dtype does not match outer dtype", ); vortex_ensure_eq!( core_storage.len(), len, - InvalidArgument: "VariantArray core_storage length does not match outer length", + "VariantArray core_storage length does not match outer length", ); if let Some(shredded) = slots[VariantSlots::SHREDDED].as_ref() { vortex_ensure_eq!( shredded.len(), len, - InvalidArgument: "VariantArray shredded length does not match outer length", + "VariantArray shredded length does not match outer length", ); } Ok(()) @@ -110,7 +110,7 @@ impl VTable for Variant { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "VariantArray buffer index {idx} out of bounds") + vortex_panic!("VariantArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -149,7 +149,7 @@ impl VTable for Variant { ) -> VortexResult> { vortex_ensure!( buffers.is_empty(), - InvalidArgument: "VariantArray expects 0 buffers, got {}", + "VariantArray expects 0 buffers, got {}", buffers.len() ); let proto = VariantMetadataProto::decode(metadata)?; @@ -158,9 +158,9 @@ impl VTable for Variant { .as_ref() .map(|dtype| DType::from_proto(dtype, session)) .transpose()?; - vortex_ensure!(matches!(dtype, DType::Variant(_)), MismatchedTypes: "Expected Variant DType"); + vortex_ensure!(matches!(dtype, DType::Variant(_)), "Expected Variant DType"); let expected_children = 1 + usize::from(shredded_dtype.is_some()); - vortex_ensure_eq!(children.len(), expected_children, InvalidArgument); + vortex_ensure_eq!(children.len(), expected_children); let core_storage = children.get(0, dtype, len)?; let shredded = shredded_dtype .map(|dtype| children.get(1, &dtype, len)) @@ -181,7 +181,7 @@ impl VTable for Variant { fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { match VariantSlots::NAMES.get(idx) { Some(name) => (*name).to_string(), - None => vortex_panic!(OutOfBounds: "VariantArray slot_name index {idx} out of bounds"), + None => vortex_panic!("VariantArray slot_name index {idx} out of bounds"), } } diff --git a/vortex-array/src/builders/bool.rs b/vortex-array/src/builders/bool.rs index d6ff316cf35..7a718e9244b 100644 --- a/vortex-array/src/builders/bool.rs +++ b/vortex-array/src/builders/bool.rs @@ -128,7 +128,7 @@ impl ArrayBuilder for BoolBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "BoolBuilder received a scalar with the wrong dtype" + "BoolBuilder received a scalar with the wrong dtype" ); match scalar.as_bool().value() { diff --git a/vortex-array/src/builders/child.rs b/vortex-array/src/builders/child.rs index e28a529e70e..923b7f76114 100644 --- a/vortex-array/src/builders/child.rs +++ b/vortex-array/src/builders/child.rs @@ -77,7 +77,7 @@ impl ChildBuilder { vortex_ensure_eq!( array.dtype(), &self.dtype, - MismatchedTypes: "Cannot append an array to a child builder of a different dtype", + "Cannot append an array to a child builder of a different dtype", ); if array.is_empty() { diff --git a/vortex-array/src/builders/decimal.rs b/vortex-array/src/builders/decimal.rs index bde9c0798ea..2a664f17398 100644 --- a/vortex-array/src/builders/decimal.rs +++ b/vortex-array/src/builders/decimal.rs @@ -191,7 +191,7 @@ impl DecimalBuilder { /// The [`DecimalDType`] of this builder. pub fn decimal_dtype(&self) -> &DecimalDType { let DType::Decimal(decimal_dtype, _) = &self.dtype else { - vortex_panic!(AssertionFailed: "`DecimalBuilder` somehow had dtype {}", self.dtype); + vortex_panic!("`DecimalBuilder` somehow had dtype {}", self.dtype); }; decimal_dtype @@ -229,7 +229,7 @@ impl ArrayBuilder for DecimalBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "DecimalBuilder received a scalar with the wrong dtype" + "DecimalBuilder received a scalar with the wrong dtype" ); match scalar.as_decimal().decimal_value() { @@ -267,7 +267,7 @@ impl DecimalBuffer { ::from(value) .ok_or_else(|| { vortex_err!( - Overflow: "decimal conversion failure {:?}, type: {:?} to {:?}", + "decimal conversion failure {:?}, type: {:?} to {:?}", value, V::DECIMAL_TYPE, T::DECIMAL_TYPE, diff --git a/vortex-array/src/builders/dict/bytes.rs b/vortex-array/src/builders/dict/bytes.rs index 75c1f41a916..4614181a707 100644 --- a/vortex-array/src/builders/dict/bytes.rs +++ b/vortex-array/src/builders/dict/bytes.rs @@ -159,9 +159,9 @@ impl BytesDictBuilder { self.values.extend_from_slice(val); } - let next_code = Code::from_usize(next_code).unwrap_or_else( - || vortex_panic!(Overflow: "{next_code} has to fit into {}", Code::PTYPE), - ); + let next_code = Code::from_usize(next_code).unwrap_or_else(|| { + vortex_panic!("{next_code} has to fit into {}", Code::PTYPE) + }); Some(*vacant.insert(next_code).get()) } } @@ -185,7 +185,7 @@ impl BytesDictBuilder { self.views.push(BinaryView::default()); self.values_nulls.append_false(); let code = Code::from_usize(code) - .unwrap_or_else(|| vortex_panic!(Overflow: "{} has to fit into {}", code, Code::PTYPE)); + .unwrap_or_else(|| vortex_panic!("{} has to fit into {}", code, Code::PTYPE)); self.null_code .set(code) .ok() diff --git a/vortex-array/src/builders/dict/mod.rs b/vortex-array/src/builders/dict/mod.rs index 318681e2116..988bf3f7295 100644 --- a/vortex-array/src/builders/dict/mod.rs +++ b/vortex-array/src/builders/dict/mod.rs @@ -70,7 +70,7 @@ pub fn dict_encoder_in( } else if let Some(vb) = array.as_opt::() { bytes_dict_builder(vb.dtype().clone(), constraints, allocator) } else { - vortex_panic!(MismatchedTypes: "Can only encode primitive or varbin/view arrays") + vortex_panic!("Can only encode primitive or varbin/view arrays") }; dict_builder } @@ -100,7 +100,7 @@ pub fn dict_encode(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult u16::MAX as u64, 32 => u32::MAX as u64, 64 => u64::MAX, - width => vortex_panic!(InvalidArgument: "invalid bit_width: {width}"), + width => vortex_panic!("invalid bit_width: {width}"), }); match max_possible_len { max if max <= u8::MAX as u64 => Box::new(PrimitiveDictBuilder::::new_in( @@ -106,7 +106,7 @@ where return None; } let next_code = Code::from_usize(self.values.len()).unwrap_or_else(|| { - vortex_panic!(Overflow: "{} has to fit into {}", self.values.len(), Code::PTYPE) + vortex_panic!("{} has to fit into {}", self.values.len(), Code::PTYPE) }); self.values.push(v); self.values_nulls.append_true(); @@ -126,9 +126,9 @@ where return None; } - let code = Code::from_usize(self.values.len()).unwrap_or_else( - || vortex_panic!(Overflow: "{} has to fit into {}", self.values.len(), Code::PTYPE), - ); + let code = Code::from_usize(self.values.len()).unwrap_or_else(|| { + vortex_panic!("{} has to fit into {}", self.values.len(), Code::PTYPE) + }); self.values.push(T::default()); self.values_nulls.append_false(); self.null_code diff --git a/vortex-array/src/builders/extension.rs b/vortex-array/src/builders/extension.rs index 48cd073205c..d0edb237b99 100644 --- a/vortex-array/src/builders/extension.rs +++ b/vortex-array/src/builders/extension.rs @@ -119,7 +119,7 @@ impl ArrayBuilder for ExtensionBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "ExtensionBuilder received a scalar with the wrong dtype" + "ExtensionBuilder received a scalar with the wrong dtype" ); self.append_value(scalar.as_extension()) diff --git a/vortex-array/src/builders/fixed_size_list.rs b/vortex-array/src/builders/fixed_size_list.rs index 3c37af51b8b..0584e138b5b 100644 --- a/vortex-array/src/builders/fixed_size_list.rs +++ b/vortex-array/src/builders/fixed_size_list.rs @@ -122,8 +122,8 @@ impl FixedSizeListBuilder { array: &ArrayRef, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); - vortex_ensure_eq!(array.len(), self.list_size() as usize, InvalidArgument); + vortex_ensure_eq!(array.dtype(), self.element_dtype()); + vortex_ensure_eq!(array.len(), self.list_size() as usize); self.elements_builder.append_array(array, ctx)?; self.nulls.append_non_null(); @@ -147,8 +147,8 @@ impl FixedSizeListBuilder { n: usize, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); - vortex_ensure_eq!(array.len(), self.list_size() as usize, InvalidArgument); + vortex_ensure_eq!(array.dtype(), self.element_dtype()); + vortex_ensure_eq!(array.len(), self.list_size() as usize); if n == 0 { return Ok(()); @@ -200,7 +200,7 @@ impl FixedSizeListBuilder { if value.len() != self.list_size() as usize { vortex_bail!( - InvalidArgument: "Tried to append a `ListScalar` with length {} to a `FixedSizeListScalar` \ + "Tried to append a `ListScalar` with length {} to a `FixedSizeListScalar` \ with fixed size of {}", value.len(), self.list_size() @@ -241,7 +241,7 @@ impl FixedSizeListBuilder { pub fn element_dtype(&self) -> &DType { let DType::FixedSizeList(element_dtype, ..) = &self.dtype else { vortex_panic!( - AssertionFailed: "`FixedSizeListBuilder` has an incorrect dtype: {}", + "`FixedSizeListBuilder` has an incorrect dtype: {}", self.dtype ); }; @@ -253,7 +253,7 @@ impl FixedSizeListBuilder { pub fn list_size(&self) -> u32 { let DType::FixedSizeList(_, list_size, _) = self.dtype else { vortex_panic!( - AssertionFailed: "`FixedSizeListBuilder` has an incorrect dtype: {}", + "`FixedSizeListBuilder` has an incorrect dtype: {}", self.dtype ); }; @@ -308,7 +308,7 @@ impl ArrayBuilder for FixedSizeListBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "FixedSizeListBuilder received a scalar with the wrong dtype" + "FixedSizeListBuilder received a scalar with the wrong dtype" ); let list_scalar = scalar.as_list(); diff --git a/vortex-array/src/builders/lazy_null_builder.rs b/vortex-array/src/builders/lazy_null_builder.rs index 0da2bb36d7f..d46d731cf25 100644 --- a/vortex-array/src/builders/lazy_null_builder.rs +++ b/vortex-array/src/builders/lazy_null_builder.rs @@ -124,7 +124,7 @@ impl LazyBitBufferBuilder { (NonNullable, None) => Validity::NonNullable, (Nullable, None) => Validity::AllValid, (Nullable, Some(arr)) => Validity::from(arr), - _ => vortex_panic!(AssertionFailed: "Invalid nullability/nulls combination"), + _ => vortex_panic!("Invalid nullability/nulls combination"), } } diff --git a/vortex-array/src/builders/list.rs b/vortex-array/src/builders/list.rs index 56a7c414850..7cd7c2ee868 100644 --- a/vortex-array/src/builders/list.rs +++ b/vortex-array/src/builders/list.rs @@ -137,7 +137,7 @@ impl ListBuilder { array: &ArrayRef, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); + vortex_ensure_eq!(array.dtype(), self.element_dtype()); self.elements_builder.append_array(array, ctx)?; self.nulls.append_non_null(); @@ -154,7 +154,7 @@ impl ListBuilder { match value.elements() { None => { if self.dtype.nullability() == NonNullable { - vortex_bail!(InvalidArgument: "Cannot append null value to non-nullable list"); + vortex_bail!("Cannot append null value to non-nullable list"); } self.append_null(); } @@ -199,7 +199,7 @@ impl ListBuilder { /// the outer `List`. pub fn element_dtype(&self) -> &DType { let DType::List(element_dtype, _) = &self.dtype else { - vortex_panic!(AssertionFailed: "`ListBuilder` has an incorrect dtype: {}", self.dtype); + vortex_panic!("`ListBuilder` has an incorrect dtype: {}", self.dtype); }; element_dtype @@ -393,7 +393,7 @@ impl ArrayBuilder for ListBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "ListBuilder received a scalar with the wrong dtype" + "ListBuilder received a scalar with the wrong dtype" ); self.append_value(scalar.as_list()) diff --git a/vortex-array/src/builders/listview.rs b/vortex-array/src/builders/listview.rs index 475c8b1ba75..bafc1a4c575 100644 --- a/vortex-array/src/builders/listview.rs +++ b/vortex-array/src/builders/listview.rs @@ -170,7 +170,7 @@ impl ListViewBuilder { array: &ArrayRef, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); + vortex_ensure_eq!(array.dtype(), self.element_dtype()); let curr_offset = self.elements_builder.len(); let num_elements = array.len(); @@ -204,7 +204,7 @@ impl ListViewBuilder { // If `elements` is `None`, then the `value` is a null value. vortex_ensure!( self.dtype.is_nullable(), - InvalidArgument: "Cannot append null value to non-nullable list builder" + "Cannot append null value to non-nullable list builder" ); self.append_null(); return Ok(()); @@ -250,7 +250,7 @@ impl ListViewBuilder { n: usize, ctx: &mut ExecutionCtx, ) -> VortexResult<()> { - vortex_ensure_eq!(array.dtype(), self.element_dtype(), MismatchedTypes); + vortex_ensure_eq!(array.dtype(), self.element_dtype()); if n == 0 { return Ok(()); @@ -315,7 +315,7 @@ impl ListViewBuilder { /// the outer `FixedSizeList`. pub fn element_dtype(&self) -> &DType { let DType::List(element_dtype, ..) = &self.dtype else { - vortex_panic!(AssertionFailed: "`ListViewBuilder` has an incorrect dtype: {}", self.dtype); + vortex_panic!("`ListViewBuilder` has an incorrect dtype: {}", self.dtype); }; element_dtype @@ -511,7 +511,7 @@ impl ArrayBuilder for ListViewBuil vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "ListViewBuilder received a scalar with the wrong dtype" + "ListViewBuilder received a scalar with the wrong dtype" ); let list_scalar = scalar.as_list(); diff --git a/vortex-array/src/builders/map.rs b/vortex-array/src/builders/map.rs index 3175424741c..ce39bee96bf 100644 --- a/vortex-array/src/builders/map.rs +++ b/vortex-array/src/builders/map.rs @@ -92,7 +92,7 @@ impl MapBuilder { vortex_ensure_eq!( value.dtype(), &self.dtype, - MismatchedTypes: "MapBuilder received a map scalar with the wrong dtype" + "MapBuilder received a map scalar with the wrong dtype" ); if value.is_null() { @@ -126,7 +126,7 @@ impl MapBuilder { vortex_ensure_eq!( array.dtype(), self.dtype(), - MismatchedTypes: "MapBuilder received a map array with the wrong dtype" + "MapBuilder received a map array with the wrong dtype" ); self.entries_builder .append_listview_array(array.entries().as_::(), ctx) @@ -162,7 +162,7 @@ impl ArrayBuilder for MapBuilder vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), DType::Variant(_) => { - vortex_panic!(NotImplemented: "Variant builders are not implemented") + vortex_panic!("Variant builders are not implemented") } DType::Extension(ext_dtype) => Box::new(ExtensionBuilder::with_capacity_in( ext_dtype.clone(), diff --git a/vortex-array/src/builders/null.rs b/vortex-array/src/builders/null.rs index a93b0bfc397..3ca65919cae 100644 --- a/vortex-array/src/builders/null.rs +++ b/vortex-array/src/builders/null.rs @@ -61,7 +61,7 @@ impl ArrayBuilder for NullBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "NullBuilder received a scalar with the wrong dtype" + "NullBuilder received a scalar with the wrong dtype" ); self.append_null(); diff --git a/vortex-array/src/builders/primitive.rs b/vortex-array/src/builders/primitive.rs index d97e20aaaf0..266ac7ce1c8 100644 --- a/vortex-array/src/builders/primitive.rs +++ b/vortex-array/src/builders/primitive.rs @@ -202,7 +202,7 @@ impl ArrayBuilder for PrimitiveBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "PrimitiveBuilder received a scalar with the wrong dtype" + "PrimitiveBuilder received a scalar with the wrong dtype" ); if let Some(pv) = scalar.as_primitive().pvalue() { diff --git a/vortex-array/src/builders/struct_.rs b/vortex-array/src/builders/struct_.rs index 9a1cdbb9ba9..c437c2de024 100644 --- a/vortex-array/src/builders/struct_.rs +++ b/vortex-array/src/builders/struct_.rs @@ -92,12 +92,12 @@ impl StructBuilder { /// Appends a struct `value` to the builder. pub fn append_value(&mut self, struct_scalar: StructScalar) -> VortexResult<()> { if !self.dtype.is_nullable() && struct_scalar.is_null() { - vortex_bail!(InvalidArgument: "Tried to append a null `StructScalar` to a non-nullable struct builder",); + vortex_bail!("Tried to append a null `StructScalar` to a non-nullable struct builder",); } if struct_scalar.struct_fields() != self.struct_fields() { vortex_bail!( - MismatchedTypes: "Tried to append a `StructScalar` with fields {} to a \ + "Tried to append a `StructScalar` with fields {} to a \ struct builder with fields {}", struct_scalar.struct_fields(), self.struct_fields() @@ -145,7 +145,7 @@ impl StructBuilder { /// The [`StructFields`] of this struct builder. pub fn struct_fields(&self) -> &StructFields { let DType::Struct(struct_fields, _) = &self.dtype else { - vortex_panic!(AssertionFailed: "`StructBuilder` somehow had dtype {}", self.dtype); + vortex_panic!("`StructBuilder` somehow had dtype {}", self.dtype); }; struct_fields @@ -207,7 +207,7 @@ impl ArrayBuilder for StructBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "StructBuilder received a scalar with the wrong dtype" + "StructBuilder received a scalar with the wrong dtype" ); self.append_value(scalar.as_struct()) diff --git a/vortex-array/src/builders/tests.rs b/vortex-array/src/builders/tests.rs index cf4d224443d..0271837c8e5 100644 --- a/vortex-array/src/builders/tests.rs +++ b/vortex-array/src/builders/tests.rs @@ -862,7 +862,7 @@ fn create_test_scalars_for_dtype(dtype: &DType, count: usize) -> Vec { .collect(); Scalar::struct_(DType::Struct(fields.clone(), *n), field_values) } - DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), DType::Variant(_) => continue, DType::Extension(ext_dtype) => { // Create extension scalars with storage values. diff --git a/vortex-array/src/builders/validity.rs b/vortex-array/src/builders/validity.rs index e69239a2433..358473b603a 100644 --- a/vortex-array/src/builders/validity.rs +++ b/vortex-array/src/builders/validity.rs @@ -112,7 +112,7 @@ impl ValidityBuilder { let validity = Validity::concat(runs).vortex_expect("runs is not empty"); if nullability == NonNullable { - vortex_panic!(AssertionFailed: "cannot finish a non-nullable builder holding {validity:?} validity"); + vortex_panic!("cannot finish a non-nullable builder holding {validity:?} validity"); } validity } diff --git a/vortex-array/src/builders/varbinview.rs b/vortex-array/src/builders/varbinview.rs index f17d4a9fb12..8751802aeb0 100644 --- a/vortex-array/src/builders/varbinview.rs +++ b/vortex-array/src/builders/varbinview.rs @@ -838,7 +838,7 @@ impl ArrayBuilder for VarBinViewBuilder { vortex_ensure_eq!( scalar.dtype(), self.dtype(), - MismatchedTypes: "VarBinViewBuilder received a scalar with the wrong dtype" + "VarBinViewBuilder received a scalar with the wrong dtype" ); match self.dtype() { @@ -851,7 +851,7 @@ impl ArrayBuilder for VarBinViewBuilder { None => self.append_null(), }, _ => vortex_bail!( - MismatchedTypes: "VarBinViewBuilder can only handle Utf8 or Binary scalars, got {:?}", + "VarBinViewBuilder can only handle Utf8 or Binary scalars, got {:?}", scalar.dtype() ), } diff --git a/vortex-array/src/canonical.rs b/vortex-array/src/canonical.rs index 2b36b64cd96..d154bbc3954 100644 --- a/vortex-array/src/canonical.rs +++ b/vortex-array/src/canonical.rs @@ -256,7 +256,7 @@ impl Canonical { Canonical::Union(UnionArray::empty(variants.clone(), *nullability)) } DType::Variant(_) => { - vortex_panic!(InvalidArgument: "Canonical empty is not supported for Variant") + vortex_panic!("Canonical empty is not supported for Variant") } DType::Extension(ext_dtype) => Canonical::Extension(ExtensionArray::new( ext_dtype.clone(), @@ -312,7 +312,7 @@ impl Canonical { if let Canonical::Null(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get NullArray from {:?}", &self) + vortex_panic!("Cannot get NullArray from {:?}", &self) } } @@ -320,7 +320,7 @@ impl Canonical { if let Canonical::Null(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap NullArray from {:?}", &self) + vortex_panic!("Cannot unwrap NullArray from {:?}", &self) } } @@ -328,7 +328,7 @@ impl Canonical { if let Canonical::Bool(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get BoolArray from {:?}", &self) + vortex_panic!("Cannot get BoolArray from {:?}", &self) } } @@ -336,7 +336,7 @@ impl Canonical { if let Canonical::Bool(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap BoolArray from {:?}", &self) + vortex_panic!("Cannot unwrap BoolArray from {:?}", &self) } } @@ -344,7 +344,7 @@ impl Canonical { if let Canonical::Primitive(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get PrimitiveArray from {:?}", &self) + vortex_panic!("Cannot get PrimitiveArray from {:?}", &self) } } @@ -352,7 +352,7 @@ impl Canonical { if let Canonical::Primitive(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap PrimitiveArray from {:?}", &self) + vortex_panic!("Cannot unwrap PrimitiveArray from {:?}", &self) } } @@ -360,7 +360,7 @@ impl Canonical { if let Canonical::Decimal(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get DecimalArray from {:?}", &self) + vortex_panic!("Cannot get DecimalArray from {:?}", &self) } } @@ -368,7 +368,7 @@ impl Canonical { if let Canonical::Decimal(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap DecimalArray from {:?}", &self) + vortex_panic!("Cannot unwrap DecimalArray from {:?}", &self) } } @@ -376,7 +376,7 @@ impl Canonical { if let Canonical::VarBinView(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get VarBinViewArray from {:?}", &self) + vortex_panic!("Cannot get VarBinViewArray from {:?}", &self) } } @@ -384,7 +384,7 @@ impl Canonical { if let Canonical::VarBinView(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap VarBinViewArray from {:?}", &self) + vortex_panic!("Cannot unwrap VarBinViewArray from {:?}", &self) } } @@ -392,7 +392,7 @@ impl Canonical { if let Canonical::List(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get ListArray from {:?}", &self) + vortex_panic!("Cannot get ListArray from {:?}", &self) } } @@ -400,7 +400,7 @@ impl Canonical { if let Canonical::List(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap ListArray from {:?}", &self) + vortex_panic!("Cannot unwrap ListArray from {:?}", &self) } } @@ -408,7 +408,7 @@ impl Canonical { if let Canonical::Map(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get MapArray from {:?}", &self) + vortex_panic!("Cannot get MapArray from {:?}", &self) } } @@ -416,7 +416,7 @@ impl Canonical { if let Canonical::Map(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap MapArray from {:?}", &self) + vortex_panic!("Cannot unwrap MapArray from {:?}", &self) } } @@ -424,7 +424,7 @@ impl Canonical { if let Canonical::FixedSizeList(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get FixedSizeListArray from {:?}", &self) + vortex_panic!("Cannot get FixedSizeListArray from {:?}", &self) } } @@ -432,7 +432,7 @@ impl Canonical { if let Canonical::FixedSizeList(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap FixedSizeListArray from {:?}", &self) + vortex_panic!("Cannot unwrap FixedSizeListArray from {:?}", &self) } } @@ -440,7 +440,7 @@ impl Canonical { if let Canonical::Struct(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get StructArray from {:?}", &self) + vortex_panic!("Cannot get StructArray from {:?}", &self) } } @@ -448,7 +448,7 @@ impl Canonical { if let Canonical::Struct(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap StructArray from {:?}", &self) + vortex_panic!("Cannot unwrap StructArray from {:?}", &self) } } @@ -457,7 +457,7 @@ impl Canonical { if let Canonical::Union(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get UnionArray from {:?}", &self) + vortex_panic!("Cannot get UnionArray from {:?}", &self) } } @@ -466,7 +466,7 @@ impl Canonical { if let Canonical::Union(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap UnionArray from {:?}", &self) + vortex_panic!("Cannot unwrap UnionArray from {:?}", &self) } } @@ -474,7 +474,7 @@ impl Canonical { if let Canonical::Extension(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot get ExtensionArray from {:?}", &self) + vortex_panic!("Cannot get ExtensionArray from {:?}", &self) } } @@ -482,7 +482,7 @@ impl Canonical { if let Canonical::Extension(a) = self { a } else { - vortex_panic!(MismatchedTypes: "Cannot unwrap ExtensionArray from {:?}", &self) + vortex_panic!("Cannot unwrap ExtensionArray from {:?}", &self) } } } @@ -889,7 +889,7 @@ impl Executable for Buffer { array.validity()?, Validity::NonNullable | Validity::AllValid ), - InvalidArgument: "Cannot execute to native buffer: array is not all-valid." + "Cannot execute to native buffer: array is not all-valid." ); Ok(array.into_buffer()) } @@ -1051,7 +1051,7 @@ impl Executable for VariantArray { Err(array) => match Canonical::execute(array, ctx)? { Canonical::Variant(variant_array) => Ok(variant_array), canonical => { - vortex_panic!(MismatchedTypes: "Cannot unwrap VariantArray from {:?}", canonical) + vortex_panic!("Cannot unwrap VariantArray from {:?}", canonical) } }, } @@ -1342,19 +1342,17 @@ mod tests { .execute::(&mut ctx)? .0 else { - return Err(vortex_err!(MismatchedTypes: "expected canonical variant")); + return Err(vortex_err!("expected canonical variant")); }; let nested_variant = canonical .shredded() .and_then(|shredded| shredded.as_opt::()) - .ok_or_else( - || vortex_err!(InvalidArgument: "expected nested variant shredded child"), - )?; + .ok_or_else(|| vortex_err!("expected nested variant shredded child"))?; let nested_struct = nested_variant .shredded() .and_then(|shredded| shredded.as_opt::()) - .ok_or_else(|| vortex_err!(InvalidArgument: "expected nested struct shredded child"))?; + .ok_or_else(|| vortex_err!("expected nested struct shredded child"))?; let value = nested_struct.unmasked_field_by_name("value")?; assert!(value.is::()); diff --git a/vortex-array/src/compute/conformance/binary_numeric.rs b/vortex-array/src/compute/conformance/binary_numeric.rs index acbf0a8c97a..9b87f5fea2c 100644 --- a/vortex-array/src/compute/conformance/binary_numeric.rs +++ b/vortex-array/src/compute/conformance/binary_numeric.rs @@ -140,7 +140,7 @@ pub fn test_binary_numeric_array(array: &ArrayRef, ctx: &mut ExecutionCtx) { test_binary_numeric_conformance_decimal(array, *decimal_dtype, ctx) } dtype => vortex_panic!( - NotImplemented: "Binary numeric tests are only supported for primitive and decimal types, got {dtype}", + "Binary numeric tests are only supported for primitive and decimal types, got {dtype}", ), } } @@ -377,7 +377,7 @@ fn test_binary_numeric_edge_cases(array: &ArrayRef, ctx: &mut ExecutionCtx) { PType::F64 => test_binary_numeric_edge_cases_float::(array, ctx), }, dtype => vortex_panic!( - NotImplemented: "Binary numeric edge case tests are only supported for primitive numeric types, got {dtype}" + "Binary numeric edge case tests are only supported for primitive numeric types, got {dtype}" ), } } diff --git a/vortex-array/src/compute/conformance/cast.rs b/vortex-array/src/compute/conformance/cast.rs index bb4527564bd..175ece9e524 100644 --- a/vortex-array/src/compute/conformance/cast.rs +++ b/vortex-array/src/compute/conformance/cast.rs @@ -172,7 +172,7 @@ fn test_cast_to_non_nullable(array: &ArrayRef, ctx: &mut ExecutionCtx) { .err() .unwrap_or_else(|| { vortex_panic!( - AssertionFailed: "arrays with nulls should error when casting to non-nullable {}", + "arrays with nulls should error when casting to non-nullable {}", array, ) }); @@ -273,7 +273,7 @@ fn test_cast_to_primitive( .err() .unwrap_or_else(|| { vortex_panic!( - AssertionFailed: "Cast must fail because some values are out of bounds. {} {:?} {:?} {} {}", + "Cast must fail because some values are out of bounds. {} {:?} {:?} {} {}", target_ptype, min, max, diff --git a/vortex-array/src/compute/conformance/consistency.rs b/vortex-array/src/compute/conformance/consistency.rs index f07fc87f019..e83b4867eb9 100644 --- a/vortex-array/src/compute/conformance/consistency.rs +++ b/vortex-array/src/compute/conformance/consistency.rs @@ -1046,9 +1046,9 @@ fn slice_cast_targets(dtype: &DType) -> Vec { }; vec![DType::Struct(fields.clone(), opposite)] } - DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), DType::Variant(_) => { - vortex_panic!(NotImplemented: "Variant conformance casting is not implemented") + vortex_panic!("Variant conformance casting is not implemented") } DType::Extension(_) => vec![], // Extension types typically only cast to themselves } diff --git a/vortex-array/src/dtype/decimal/mod.rs b/vortex-array/src/dtype/decimal/mod.rs index 2de3eb90bcc..10396eab24d 100644 --- a/vortex-array/src/dtype/decimal/mod.rs +++ b/vortex-array/src/dtype/decimal/mod.rs @@ -48,26 +48,26 @@ impl DecimalDType { pub fn try_new(precision: u8, scale: i8) -> VortexResult { let precision = NonZero::new(precision).ok_or_else(|| { vortex_err!( - InvalidArgument: "decimal precision must be between 1 and {} (inclusive)", + "decimal precision must be between 1 and {} (inclusive)", MAX_PRECISION ) })?; if precision.get() > MAX_PRECISION { vortex_bail!( - InvalidArgument: "decimal precision {} exceeds MAX_PRECISION {}", + "decimal precision {} exceeds MAX_PRECISION {}", precision, MAX_PRECISION ); } if scale > MAX_SCALE { - vortex_bail!(InvalidArgument: "decimal scale {} exceeds MAX_SCALE {}", scale, MAX_SCALE); + vortex_bail!("decimal scale {} exceeds MAX_SCALE {}", scale, MAX_SCALE); } if scale > 0 && scale as u8 > precision.get() { vortex_bail!( - InvalidArgument: "decimal scale {} is greater than precision {}", + "decimal scale {} is greater than precision {}", scale, precision ); @@ -122,7 +122,7 @@ impl TryFrom<&DType> for DecimalDType { if let DType::Decimal(dt, _) = value { Ok(*dt) } else { - vortex_bail!(MismatchedTypes: "Cannot convert DType {value} into DecimalType") + vortex_bail!("Cannot convert DType {value} into DecimalType") } } } diff --git a/vortex-array/src/dtype/decimal/precision.rs b/vortex-array/src/dtype/decimal/precision.rs index 136a6d5bcd4..9785828b2f6 100644 --- a/vortex-array/src/dtype/decimal/precision.rs +++ b/vortex-array/src/dtype/decimal/precision.rs @@ -49,23 +49,23 @@ impl PrecisionScale { pub fn try_new(precision: u8, scale: i8) -> VortexResult { let precision = NonZero::new(precision).ok_or_else(|| { vortex_err!( - InvalidArgument: "precision cannot be 0, has to be between [1, {}]", + "precision cannot be 0, has to be between [1, {}]", D::MAX_PRECISION ) })?; if precision.get() > D::MAX_PRECISION { vortex_bail!( - InvalidArgument: "Precision {} is greater than max {}", + "Precision {} is greater than max {}", precision, D::MAX_PRECISION ); } if scale > D::MAX_SCALE { - vortex_bail!(InvalidArgument: "Scale {} is greater than max {}", scale, D::MAX_SCALE); + vortex_bail!("Scale {} is greater than max {}", scale, D::MAX_SCALE); } if scale > 0 && scale as u8 > precision.get() { - vortex_bail!(InvalidArgument: "Scale {} is greater than precision {}", scale, precision); + vortex_bail!("Scale {} is greater than precision {}", scale, precision); } Ok(Self { precision, diff --git a/vortex-array/src/dtype/decimal/types.rs b/vortex-array/src/dtype/decimal/types.rs index 8435e200a33..f83a3918a86 100644 --- a/vortex-array/src/dtype/decimal/types.rs +++ b/vortex-array/src/dtype/decimal/types.rs @@ -257,7 +257,7 @@ impl TryFrom for DecimalType { | PType::F16 | PType::F32 | PType::F64) => { - vortex_bail!(MismatchedTypes: "cannot convert ptype {p} to DecimalType") + vortex_bail!("cannot convert ptype {p} to DecimalType") } }) } diff --git a/vortex-array/src/dtype/dtype_impl.rs b/vortex-array/src/dtype/dtype_impl.rs index 192f7a8a30d..27d083edff8 100644 --- a/vortex-array/src/dtype/dtype_impl.rs +++ b/vortex-array/src/dtype/dtype_impl.rs @@ -91,7 +91,7 @@ impl DType { pub fn with_nullability(&self, nullability: Nullability) -> Self { match self { Null if nullability == Nullability::NonNullable => { - vortex_panic!(InvalidArgument: "DType::Null cannot be made non-nullable") + vortex_panic!("DType::Null cannot be made non-nullable") } Null => Null, Bool(_) => Bool(nullability), @@ -210,7 +210,7 @@ impl DType { if let Primitive(ptype, _) = self { *ptype } else { - vortex_panic!(MismatchedTypes: "DType {self} is not a primitive type") + vortex_panic!("DType {self} is not a primitive type") } } @@ -448,7 +448,7 @@ impl DType { if let Struct(f, _) = self { return f; } - vortex_panic!(MismatchedTypes: "DType is not a Struct") + vortex_panic!("DType is not a Struct") } /// Owned version of [Self::as_struct_fields]. @@ -456,7 +456,7 @@ impl DType { if let Struct(f, _) = self { return f; } - vortex_panic!(MismatchedTypes: "DType is not a Struct") + vortex_panic!("DType is not a Struct") } /// Get the `StructDType` if `self` is a `StructDType`, otherwise `None` @@ -501,7 +501,7 @@ impl DType { /// Downcast a `DType` to an `ExtDType` pub fn as_extension(&self) -> &ExtDTypeRef { let Extension(ext) = self else { - vortex_panic!(MismatchedTypes: "DType is not an Extension") + vortex_panic!("DType is not an Extension") }; ext } diff --git a/vortex-array/src/dtype/extension/erased.rs b/vortex-array/src/dtype/extension/erased.rs index 8cd55baac27..b2f49974247 100644 --- a/vortex-array/src/dtype/extension/erased.rs +++ b/vortex-array/src/dtype/extension/erased.rs @@ -152,7 +152,7 @@ impl ExtDTypeRef { self.try_downcast::() .map_err(|this| { vortex_err!( - MismatchedTypes: "Failed to downcast ExtDTypeRef {} to {}", + "Failed to downcast ExtDTypeRef {} to {}", this.0.id(), type_name::(), ) diff --git a/vortex-array/src/dtype/field_mask.rs b/vortex-array/src/dtype/field_mask.rs index b7c770f7d80..006768379d9 100644 --- a/vortex-array/src/dtype/field_mask.rs +++ b/vortex-array/src/dtype/field_mask.rs @@ -40,7 +40,7 @@ impl FieldMask { if let Some(stepped_fp) = fp.step_into() { Ok(FieldMask::Exact(stepped_fp)) } else { - vortex_bail!(InvalidArgument: "Cannot step into exact root field path"); + vortex_bail!("Cannot step into exact root field path"); } } } @@ -50,7 +50,7 @@ impl FieldMask { pub fn starting_field(&self) -> VortexResult> { match self { FieldMask::All => { - vortex_bail!(InvalidArgument: "Cannot get starting field from All mask") + vortex_bail!("Cannot get starting field from All mask") } // We know that fp is non-empty FieldMask::Prefix(fp) | FieldMask::Exact(fp) => Ok(fp.parts().first()), diff --git a/vortex-array/src/dtype/map.rs b/vortex-array/src/dtype/map.rs index fc4a77e02ff..e138cea6545 100644 --- a/vortex-array/src/dtype/map.rs +++ b/vortex-array/src/dtype/map.rs @@ -108,7 +108,7 @@ impl MapDType { ) -> VortexResult { vortex_ensure!( !key.value()?.is_nullable(), - InvalidArgument: "map key dtype must be non-nullable" + "map key dtype must be non-nullable" ); Ok(Self(Arc::new(MapDTypeInner { diff --git a/vortex-array/src/dtype/ptype.rs b/vortex-array/src/dtype/ptype.rs index 808e0486fd8..03a0a9d1da8 100644 --- a/vortex-array/src/dtype/ptype.rs +++ b/vortex-array/src/dtype/ptype.rs @@ -891,7 +891,7 @@ impl TryFrom<&DType> for PType { if let DType::Primitive(p, _) = value { Ok(*p) } else { - vortex_bail!(MismatchedTypes: "Cannot convert DType {value} into PType") + vortex_bail!("Cannot convert DType {value} into PType") } } } @@ -948,7 +948,7 @@ macro_rules! try_from_bytes { impl TryFromBytes for $T { fn try_from_le_bytes(bytes: &[u8]) -> VortexResult { Ok(<$T>::from_le_bytes(bytes.try_into().map_err(|_| { - vortex_err!(InvalidArgument: "Failed to convert bytes into {}", stringify!($T)) + vortex_err!("Failed to convert bytes into {}", stringify!($T)) })?)) } } diff --git a/vortex-array/src/dtype/serde/flatbuffers.rs b/vortex-array/src/dtype/serde/flatbuffers.rs index 7467ec435fa..1f4b36acf23 100644 --- a/vortex-array/src/dtype/serde/flatbuffers.rs +++ b/vortex-array/src/dtype/serde/flatbuffers.rs @@ -72,13 +72,13 @@ impl StructFields { ) -> VortexResult { let names: FieldNames = fb_struct .names() - .ok_or_else(|| vortex_err!(Serde: "failed to parse struct names from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse struct names from flatbuffer"))? .iter() .collect(); let dtypes = fb_struct .dtypes() - .ok_or_else(|| vortex_err!(Serde: "failed to parse struct dtypes from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse struct dtypes from flatbuffer"))? .iter() .map(|dt| { FieldDType::from(ViewedDType::from_fb_loc( @@ -91,7 +91,7 @@ impl StructFields { if names.len() != dtypes.len() { vortex_bail!( - MismatchedTypes: "length mismatch between struct names ({}) and dtypes ({})", + "length mismatch between struct names ({}) and dtypes ({})", names.len(), dtypes.len() ); @@ -110,13 +110,13 @@ impl UnionVariants { ) -> VortexResult { let names = fb_union .names() - .ok_or_else(|| vortex_err!(Serde: "failed to parse union names from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse union names from flatbuffer"))? .iter() .collect(); let dtypes = fb_union .dtypes() - .ok_or_else(|| vortex_err!(Serde: "failed to parse union dtypes from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse union dtypes from flatbuffer"))? .iter() .map(|dt| { FieldDType::from(ViewedDType::from_fb_loc( @@ -129,7 +129,7 @@ impl UnionVariants { let type_ids: Vec = fb_union .type_ids() - .ok_or_else(|| vortex_err!(Serde: "failed to parse union type_ids from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse union type_ids from flatbuffer"))? .iter() .map(i8::cast_unsigned) .collect(); @@ -147,10 +147,10 @@ impl MapDType { ) -> VortexResult { let key = fb_map .key_type() - .ok_or_else(|| vortex_err!(Serde: "failed to parse map key type from flatbuffer"))?; + .ok_or_else(|| vortex_err!("failed to parse map key type from flatbuffer"))?; let value = fb_map .value_type() - .ok_or_else(|| vortex_err!(Serde: "failed to parse map value type from flatbuffer"))?; + .ok_or_else(|| vortex_err!("failed to parse map value type from flatbuffer"))?; MapDType::try_from_fields( FieldDType::from(ViewedDType::from_fb_loc( @@ -185,23 +185,23 @@ impl TryFrom for DType { fb::Type::Null => Ok(Self::Null), fb::Type::Bool => Ok(Self::Bool( fb.type__as_bool() - .ok_or_else(|| vortex_err!(Serde: "failed to parse bool from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse bool from flatbuffer"))? .nullable() .into(), )), fb::Type::Primitive => { - let fb_primitive = fb.type__as_primitive().ok_or_else( - || vortex_err!(Serde: "failed to parse primitive from flatbuffer"), - )?; + let fb_primitive = fb + .type__as_primitive() + .ok_or_else(|| vortex_err!("failed to parse primitive from flatbuffer"))?; Ok(Self::Primitive( fb_primitive.ptype().try_into()?, fb_primitive.nullable().into(), )) } fb::Type::Decimal => { - let fb_decimal = fb.type__as_decimal().ok_or_else( - || vortex_err!(Serde: "failed to parse decimal dtype from flatbuffer"), - )?; + let fb_decimal = fb + .type__as_decimal() + .ok_or_else(|| vortex_err!("failed to parse decimal dtype from flatbuffer"))?; Ok(Self::Decimal( DecimalDType::try_new(fb_decimal.precision(), fb_decimal.scale())?, fb_decimal.nullable().into(), @@ -209,24 +209,24 @@ impl TryFrom for DType { } fb::Type::Utf8 => Ok(Self::Utf8( fb.type__as_utf_8() - .ok_or_else(|| vortex_err!(Serde: "failed to parse utf-8 from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse utf-8 from flatbuffer"))? .nullable() .into(), )), fb::Type::Binary => Ok(Self::Binary( fb.type__as_binary() - .ok_or_else(|| vortex_err!(Serde: "failed to parse binary from flatbuffer"))? + .ok_or_else(|| vortex_err!("failed to parse binary from flatbuffer"))? .nullable() .into(), )), fb::Type::List => { let fb_list = fb .type__as_list() - .ok_or_else(|| vortex_err!(Serde: "failed to parse list from flatbuffer"))?; + .ok_or_else(|| vortex_err!("failed to parse list from flatbuffer"))?; - let list_element = fb_list.element_type().ok_or_else( - || vortex_err!(Serde: "failed to parse list element type from flatbuffer"), - )?; + let list_element = fb_list.element_type().ok_or_else(|| { + vortex_err!("failed to parse list element type from flatbuffer") + })?; let element_dtype = Self::try_from(ViewedDType::from_fb_loc( list_element._tab.loc(), vfdt.buffer().clone(), @@ -238,13 +238,13 @@ impl TryFrom for DType { )) } fb::Type::FixedSizeList => { - let fb_fixed_size_list = fb.type__as_fixed_size_list().ok_or_else( - || vortex_err!(Serde: "failed to parse fixed-size list from flatbuffer"), - )?; + let fb_fixed_size_list = fb.type__as_fixed_size_list().ok_or_else(|| { + vortex_err!("failed to parse fixed-size list from flatbuffer") + })?; - let list_element = fb_fixed_size_list.element_type().ok_or_else( - || vortex_err!(Serde: "failed to parse list element type from flatbuffer"), - )?; + let list_element = fb_fixed_size_list.element_type().ok_or_else(|| { + vortex_err!("failed to parse list element type from flatbuffer") + })?; let element_dtype = Self::try_from(ViewedDType::from_fb_loc( list_element._tab.loc(), vfdt.buffer().clone(), @@ -259,14 +259,14 @@ impl TryFrom for DType { fb::Type::Map => { let fb_map = fb .type__as_map() - .ok_or_else(|| vortex_err!(Serde: "failed to parse map from flatbuffer"))?; + .ok_or_else(|| vortex_err!("failed to parse map from flatbuffer"))?; let map = MapDType::from_fb(fb_map, vfdt.buffer().clone(), vfdt.session.clone())?; Ok(Self::Map(map, fb_map.nullable().into())) } fb::Type::Struct_ => { let fb_struct = fb .type__as_struct_() - .ok_or_else(|| vortex_err!(Serde: "failed to parse struct from flatbuffer"))?; + .ok_or_else(|| vortex_err!("failed to parse struct from flatbuffer"))?; let struct_dtype = StructFields::from_fb(fb_struct, vfdt.buffer().clone(), vfdt.session.clone())?; @@ -275,7 +275,7 @@ impl TryFrom for DType { fb::Type::Union => { let fb_union = fb .type__as_union() - .ok_or_else(|| vortex_err!(Serde: "failed to parse union from flatbuffer"))?; + .ok_or_else(|| vortex_err!("failed to parse union from flatbuffer"))?; let variants = UnionVariants::from_fb(fb_union, vfdt.buffer().clone(), vfdt.session.clone())?; Ok(Self::Union(variants, fb_union.nullable().into())) @@ -283,20 +283,20 @@ impl TryFrom for DType { fb::Type::Variant => { let fb_variant = fb .type__as_variant() - .ok_or_else(|| vortex_err!(Serde: "failed to parse variant from flatbuffer"))?; + .ok_or_else(|| vortex_err!("failed to parse variant from flatbuffer"))?; Ok(Self::Variant(fb_variant.nullable().into())) } fb::Type::Extension => { - let fb_ext = fb.type__as_extension().ok_or_else( - || vortex_err!(Serde: "failed to parse extension from flatbuffer"), - )?; + let fb_ext = fb + .type__as_extension() + .ok_or_else(|| vortex_err!("failed to parse extension from flatbuffer"))?; #[expect(clippy::disallowed_methods, reason = "interning a dynamic id")] - let id = ExtId::new(fb_ext.id().ok_or_else( - || vortex_err!(Serde: "failed to parse extension id from flatbuffer"), - )?); + let id = + ExtId::new(fb_ext.id().ok_or_else(|| { + vortex_err!("failed to parse extension id from flatbuffer") + })?); let storage_dtype = fb_ext.storage_dtype().ok_or_else(|| { - vortex_err!( - Serde: "storage_dtype must be present on DType fbs message") + vortex_err!("storage_dtype must be present on DType fbs message") })?; let storage_view = ViewedDType::from_fb_loc( storage_dtype._tab.loc(), @@ -308,21 +308,21 @@ impl TryFrom for DType { let metadata = fb_ext .metadata() - .ok_or_else( - || vortex_err!(Serde: "failed to parse extension metadata from flatbuffer"), - )? + .ok_or_else(|| { + vortex_err!("failed to parse extension metadata from flatbuffer") + })? .bytes(); let ext_dtype = if let Some(vtable) = vfdt.session.dtypes().registry().get(&id) { vtable.deserialize(metadata, storage_dtype)? } else if vfdt.session.allows_unknown() { ForeignExtDType::from_parts(id, metadata.to_vec(), storage_dtype)? } else { - return Err(vortex_err!(NotFound: "No such DType extension ID: {}", id)); + return Err(vortex_err!("No such DType extension ID: {}", id)); }; Ok(Self::Extension(ext_dtype)) } - _ => Err(vortex_err!(Serde: "Unknown DType variant")), + _ => Err(vortex_err!("Unknown DType variant")), } } } @@ -555,7 +555,7 @@ impl TryFrom for PType { fb::PType::F16 => Self::F16, fb::PType::F32 => Self::F32, fb::PType::F64 => Self::F64, - _ => vortex_bail!(Serde: "Unknown PType variant"), + _ => vortex_bail!("Unknown PType variant"), }) } } diff --git a/vortex-array/src/dtype/serde/proto.rs b/vortex-array/src/dtype/serde/proto.rs index 67820140d14..d6d4d31e0c8 100644 --- a/vortex-array/src/dtype/serde/proto.rs +++ b/vortex-array/src/dtype/serde/proto.rs @@ -29,19 +29,19 @@ impl DType { match value .dtype_type .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Unrecognized DType"))? + .ok_or_else(|| vortex_err!("Unrecognized DType"))? { DtypeType::Null(_) => Ok(Self::Null), DtypeType::Bool(b) => Ok(Self::Bool(b.nullable.into())), DtypeType::Primitive(p) => Ok(Self::Primitive(p.r#type().into(), p.nullable.into())), DtypeType::Decimal(d) => Ok(Self::Decimal( DecimalDType::try_new( - d.precision.try_into().map_err( - |_| vortex_err!(Serde: "proto precision could not be downcast to u8"), - )?, - d.scale.try_into().map_err( - |_| vortex_err!(Serde: "proto scale could not be downcast to i8"), - )?, + d.precision + .try_into() + .map_err(|_| vortex_err!("proto precision could not be downcast to u8"))?, + d.scale + .try_into() + .map_err(|_| vortex_err!("proto scale could not be downcast to i8"))?, )?, d.nullable.into(), )), @@ -53,7 +53,7 @@ impl DType { DType::from_proto( l.element_type .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Invalid list element type"))? + .ok_or_else(|| vortex_err!("Invalid list element type"))? .as_ref(), session, ) @@ -67,9 +67,7 @@ impl DType { DType::from_proto( fsl.element_type .as_ref() - .ok_or_else( - || vortex_err!(Serde: "Invalid fixed-size list element type"), - )? + .ok_or_else(|| vortex_err!("Invalid fixed-size list element type"))? .as_ref(), session, ) @@ -83,14 +81,14 @@ impl DType { DType::from_proto( map.key_type .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Invalid map key type"))? + .ok_or_else(|| vortex_err!("Invalid map key type"))? .as_ref(), session, )?, DType::from_proto( map.value_type .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Invalid map value type"))? + .ok_or_else(|| vortex_err!("Invalid map value type"))? .as_ref(), session, )?, @@ -120,7 +118,7 @@ impl DType { .iter() .map(|t| { u8::try_from(*t).map_err(|_| { - vortex_err!(Overflow: "Union type_id {t} somehow does not fit in u8") + vortex_err!("Union type_id {t} somehow does not fit in u8") }) }) .collect::>>()?; @@ -132,9 +130,9 @@ impl DType { #[expect(clippy::disallowed_methods, reason = "interning a dynamic id")] let id = ExtId::new(e.id.as_str()); let storage_dtype = DType::from_proto( - e.storage_dtype.as_ref().ok_or_else( - || vortex_err!(Serde: "Extension DType missing storage proto"), - )?, + e.storage_dtype + .as_ref() + .ok_or_else(|| vortex_err!("Extension DType missing storage proto"))?, session, )?; let ext_dtype = if let Some(vtable) = session.dtypes().registry().get(&id) { @@ -142,7 +140,7 @@ impl DType { } else if session.allows_unknown() { ForeignExtDType::from_parts(id, e.metadata().to_vec(), storage_dtype)? } else { - return Err(vortex_err!(Serde: "Unregistered extension type ID: {}", e.id)); + return Err(vortex_err!("Unregistered extension type ID: {}", e.id)); }; Ok(Self::Extension(ext_dtype)) } @@ -273,7 +271,7 @@ impl TryFrom<&pb::FieldPath> for FieldPath { match field .field_type .as_ref() - .ok_or_else(|| vortex_err!(Serde: "FieldPath part missing type"))? + .ok_or_else(|| vortex_err!("FieldPath part missing type"))? { FieldType::Name(name) => path.push(Field::from(name.as_str())), } diff --git a/vortex-array/src/dtype/struct_.rs b/vortex-array/src/dtype/struct_.rs index 464946f9ae7..1482f4cee59 100644 --- a/vortex-array/src/dtype/struct_.rs +++ b/vortex-array/src/dtype/struct_.rs @@ -327,7 +327,7 @@ impl StructFields { pub fn new(names: FieldNames, dtypes: Vec) -> Self { if names.len() != dtypes.len() { vortex_panic!( - InvalidArgument: "length mismatch between names ({}) and dtypes ({})", + "length mismatch between names ({}) and dtypes ({})", names.len(), dtypes.len() ); @@ -347,7 +347,7 @@ impl StructFields { pub fn from_fields(names: FieldNames, dtypes: Vec) -> Self { if names.len() != dtypes.len() { vortex_panic!( - InvalidArgument: "length mismatch between names ({}) and dtypes ({})", + "length mismatch between names ({}) and dtypes ({})", names.len(), dtypes.len() ); @@ -434,7 +434,7 @@ impl StructFields { for field in projection { let idx = self .find(field) - .ok_or_else(|| vortex_err!(NotFound: "{field} not found"))?; + .ok_or_else(|| vortex_err!("{field} not found"))?; names.push(self.0.names[idx].clone()); dtypes.push(self.0.dtypes[idx].clone()); } @@ -449,7 +449,7 @@ impl StructFields { pub fn without_field(&self, index: usize) -> VortexResult { if index >= self.nfields() { vortex_bail!( - OutOfBounds: "index {} out of bounds for struct with {} fields", + "index {} out of bounds for struct with {} fields", index, self.nfields() ); @@ -491,7 +491,7 @@ impl StructFields { .collect::(); if !names.iter().all_unique() { - vortex_bail!(InvalidArgument: "Can't merge struct fields with duplicate names"); + vortex_bail!("Can't merge struct fields with duplicate names"); } let dtypes = self diff --git a/vortex-array/src/dtype/union.rs b/vortex-array/src/dtype/union.rs index af5b037da2a..7174ab2d988 100644 --- a/vortex-array/src/dtype/union.rs +++ b/vortex-array/src/dtype/union.rs @@ -171,32 +171,32 @@ impl UnionVariants { vortex_ensure_eq!( names.len(), n_dtypes, - InvalidArgument: "union names and dtypes length mismatch" + "union names and dtypes length mismatch" ); vortex_ensure_eq!( names.len(), type_ids.len(), - InvalidArgument: "union names and type_ids length mismatch" + "union names and type_ids length mismatch" ); vortex_ensure!( !names.is_empty(), - InvalidArgument: "union must have at least one variant (for now)" + "union must have at least one variant (for now)" ); vortex_ensure!( type_ids.iter().all_unique(), - InvalidArgument: "type_ids must be distinct, got {:?}", + "type_ids must be distinct, got {:?}", type_ids ); vortex_ensure!( type_ids.len() <= u8::MAX as usize + 1, - InvalidArgument: "union supports at most {} variants, got {}", + "union supports at most {} variants, got {}", u8::MAX as usize + 1, type_ids.len() ); vortex_ensure!( names.iter().all_unique(), - InvalidArgument: "union variant names must be distinct, got {:?}", + "union variant names must be distinct, got {:?}", names ); @@ -231,7 +231,7 @@ impl UnionVariants { const MAX_VARIANTS: usize = u8::MAX as usize + 1; vortex_ensure!( names.len() <= MAX_VARIANTS, - InvalidArgument: "union supports at most {} consecutive variants, got {}", + "union supports at most {} consecutive variants, got {}", MAX_VARIANTS, names.len() ); diff --git a/vortex-array/src/executor.rs b/vortex-array/src/executor.rs index db2b61483ff..b9e22a41e62 100644 --- a/vortex-array/src/executor.rs +++ b/vortex-array/src/executor.rs @@ -55,12 +55,12 @@ use crate::trace_op; pub(crate) fn max_iterations() -> usize { static MAX_ITERATIONS: LazyLock = LazyLock::new(|| { match std::env::var("VORTEX_MAX_ITERATIONS") { - Ok(val) => val.parse::().unwrap_or_else(|e| { - vortex_panic!(InvalidArgument: "VORTEX_MAX_ITERATIONS is not a valid usize: {e}") + Ok(val) => val.parse::().unwrap_or_else(|e| { + vortex_panic!("VORTEX_MAX_ITERATIONS is not a valid usize: {e}") }), Err(VarError::NotPresent) => 2 << 21, // 2 ^ 22 Err(VarError::NotUnicode(_)) => { - vortex_panic!(InvalidArgument: "VORTEX_MAX_ITERATIONS is not a valid unicode string") + vortex_panic!("VORTEX_MAX_ITERATIONS is not a valid unicode string") } } }); @@ -338,7 +338,7 @@ impl ArrayRef { } vortex_bail!( - AssertionFailed: "Exceeded maximum execution iterations ({}) while executing array", + "Exceeded maximum execution iterations ({}) while executing array", max_iterations, ) } @@ -633,13 +633,13 @@ fn finalize_done( vortex_ensure_eq!( output.len(), expected_len, - AssertionFailed: "Result length mismatch for {:?}", + "Result length mismatch for {:?}", encoding_id ); vortex_ensure_eq!( output.dtype(), &expected_dtype, - AssertionFailed: "Executed canonical dtype mismatch for {:?}", + "Executed canonical dtype mismatch for {:?}", encoding_id ); } @@ -665,12 +665,12 @@ fn execute_parent_for_child( vortex_ensure_eq!( result.len(), parent.len(), - AssertionFailed: "Executed parent canonical length mismatch" + "Executed parent canonical length mismatch" ); vortex_ensure_eq!( result.dtype(), parent.dtype(), - AssertionFailed: "Executed parent canonical dtype mismatch" + "Executed parent canonical dtype mismatch" ); } log_parent_rewrite(ctx, phase, slot_idx, parent, child, &result); diff --git a/vortex-array/src/expr/bound_expression.rs b/vortex-array/src/expr/bound_expression.rs index 12a8d9eab14..035ca91f404 100644 --- a/vortex-array/src/expr/bound_expression.rs +++ b/vortex-array/src/expr/bound_expression.rs @@ -127,7 +127,7 @@ impl BoundExpression { fn try_new_vec(scalar_fn: ScalarFnRef, children: Vec) -> VortexResult { vortex_ensure!( scalar_fn.signature().arity().matches(children.len()), - InvalidArgument: "Expression arity mismatch: expected {} children but got {}", + "Expression arity mismatch: expected {} children but got {}", scalar_fn.signature().arity(), children.len() ); @@ -155,7 +155,7 @@ impl BoundExpression { let BoundExpression::Scalar { scalar_fn, .. } = &self else { vortex_ensure!( children.is_empty(), - InvalidArgument: "Root expression cannot have {} children", + "Root expression cannot have {} children", children.len() ); return Ok(self); diff --git a/vortex-array/src/expr/expression.rs b/vortex-array/src/expr/expression.rs index 0a7e105a0de..ded8e2c87d7 100644 --- a/vortex-array/src/expr/expression.rs +++ b/vortex-array/src/expr/expression.rs @@ -63,7 +63,7 @@ impl Expression { vortex_ensure!( scalar_fn.signature().arity().matches(children.len()), - InvalidArgument: "Expression arity mismatch: expected {} children but got {}", + "Expression arity mismatch: expected {} children but got {}", scalar_fn.signature().arity(), children.len() ); @@ -130,7 +130,7 @@ impl Expression { Self::Root => { vortex_ensure!( children.is_empty(), - InvalidArgument: "Expression arity mismatch: root expects 0 children but got {}", + "Expression arity mismatch: root expects 0 children but got {}", children.len() ); Ok(Self::Root) @@ -138,7 +138,7 @@ impl Expression { Self::Variable(name) => { vortex_ensure!( children.is_empty(), - InvalidArgument: "Expression arity mismatch: variable expects 0 children but got {}", + "Expression arity mismatch: variable expects 0 children but got {}", children.len() ); Ok(Self::Variable(name.clone())) @@ -146,7 +146,7 @@ impl Expression { Self::Scalar { scalar_fn, .. } => { vortex_ensure!( scalar_fn.signature().arity().matches(children.len()), - InvalidArgument: "Expression arity mismatch: expected {} children but got {}", + "Expression arity mismatch: expected {} children but got {}", scalar_fn.signature().arity(), children.len() ); @@ -271,7 +271,7 @@ impl Expression { /// The error for a variable that no enclosing lambda declares. pub(crate) fn unbound_variable(name: &FieldName) -> VortexError { - vortex_err!(NotFound: "variable @{name} is not a parameter of an enclosing lambda") + vortex_err!("variable @{name} is not a parameter of an enclosing lambda") } /// The default display implementation for expressions uses the 'SQL'-style format. diff --git a/vortex-array/src/expr/exprs.rs b/vortex-array/src/expr/exprs.rs index 430f4863c96..8634ae901b3 100644 --- a/vortex-array/src/expr/exprs.rs +++ b/vortex-array/src/expr/exprs.rs @@ -267,7 +267,7 @@ pub fn nested_case_when( } let Ok(num_when_then_pairs) = u32::try_from(when_then_pairs.len()) else { - vortex_panic!(InvalidArgument: "nested_case_when has too many when/then pairs"); + vortex_panic!("nested_case_when has too many when/then pairs"); }; let options = CaseWhenOptions { num_when_then_pairs, @@ -287,7 +287,7 @@ pub fn bound_nested_case_when( ); let Ok(num_when_then_pairs) = u32::try_from(when_then_pairs.len()) else { - vortex_panic!(InvalidArgument: "nested_case_when has too many when/then pairs"); + vortex_panic!("nested_case_when has too many when/then pairs"); }; let has_else = else_value.is_some(); let mut children = Vec::with_capacity(when_then_pairs.len() * 2 + usize::from(has_else)); @@ -1216,7 +1216,7 @@ pub fn in_list_of( vortex_ensure!( element.dtype() == &DType::Null || element.dtype().eq_ignore_nullability(&element_dtype), - MismatchedTypes: "IN list element {element} is not of type {element_dtype}" + "IN list element {element} is not of type {element_dtype}" ); element.cast(&element_dtype) }) diff --git a/vortex-array/src/expr/lambda/mod.rs b/vortex-array/src/expr/lambda/mod.rs index c82ee659034..198226622a3 100644 --- a/vortex-array/src/expr/lambda/mod.rs +++ b/vortex-array/src/expr/lambda/mod.rs @@ -73,12 +73,12 @@ impl Lambda { ) -> VortexResult { let params: FieldNames = params.into_iter().map(Into::into).collect(); if let Some(param) = params.iter().duplicates().next() { - vortex_bail!(InvalidArgument: "lambda parameter {param} is declared more than once"); + vortex_bail!("lambda parameter {param} is declared more than once"); } pre_order_visit_down(&body, |node: &Expression| { vortex_ensure!( !reads_outside_lambda(node, params.as_ref()), - InvalidArgument: "lambda ({}) can only read its parameters, not {node}; reading anything else is \ + "lambda ({}) can only read its parameters, not {node}; reading anything else is \ not supported yet", params.iter().format(", ") ); @@ -138,7 +138,7 @@ impl Lambda { fn param_fields(&self, param_dtypes: &[DType]) -> VortexResult { vortex_ensure!( param_dtypes.len() == self.params.len(), - InvalidArgument: "lambda {self} needs one dtype per parameter, got {}", + "lambda {self} needs one dtype per parameter, got {}", param_dtypes.len() ); Ok(StructFields::new( @@ -236,7 +236,7 @@ impl BoundLambda { pub fn evaluate(&self, args: Vec, len: usize) -> VortexResult { vortex_ensure!( args.len() == self.params.nfields(), - InvalidArgument: "lambda {self} needs one array per parameter, got {}", + "lambda {self} needs one array per parameter, got {}", args.len() ); for ((name, dtype), arg) in self @@ -248,7 +248,7 @@ impl BoundLambda { { vortex_ensure!( arg.dtype() == &dtype, - MismatchedTypes: "lambda {self}: parameter {name} is bound to {dtype}, not {}", + "lambda {self}: parameter {name} is bound to {dtype}, not {}", arg.dtype() ); } diff --git a/vortex-array/src/expr/lambda/tests.rs b/vortex-array/src/expr/lambda/tests.rs index 47adba0a7c2..d09592bdf11 100644 --- a/vortex-array/src/expr/lambda/tests.rs +++ b/vortex-array/src/expr/lambda/tests.rs @@ -102,7 +102,7 @@ impl ScalarFnVTable for Apply { ApplyOptions::Bound(lambda) => { vortex_ensure!( lambda.is_bound_to(args), - AssertionFailed: "{lambda} is bound to other dtypes" + "{lambda} is bound to other dtypes" ); Ok(None) } @@ -116,7 +116,7 @@ impl ScalarFnVTable for Apply { _ctx: &mut ExecutionCtx, ) -> VortexResult { let ApplyOptions::Bound(lambda) = options else { - vortex_bail!(AssertionFailed: "apply's lambda is not bound"); + vortex_bail!("apply's lambda is not bound"); }; lambda.evaluate(vec![args.get(0)?], args.row_count()) } diff --git a/vortex-array/src/expr/optimize.rs b/vortex-array/src/expr/optimize.rs index 108a36d5799..ac4356892b6 100644 --- a/vortex-array/src/expr/optimize.rs +++ b/vortex-array/src/expr/optimize.rs @@ -47,7 +47,7 @@ impl BoundExpression { loop { if loop_counter > 100 { vortex_error::vortex_bail!( - AssertionFailed: "Exceeded maximum optimization iterations (possible infinite loop)" + "Exceeded maximum optimization iterations (possible infinite loop)" ); } loop_counter += 1; @@ -204,9 +204,10 @@ mod tests { // Prune rules pattern-match a bare Literal on the comparison RHS; a cast wrapper // silently disables pruning. - let rhs = optimized.child(1).as_opt::().ok_or_else( - || vortex_err!(MismatchedTypes: "expected a bare literal RHS, got {optimized}"), - )?; + let rhs = optimized + .child(1) + .as_opt::() + .ok_or_else(|| vortex_err!("expected a bare literal RHS, got {optimized}"))?; assert_eq!(rhs, &Scalar::primitive(3.0f64, Nullability::NonNullable)); Ok(()) } diff --git a/vortex-array/src/expr/proto.rs b/vortex-array/src/expr/proto.rs index ef0fa41c062..273bb0d1166 100644 --- a/vortex-array/src/expr/proto.rs +++ b/vortex-array/src/expr/proto.rs @@ -44,7 +44,7 @@ impl ExprSerializeProtoExt for Expression { let metadata = scalar_fn.options().serialize()?.ok_or_else(|| { vortex_err!( - Serde: "Expression '{}' is not serializable: {}", + "Expression '{}' is not serializable: {}", scalar_fn.id(), self ) @@ -64,7 +64,7 @@ impl Expression { if expr.id == ROOT_ID { vortex_ensure!( expr.children.is_empty(), - Serde: "root expression must have no children, got {}", + "root expression must have no children, got {}", expr.children.len() ); return Ok(Expression::Root); @@ -83,7 +83,7 @@ impl Expression { } else if session.allows_unknown() { ForeignScalarFnVTable::make_scalar_fn(expr_id, expr.metadata().to_vec(), children.len()) } else { - return Err(vortex_err!(NotFound: "unknown expression id: {}", expr_id)); + return Err(vortex_err!("unknown expression id: {}", expr_id)); }; Expression::try_new(scalar_fn, children) diff --git a/vortex-array/src/expr/traversal/fold.rs b/vortex-array/src/expr/traversal/fold.rs index 44bc12d8196..5b6c7c94944 100644 --- a/vortex-array/src/expr/traversal/fold.rs +++ b/vortex-array/src/expr/traversal/fold.rs @@ -132,10 +132,10 @@ mod tests { if *operator == Operator::Add { Ok(FoldUp::Continue(children[0] + children[1])) } else { - vortex_bail!(InvalidArgument: "not a valid operator") + vortex_bail!("not a valid operator") } } else { - vortex_bail!(InvalidArgument: "not a valid type") + vortex_bail!("not a valid type") } } } diff --git a/vortex-array/src/extension/datetime/date.rs b/vortex-array/src/extension/datetime/date.rs index 033643df65d..1920af1a85f 100644 --- a/vortex-array/src/extension/datetime/date.rs +++ b/vortex-array/src/extension/datetime/date.rs @@ -43,9 +43,8 @@ impl Date { /// /// Note that only Milliseconds and Days time units are supported for Date. pub fn try_new(time_unit: TimeUnit, nullability: Nullability) -> VortexResult> { - let ptype = date_ptype(&time_unit).ok_or_else( - || vortex_err!(InvalidArgument: "Date type does not support time unit {}", time_unit), - )?; + let ptype = date_ptype(&time_unit) + .ok_or_else(|| vortex_err!("Date type does not support time unit {}", time_unit))?; ExtDType::try_new(time_unit, DType::Primitive(ptype, nullability)) } @@ -91,21 +90,20 @@ impl ExtVTable for Date { } fn deserialize_metadata(&self, metadata: &[u8]) -> VortexResult { - vortex_ensure!(!metadata.is_empty(), Serde: "Date metadata must not be empty"); + vortex_ensure!(!metadata.is_empty(), "Date metadata must not be empty"); let tag = metadata[0]; TimeUnit::try_from(tag) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { let metadata = ext_dtype.metadata(); - let ptype = date_ptype(metadata).ok_or_else( - || vortex_err!(InvalidArgument: "Date type does not support time unit {}", metadata), - )?; + let ptype = date_ptype(metadata) + .ok_or_else(|| vortex_err!("Date type does not support time unit {}", metadata))?; vortex_ensure_eq!( ext_dtype.storage_dtype().as_ptype(), ptype, - MismatchedTypes: "Date storage dtype for {} has the wrong ptype", + "Date storage dtype for {} has the wrong ptype", metadata ); @@ -122,7 +120,7 @@ impl ExtVTable for Date { storage_value.as_primitive().cast::()?, )), TimeUnit::Days => Ok(DateValue::Days(storage_value.as_primitive().cast::()?)), - _ => vortex_bail!(InvalidArgument: "Date type does not support time unit {}", metadata), + _ => vortex_bail!("Date type does not support time unit {}", metadata), } } } diff --git a/vortex-array/src/extension/datetime/time.rs b/vortex-array/src/extension/datetime/time.rs index d065dccb62d..2645f9fd2e9 100644 --- a/vortex-array/src/extension/datetime/time.rs +++ b/vortex-array/src/extension/datetime/time.rs @@ -38,9 +38,8 @@ impl Time { /// /// Note that Days units are not supported for Time. pub fn try_new(time_unit: TimeUnit, nullability: Nullability) -> VortexResult> { - let ptype = time_ptype(&time_unit).ok_or_else( - || vortex_err!(InvalidArgument: "Time type does not support time unit {}", time_unit), - )?; + let ptype = time_ptype(&time_unit) + .ok_or_else(|| vortex_err!("Time type does not support time unit {}", time_unit))?; ExtDType::try_new(time_unit, DType::Primitive(ptype, nullability)) } @@ -92,21 +91,20 @@ impl ExtVTable for Time { } fn deserialize_metadata(&self, data: &[u8]) -> VortexResult { - vortex_ensure!(!data.is_empty(), Serde: "Time metadata must not be empty"); + vortex_ensure!(!data.is_empty(), "Time metadata must not be empty"); let tag = data[0]; TimeUnit::try_from(tag) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { let metadata = ext_dtype.metadata(); - let ptype = time_ptype(metadata).ok_or_else( - || vortex_err!(InvalidArgument: "Time type does not support time unit {}", metadata), - )?; + let ptype = time_ptype(metadata) + .ok_or_else(|| vortex_err!("Time type does not support time unit {}", metadata))?; vortex_ensure_eq!( ext_dtype.storage_dtype().as_ptype(), ptype, - MismatchedTypes: "Time storage dtype for {} has the wrong ptype", + "Time storage dtype for {} has the wrong ptype", metadata ); @@ -121,15 +119,13 @@ impl ExtVTable for Time { let (span, value) = match *ext_dtype.metadata() { TimeUnit::Seconds => { - let v = i32::try_from(length_of_time).map_err( - |e| vortex_err!(Overflow: "Time seconds value out of i32 range: {e}"), - )?; + let v = i32::try_from(length_of_time) + .map_err(|e| vortex_err!("Time seconds value out of i32 range: {e}"))?; (Span::new().seconds(v), TimeValue::Seconds(v)) } TimeUnit::Milliseconds => { - let v = i32::try_from(length_of_time).map_err( - |e| vortex_err!(Overflow: "Time milliseconds value out of i32 range: {e}"), - )?; + let v = i32::try_from(length_of_time) + .map_err(|e| vortex_err!("Time milliseconds value out of i32 range: {e}"))?; (Span::new().milliseconds(v), TimeValue::Milliseconds(v)) } TimeUnit::Microseconds => ( @@ -141,14 +137,14 @@ impl ExtVTable for Time { TimeValue::Nanoseconds(length_of_time), ), d @ TimeUnit::Days => { - vortex_bail!(InvalidArgument: "Time type does not support time unit {d}") + vortex_bail!("Time type does not support time unit {d}") } }; // Validate the storage value is within the valid range for Time. jiff::civil::Time::MIN .checked_add(span) - .map_err(|e| vortex_err!(InvalidArgument: "Invalid time scalar: {}", e))?; + .map_err(|e| vortex_err!("Invalid time scalar: {}", e))?; Ok(value) } diff --git a/vortex-array/src/extension/datetime/timestamp.rs b/vortex-array/src/extension/datetime/timestamp.rs index 4dbd0c4cfb4..42f00776216 100644 --- a/vortex-array/src/extension/datetime/timestamp.rs +++ b/vortex-array/src/extension/datetime/timestamp.rs @@ -146,9 +146,8 @@ impl ExtVTable for Timestamp { None => bytes.extend_from_slice(0u16.to_le_bytes().as_slice()), Some(tz) => { let tz_bytes = tz.as_bytes(); - let tz_len = u16::try_from(tz_bytes.len()).unwrap_or_else( - |err| vortex_panic!(Overflow: "tz did not fit in u16: {}", err), - ); + let tz_len = u16::try_from(tz_bytes.len()) + .unwrap_or_else(|err| vortex_panic!("tz did not fit in u16: {}", err)); bytes.extend_from_slice(tz_len.to_le_bytes().as_slice()); bytes.extend_from_slice(tz_bytes); } @@ -160,7 +159,7 @@ impl ExtVTable for Timestamp { fn deserialize_metadata(&self, data: &[u8]) -> VortexResult { vortex_ensure!( data.len() >= 3, - Serde: "Timestamp metadata must have at least 3 bytes, got {}", + "Timestamp metadata must have at least 3 bytes, got {}", data.len() ); @@ -181,13 +180,13 @@ impl ExtVTable for Timestamp { // Attempt to load from len-prefixed bytes vortex_ensure!( data.len() >= 3 + tz_len, - Serde: "Timestamp metadata is truncated: declared timezone length {} but only {} bytes available", + "Timestamp metadata is truncated: declared timezone length {} but only {} bytes available", tz_len, data.len() - 3 ); let tz_bytes = &data[3..3 + tz_len]; let tz: Arc = str::from_utf8(tz_bytes) - .map_err(|e| vortex_err!(Serde: "timezone is not valid utf8 string: {e}"))? + .map_err(|e| vortex_err!("timezone is not valid utf8 string: {e}"))? .to_string() .into(); Ok(TimestampOptions { @@ -199,7 +198,7 @@ impl ExtVTable for Timestamp { fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( matches!(ext_dtype.storage_dtype(), DType::Primitive(PType::I64, _)), - MismatchedTypes: "Timestamp storage dtype must be i64" + "Timestamp storage dtype must be i64" ); Ok(()) } @@ -230,14 +229,14 @@ impl ExtVTable for Timestamp { TimestampValue::Seconds(ts_value, tz), ), TimeUnit::Days => { - vortex_bail!(InvalidArgument: "Timestamp does not support Days time unit") + vortex_bail!("Timestamp does not support Days time unit") } }; // Validate the storage value is within the valid range for Timestamp. jiff::Timestamp::UNIX_EPOCH .checked_add(span) - .map_err(|e| vortex_err!(InvalidArgument: "Invalid timestamp scalar: {}", e))?; + .map_err(|e| vortex_err!("Invalid timestamp scalar: {}", e))?; if let Some(tz) = tz { resolve_time_zone(Some(tz)) diff --git a/vortex-array/src/extension/datetime/unit.rs b/vortex-array/src/extension/datetime/unit.rs index f91025f9f61..7bc7c03121a 100644 --- a/vortex-array/src/extension/datetime/unit.rs +++ b/vortex-array/src/extension/datetime/unit.rs @@ -37,7 +37,7 @@ impl TryFrom for TimeUnit { 2 => Ok(TimeUnit::Milliseconds), 3 => Ok(TimeUnit::Seconds), 4 => Ok(TimeUnit::Days), - _ => vortex_bail!(InvalidArgument: "invalid time unit: {value}u8"), + _ => vortex_bail!("invalid time unit: {value}u8"), } } } diff --git a/vortex-array/src/extension/tests/divisible_int.rs b/vortex-array/src/extension/tests/divisible_int.rs index 8a0d276cfcb..bb035393a91 100644 --- a/vortex-array/src/extension/tests/divisible_int.rs +++ b/vortex-array/src/extension/tests/divisible_int.rs @@ -45,19 +45,19 @@ impl ExtVTable for DivisibleInt { } fn deserialize_metadata(&self, data: &[u8]) -> VortexResult { - vortex_ensure_eq!(data.len(), 8, Serde: "divisible int metadata has the wrong length"); - let bytes: [u8; 8] = data.try_into().map_err( - |_| vortex_error::vortex_err!(Serde: "divisible int metadata must be 8 bytes"), - )?; + vortex_ensure_eq!(data.len(), 8, "divisible int metadata has the wrong length"); + let bytes: [u8; 8] = data + .try_into() + .map_err(|_| vortex_error::vortex_err!("divisible int metadata must be 8 bytes"))?; let n = u64::from_le_bytes(bytes); - vortex_ensure!(n > 0, InvalidArgument: "divisor must be greater than 0"); + vortex_ensure!(n > 0, "divisor must be greater than 0"); Ok(Divisor(n)) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( matches!(ext_dtype.storage_dtype(), DType::Primitive(PType::U64, _)), - MismatchedTypes: "divisible int storage dtype must be u64" + "divisible int storage dtype must be u64" ); Ok(()) } @@ -69,7 +69,7 @@ impl ExtVTable for DivisibleInt { let value = storage_value.as_primitive().cast::()?; let metadata = ext_dtype.metadata(); if value % metadata.0 != 0 { - vortex_bail!(InvalidArgument: "{} is not divisible by {}", value, metadata.0); + vortex_bail!("{} is not divisible by {}", value, metadata.0); } Ok(value) } diff --git a/vortex-array/src/mask.rs b/vortex-array/src/mask.rs index f6a0b70afd4..561bb3ecdc1 100644 --- a/vortex-array/src/mask.rs +++ b/vortex-array/src/mask.rs @@ -24,7 +24,7 @@ impl Executable for Mask { fn execute(array: ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { if !matches!(array.dtype(), DType::Bool(Nullability::NonNullable)) { vortex_bail!( - MismatchedTypes: "Mask array must have boolean(NonNullable) dtype, not {}", + "Mask array must have boolean(NonNullable) dtype, not {}", array.dtype() ); } diff --git a/vortex-array/src/mask_future.rs b/vortex-array/src/mask_future.rs index 2e0ebdb7d6b..802a4bf459d 100644 --- a/vortex-array/src/mask_future.rs +++ b/vortex-array/src/mask_future.rs @@ -33,7 +33,7 @@ impl MaskFuture { .inspect(move |r| { if let Ok(mask) = r && mask.len() != len { - vortex_panic!(AssertionFailed: "MaskFuture created with future that returned mask of incorrect length (expected {}, got {})", len, mask.len()); + vortex_panic!("MaskFuture created with future that returned mask of incorrect length (expected {}, got {})", len, mask.len()); } }) .map_err(Arc::new) diff --git a/vortex-array/src/metadata.rs b/vortex-array/src/metadata.rs index 456b07f81d8..49baf97a19c 100644 --- a/vortex-array/src/metadata.rs +++ b/vortex-array/src/metadata.rs @@ -40,7 +40,7 @@ impl DeserializeMetadata for EmptyMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { if !metadata.is_empty() { - vortex_bail!(AssertionFailed: "EmptyMetadata should not have metadata bytes") + vortex_bail!("EmptyMetadata should not have metadata bytes") } Ok(EmptyMetadata) } diff --git a/vortex-array/src/normalize.rs b/vortex-array/src/normalize.rs index 302ae3d1f47..1204f466c20 100644 --- a/vortex-array/src/normalize.rs +++ b/vortex-array/src/normalize.rs @@ -43,7 +43,7 @@ impl ArrayRef { fn normalize_with_error(&self, allowed: &HashSet) -> VortexResult<()> { if !self.is_allowed_encoding(allowed) { - vortex_bail!(AssertionFailed: "normalize forbids encoding ({})", self.encoding_id()) + vortex_bail!("normalize forbids encoding ({})", self.encoding_id()) } for child in self.children() { diff --git a/vortex-array/src/optimizer/mod.rs b/vortex-array/src/optimizer/mod.rs index 2aa88c7ad8c..1d9c2c87da0 100644 --- a/vortex-array/src/optimizer/mod.rs +++ b/vortex-array/src/optimizer/mod.rs @@ -129,7 +129,7 @@ fn optimize_owned( return Ok((current_array, any_optimizations)); } - vortex_bail!(AssertionFailed: "Exceeded maximum optimization iterations (possible infinite loop)"); + vortex_bail!("Exceeded maximum optimization iterations (possible infinite loop)"); } fn try_session_parent_reduce( diff --git a/vortex-array/src/optimizer/rules.rs b/vortex-array/src/optimizer/rules.rs index 9698fa72807..90c5e4a7381 100644 --- a/vortex-array/src/optimizer/rules.rs +++ b/vortex-array/src/optimizer/rules.rs @@ -194,7 +194,7 @@ impl ParentRuleSet { vortex_error::vortex_ensure_eq!( reduced.len(), parent.len(), - AssertionFailed: "Reduced array length mismatch from {:?}\nFrom:\n{}\nTo:\n{}", + "Reduced array length mismatch from {:?}\nFrom:\n{}\nTo:\n{}", rule, parent.encoding_id(), reduced.encoding_id() @@ -202,7 +202,7 @@ impl ParentRuleSet { vortex_error::vortex_ensure_eq!( reduced.dtype(), parent.dtype(), - AssertionFailed: "Reduced array dtype mismatch from {:?}\nFrom:\n{}\nTo:\n{}", + "Reduced array dtype mismatch from {:?}\nFrom:\n{}\nTo:\n{}", rule, parent.encoding_id(), reduced.encoding_id() diff --git a/vortex-array/src/patches.rs b/vortex-array/src/patches.rs index 7773f5ef17e..3dab7b37c3d 100644 --- a/vortex-array/src/patches.rs +++ b/vortex-array/src/patches.rs @@ -87,7 +87,7 @@ impl PatchesMetadata { #[inline] pub fn len(&self) -> VortexResult { - usize::try_from(self.len).map_err(|_| vortex_err!(Overflow: "len does not fit in usize")) + usize::try_from(self.len).map_err(|_| vortex_err!("len does not fit in usize")) } #[inline] @@ -97,8 +97,7 @@ impl PatchesMetadata { #[inline] pub fn offset(&self) -> VortexResult { - usize::try_from(self.offset) - .map_err(|_| vortex_err!(Overflow: "offset does not fit in usize")) + usize::try_from(self.offset).map_err(|_| vortex_err!("offset does not fit in usize")) } #[inline] @@ -106,9 +105,7 @@ impl PatchesMetadata { self.chunk_offsets_ptype .map(|t| { PType::try_from(t) - .map_err( - |e| vortex_err!(InvalidArgument: "invalid i32 value {t} for PType: {}", e), - ) + .map_err(|e| vortex_err!("invalid i32 value {t} for PType: {}", e)) .map(|ptype| DType::Primitive(ptype, NonNullable)) }) .transpose() @@ -116,12 +113,12 @@ impl PatchesMetadata { #[inline] pub fn indices_dtype(&self) -> VortexResult { - let ptype = PType::try_from(self.indices_ptype).map_err(|e| { - vortex_err!(InvalidArgument: "invalid i32 value {} for PType: {}", self.indices_ptype, e) + let ptype = PType::try_from(self.indices_ptype).map_err(|e| { + vortex_err!("invalid i32 value {} for PType: {}", self.indices_ptype, e) })?; vortex_ensure!( ptype.is_unsigned_int(), - MismatchedTypes: "Patch indices must be unsigned integers" + "Patch indices must be unsigned integers" ); Ok(DType::Primitive(ptype, NonNullable)) } @@ -249,27 +246,27 @@ impl Patches { chunk_offsets: Option, ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_ensure_eq!(indices.len(), values.len(), InvalidArgument); + vortex_ensure_eq!(indices.len(), values.len()); vortex_ensure!( indices.dtype().is_unsigned_int() && !indices.dtype().is_nullable(), - MismatchedTypes: "Patch indices must be non-nullable unsigned integers, got {:?}", + "Patch indices must be non-nullable unsigned integers, got {:?}", indices.dtype() ); vortex_ensure!( indices.len() <= array_len, - InvalidArgument: "Patch indices must be shorter than the array length" + "Patch indices must be shorter than the array length" ); - vortex_ensure!(!indices.is_empty(), InvalidArgument: "Patch indices must not be empty"); + vortex_ensure!(!indices.is_empty(), "Patch indices must not be empty"); // Perform validation of components when they are host-resident. // This is not possible to do eagerly when the data is on GPU memory. if indices.is_host() && values.is_host() { let max = usize::try_from(&indices.execute_scalar(indices.len() - 1, ctx)?) - .map_err(|_| vortex_err!(InvalidArgument: "indices must be a number"))?; + .map_err(|_| vortex_err!("indices must be a number"))?; vortex_ensure!( max - offset < array_len, - OutOfBounds: "Patch indices {max:?}, offset {offset} are longer than the array length {array_len}" + "Patch indices {max:?}, offset {offset} are longer than the array length {array_len}" ); #[cfg(debug_assertions)] @@ -379,14 +376,14 @@ impl Patches { #[inline] pub fn chunk_offset_at(&self, idx: usize, ctx: &mut ExecutionCtx) -> VortexResult { let Some(chunk_offsets) = &self.chunk_offsets else { - vortex_bail!(InvalidArgument: "chunk_offsets must be set to retrieve offset at index") + vortex_bail!("chunk_offsets must be set to retrieve offset at index") }; chunk_offsets .execute_scalar(idx, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(Overflow: "chunk offset does not fit in usize")) + .ok_or_else(|| vortex_err!("chunk offset does not fit in usize")) } /// Returns the number of patches sliced off from the current first chunk. @@ -405,20 +402,20 @@ impl Patches { #[inline] pub fn indices_ptype(&self) -> VortexResult { PType::try_from(self.indices.dtype()) - .map_err(|_| vortex_err!(MismatchedTypes: "indices dtype is not primitive")) + .map_err(|_| vortex_err!("indices dtype is not primitive")) } pub fn to_metadata(&self, len: usize, dtype: &DType) -> VortexResult { if self.indices.len() > len { vortex_bail!( - InvalidArgument: "Patch indices {} are longer than the array length {}", + "Patch indices {} are longer than the array length {}", self.indices.len(), len ); } if self.values.dtype() != dtype { vortex_bail!( - MismatchedTypes: "Patch values dtype {} does not match array dtype {}", + "Patch values dtype {} does not match array dtype {}", self.values.dtype(), dtype ); @@ -488,11 +485,11 @@ impl Patches { ctx: &mut ExecutionCtx, ) -> VortexResult { let Some(chunk_offsets) = &self.chunk_offsets else { - vortex_bail!(InvalidArgument: "chunk_offsets is required to be set") + vortex_bail!("chunk_offsets is required to be set") }; let Some(offset_within_chunk) = self.offset_within_chunk else { - vortex_bail!(InvalidArgument: "offset_within_chunk is required to be set") + vortex_bail!("offset_within_chunk is required to be set") }; if index >= self.array_len() { @@ -509,7 +506,7 @@ impl Patches { .execute_scalar(idx, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(Overflow: "chunk offset does not fit in usize")) + .ok_or_else(|| vortex_err!("chunk offset does not fit in usize")) }; // Patch index offsets are absolute and need to be offset by the first chunk of the current slice. @@ -559,7 +556,7 @@ impl Patches { usize: TryFrom, { let Some(offset_within_chunk) = self.offset_within_chunk else { - vortex_bail!(InvalidArgument: "offset_within_chunk is required to be set") + vortex_bail!("offset_within_chunk is required to be set") }; let chunk_idx = { @@ -577,7 +574,7 @@ impl Patches { // Patch index offsets are absolute and need to be offset by the first chunk of the current slice. let chunk_offset = usize::try_from(chunk_offsets[chunk_idx] - chunk_offsets[0]) - .map_err(|_| vortex_err!(Overflow: "chunk_offset failed to convert to usize"))?; + .map_err(|_| vortex_err!("chunk_offset failed to convert to usize"))?; let patches_start_idx = chunk_offset // Chunk offsets are only sliced off in case the slice is fully @@ -590,7 +587,7 @@ impl Patches { let patches_end_idx = if chunk_idx < chunk_offsets.len() - 1 { usize::try_from(chunk_offsets[chunk_idx + 1] - chunk_offsets[0]) - .map_err(|_| vortex_err!(Overflow: "patches_end_idx failed to convert to usize"))? + .map_err(|_| vortex_err!("patches_end_idx failed to convert to usize"))? .saturating_sub(offset_within_chunk) .min(indices.len()) } else { @@ -618,7 +615,7 @@ impl Patches { .execute_scalar(0, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(Overflow: "index does not fit in usize"))?; + .ok_or_else(|| vortex_err!("index does not fit in usize"))?; Ok(first - self.offset) } @@ -629,7 +626,7 @@ impl Patches { .execute_scalar(self.indices.len() - 1, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(Overflow: "index does not fit in usize"))?; + .ok_or_else(|| vortex_err!("index does not fit in usize"))?; Ok(last - self.offset) } @@ -637,7 +634,7 @@ impl Patches { pub fn filter(&self, mask: &Mask, ctx: &mut ExecutionCtx) -> VortexResult> { if mask.len() != self.array_len { vortex_bail!( - MismatchedTypes: "Filter mask length {} does not match array length {}", + "Filter mask length {} does not match array length {}", mask.len(), self.array_len ); @@ -672,7 +669,7 @@ impl Patches { pub fn mask(&self, mask: &Mask, ctx: &mut ExecutionCtx) -> VortexResult> { if mask.len() != self.array_len { vortex_bail!( - MismatchedTypes: "Filter mask length {} does not match array length {}", + "Filter mask length {} does not match array length {}", mask.len(), self.array_len ); @@ -761,7 +758,7 @@ impl Patches { .execute_scalar(0, ctx)? .as_primitive() .as_::() - .ok_or_else(|| vortex_err!(Overflow: "chunk offset does not fit in usize"))?; + .ok_or_else(|| vortex_err!("chunk offset does not fit in usize"))?; let parent_chunk_base = self.chunk_offset_at(0, ctx)?; let parent_within = self.offset_within_chunk.unwrap_or(0); Ok(parent_chunk_base + parent_within + slice_start_idx - new_chunk_base) @@ -979,7 +976,7 @@ impl Patches { let values = f(self.values)?; if self.indices.len() != values.len() { vortex_bail!( - InvalidArgument: "map_values must preserve length: expected {} received {}", + "map_values must preserve length: expected {} received {}", self.indices.len(), values.len() ) @@ -1068,7 +1065,7 @@ where for (idx_in_take, &take_idx) in take_indices.iter().enumerate() { let ti = usize::try_from(take_idx) - .map_err(|_| vortex_err!(Overflow: "Failed to convert index to usize"))?; + .map_err(|_| vortex_err!("Failed to convert index to usize"))?; // If we have to take nulls the take index doesn't matter, make it 0 for consistency let is_null = match take_validity.bit_buffer() { @@ -1083,7 +1080,7 @@ where } } else if ti >= min_index && ti <= max_index { let ti_as_i = I::try_from(ti) - .map_err(|_| vortex_err!(Overflow: "take index does not fit in index type"))?; + .map_err(|_| vortex_err!("take index does not fit in index type"))?; if let Some(&value_index) = sparse_index_to_value_index.get(&ti_as_i) { new_sparse_indices.push(idx_in_take as u64); value_indices.push(value_index as u64); @@ -1312,7 +1309,7 @@ fn rank_patches_in_mask_bitmap( fn patch_index_to_usize(patch_index: T, offset: usize) -> VortexResult { Ok(patch_index .to_usize() - .ok_or_else(|| vortex_err!(Overflow: "patch index does not fit in usize"))? + .ok_or_else(|| vortex_err!("patch index does not fit in usize"))? - offset) } diff --git a/vortex-array/src/scalar/cast.rs b/vortex-array/src/scalar/cast.rs index c52c22fa5c2..8e57cb68fff 100644 --- a/vortex-array/src/scalar/cast.rs +++ b/vortex-array/src/scalar/cast.rs @@ -37,7 +37,7 @@ impl Scalar { && !source.keys_sorted() { return Err(vortex_err!( - MismatchedTypes: "Cannot cast {} to {target_dtype}: source does not assert sorted map keys", + "Cannot cast {} to {target_dtype}: source does not assert sorted map keys", self.dtype() )); } @@ -47,7 +47,7 @@ impl Scalar { if self.value().is_none() || matches!(self.dtype(), DType::Null) { vortex_ensure!( target_dtype.is_nullable(), - InvalidArgument: "Cannot cast null to {target_dtype}: target type is non-nullable" + "Cannot cast null to {target_dtype}: target type is non-nullable" ); return Scalar::try_new(target_dtype.clone(), self.value().cloned()); @@ -63,25 +63,25 @@ impl Scalar { match &self.dtype() { DType::Null => unreachable!("Handled by the if case above"), DType::Bool(_) => vortex_bail!( - MismatchedTypes: "Cannot cast bool to {target_dtype}: boolean scalars can only be cast to boolean types with different nullability" + "Cannot cast bool to {target_dtype}: boolean scalars can only be cast to boolean types with different nullability" ), DType::Primitive(..) => self.as_primitive().cast(target_dtype), DType::Decimal(..) => self.as_decimal().cast(target_dtype), DType::Utf8(_) => vortex_bail!( - MismatchedTypes: "Cannot cast utf8 to {target_dtype}: UTF-8 scalars can only be cast to UTF-8 types with different nullability" + "Cannot cast utf8 to {target_dtype}: UTF-8 scalars can only be cast to UTF-8 types with different nullability" ), DType::Binary(_) => vortex_bail!( - MismatchedTypes: "Cannot cast binary to {target_dtype}: binary scalars can only be cast to binary types with different nullability" + "Cannot cast binary to {target_dtype}: binary scalars can only be cast to binary types with different nullability" ), DType::List(..) | DType::FixedSizeList(..) => self.as_list().cast(target_dtype), DType::Map(..) => self.as_map().cast(target_dtype), DType::Struct(..) => self.as_struct().cast(target_dtype), DType::Union(..) => vortex_bail!( - InvalidArgument: "union scalar cast from {} to {target_dtype} is not supported (yet)", + "union scalar cast from {} to {target_dtype} is not supported (yet)", self.dtype() ), DType::Variant(_) => { - vortex_bail!(NotImplemented: "Variant scalars can't be cast to {target_dtype}") + vortex_bail!("Variant scalars can't be cast to {target_dtype}") } DType::Extension(..) => self.as_extension().cast(target_dtype), } diff --git a/vortex-array/src/scalar/constructor.rs b/vortex-array/src/scalar/constructor.rs index ab5d8bff117..81f72054696 100644 --- a/vortex-array/src/scalar/constructor.rs +++ b/vortex-array/src/scalar/constructor.rs @@ -170,9 +170,9 @@ impl Scalar { dtype: DType, entries: impl IntoIterator, ) -> VortexResult { - let map = dtype.as_map_opt().ok_or_else( - || vortex_error::vortex_err!(InvalidArgument: "Expected map dtype, found {dtype}"), - )?; + let map = dtype + .as_map_opt() + .ok_or_else(|| vortex_error::vortex_err!("Expected map dtype, found {dtype}"))?; let key_dtype = map.key_dtype(); let value_dtype = map.value_dtype(); @@ -182,13 +182,13 @@ impl Scalar { .map(|(index, (key, value))| { if key.dtype() != &key_dtype { vortex_bail!( - MismatchedTypes: "map entry {index} expected key dtype {key_dtype}, got {}", + "map entry {index} expected key dtype {key_dtype}, got {}", key.dtype() ); } if value.dtype() != &value_dtype { vortex_bail!( - MismatchedTypes: "map entry {index} expected value dtype {value_dtype}, got {}", + "map entry {index} expected value dtype {value_dtype}, got {}", value.dtype() ); } @@ -217,7 +217,7 @@ impl Scalar { .map(|child| { if child.dtype() != &*element_dtype { vortex_panic!( - MismatchedTypes: "tried to create list of {} with values of type {}", + "tried to create list of {} with values of type {}", element_dtype, child.dtype() ); @@ -278,7 +278,7 @@ impl Scalar { ) -> VortexResult { let child_index = variants.tag_to_child_index(type_id).ok_or_else(|| { vortex_err!( - NotFound: "union type ID {type_id} is not present in {:?}", + "union type ID {type_id} is not present in {:?}", variants.type_ids() ) })?; @@ -290,7 +290,7 @@ impl Scalar { vortex_ensure_eq!( child.dtype(), &expected_dtype, - MismatchedTypes: "union type ID {type_id} selects a different child dtype" + "union type ID {type_id} selects a different child dtype" ); Self::try_new( diff --git a/vortex-array/src/scalar/convert/decimal.rs b/vortex-array/src/scalar/convert/decimal.rs index 4286b167cfd..71134b4be88 100644 --- a/vortex-array/src/scalar/convert/decimal.rs +++ b/vortex-array/src/scalar/convert/decimal.rs @@ -36,7 +36,7 @@ macro_rules! decimal_scalar_unpack { None => None, Some(DecimalValue::$arm(v)) => Some(v), v => vortex_error::vortex_bail!( - MismatchedTypes: "Cannot extract decimal {:?} as {}", + "Cannot extract decimal {:?} as {}", v, stringify!($T) ), @@ -49,10 +49,10 @@ macro_rules! decimal_scalar_unpack { fn try_from(value: DecimalScalar) -> Result { match value.decimal_value() { - None => vortex_error::vortex_bail!(InvalidArgument: "Cannot extract value from null decimal"), + None => vortex_error::vortex_bail!("Cannot extract value from null decimal"), Some(DecimalValue::$arm(v)) => Ok(v), v => vortex_error::vortex_bail!( - MismatchedTypes: "Cannot extract decimal {:?} as {}", + "Cannot extract decimal {:?} as {}", v, stringify!($T) ), @@ -96,13 +96,15 @@ impl TryFrom<&Scalar> for DecimalValue { type Error = VortexError; fn try_from(scalar: &Scalar) -> Result { - let decimal_scalar = scalar.as_decimal_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected decimal scalar, found {}", scalar.dtype()), - )?; + let decimal_scalar = scalar + .as_decimal_opt() + .ok_or_else(|| vortex_err!("Expected decimal scalar, found {}", scalar.dtype()))?; - decimal_scalar.decimal_value().as_ref().cloned().ok_or_else( - || vortex_err!(InvalidArgument: "Cannot extract DecimalValue from null decimal"), - ) + decimal_scalar + .decimal_value() + .as_ref() + .cloned() + .ok_or_else(|| vortex_err!("Cannot extract DecimalValue from null decimal")) } } @@ -120,7 +122,7 @@ impl TryFrom<&Scalar> for Option { fn try_from(scalar: &Scalar) -> Result { Ok(scalar .as_decimal_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected decimal scalar, found {}", scalar.dtype()))? + .ok_or_else(|| vortex_err!("Expected decimal scalar, found {}", scalar.dtype()))? .decimal_value()) } } diff --git a/vortex-array/src/scalar/convert/from_scalar.rs b/vortex-array/src/scalar/convert/from_scalar.rs index fc3f010ea9c..77b35ad3f28 100644 --- a/vortex-array/src/scalar/convert/from_scalar.rs +++ b/vortex-array/src/scalar/convert/from_scalar.rs @@ -30,9 +30,9 @@ impl<'a> TryFrom<&'a Scalar> for BoolScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_bool_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected bool scalar, found {}", value.dtype()), - ) + value + .as_bool_opt() + .ok_or_else(|| vortex_err!("Expected bool scalar, found {}", value.dtype())) } } @@ -40,9 +40,9 @@ impl<'a> TryFrom<&'a Scalar> for PrimitiveScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_primitive_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected primitive scalar, found {}", value.dtype()), - ) + value + .as_primitive_opt() + .ok_or_else(|| vortex_err!("Expected primitive scalar, found {}", value.dtype())) } } @@ -50,9 +50,9 @@ impl<'a> TryFrom<&'a Scalar> for DecimalScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_decimal_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected decimal scalar, found {}", value.dtype()), - ) + value + .as_decimal_opt() + .ok_or_else(|| vortex_err!("Expected decimal scalar, found {}", value.dtype())) } } @@ -60,9 +60,9 @@ impl<'a> TryFrom<&'a Scalar> for Utf8Scalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_utf8_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected utf8 scalar, found {}", value.dtype()), - ) + value + .as_utf8_opt() + .ok_or_else(|| vortex_err!("Expected utf8 scalar, found {}", value.dtype())) } } @@ -70,9 +70,9 @@ impl<'a> TryFrom<&'a Scalar> for BinaryScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_binary_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected binary scalar, found {}", value.dtype()), - ) + value + .as_binary_opt() + .ok_or_else(|| vortex_err!("Expected binary scalar, found {}", value.dtype())) } } @@ -80,9 +80,9 @@ impl<'a> TryFrom<&'a Scalar> for StructScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_struct_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected struct scalar, found {}", value.dtype()), - ) + value + .as_struct_opt() + .ok_or_else(|| vortex_err!("Expected struct scalar, found {}", value.dtype())) } } @@ -90,9 +90,9 @@ impl<'a> TryFrom<&'a Scalar> for ListScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_list_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected list scalar, found {}", value.dtype()), - ) + value + .as_list_opt() + .ok_or_else(|| vortex_err!("Expected list scalar, found {}", value.dtype())) } } @@ -100,9 +100,9 @@ impl<'a> TryFrom<&'a Scalar> for MapScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_map_opt().ok_or_else( - || vortex_err!(InvalidArgument: "Expected map scalar, found {}", value.dtype()), - ) + value + .as_map_opt() + .ok_or_else(|| vortex_err!("Expected map scalar, found {}", value.dtype())) } } @@ -110,9 +110,9 @@ impl<'a> TryFrom<&'a Scalar> for ExtScalar<'a> { type Error = VortexError; fn try_from(value: &'a Scalar) -> VortexResult { - value.as_extension_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected extension scalar, found {}", value.dtype()), - ) + value + .as_extension_opt() + .ok_or_else(|| vortex_err!("Expected extension scalar, found {}", value.dtype())) } } @@ -126,13 +126,9 @@ impl TryFrom<&Scalar> for bool { fn try_from(value: &Scalar) -> VortexResult { value .as_bool_opt() - .ok_or_else( - || vortex_err!(MismatchedTypes: "Expected bool scalar, found {}", value.dtype()), - )? + .ok_or_else(|| vortex_err!("Expected bool scalar, found {}", value.dtype()))? .value() - .ok_or_else( - || vortex_err!(InvalidArgument: "Can't extract present value from null scalar"), - ) + .ok_or_else(|| vortex_err!("Can't extract present value from null scalar")) } } @@ -142,9 +138,7 @@ impl TryFrom<&Scalar> for Option { fn try_from(value: &Scalar) -> VortexResult { Ok(value .as_bool_opt() - .ok_or_else( - || vortex_err!(MismatchedTypes: "Expected bool scalar, found {}", value.dtype()), - )? + .ok_or_else(|| vortex_err!("Expected bool scalar, found {}", value.dtype()))? .value()) } } @@ -173,13 +167,14 @@ impl<'a> TryFrom<&'a Scalar> for ByteBuffer { type Error = VortexError; fn try_from(scalar: &'a Scalar) -> VortexResult { - let binary = scalar.as_binary_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Cannot extract buffer from non-buffer scalar"), - )?; + let binary = scalar + .as_binary_opt() + .ok_or_else(|| vortex_err!("Cannot extract buffer from non-buffer scalar"))?; - binary.value().cloned().ok_or_else( - || vortex_err!(InvalidArgument: "Cannot extract present value from null scalar"), - ) + binary + .value() + .cloned() + .ok_or_else(|| vortex_err!("Cannot extract present value from null scalar")) } } @@ -189,9 +184,7 @@ impl<'a> TryFrom<&'a Scalar> for Option { fn try_from(scalar: &'a Scalar) -> VortexResult { Ok(scalar .as_binary_opt() - .ok_or_else( - || vortex_err!(MismatchedTypes: "Cannot extract buffer from non-buffer scalar"), - )? + .ok_or_else(|| vortex_err!("Cannot extract buffer from non-buffer scalar"))? .value() .cloned()) } @@ -237,9 +230,8 @@ impl<'a> TryFrom<&'a Scalar> for BufferString { type Error = VortexError; fn try_from(scalar: &'a Scalar) -> VortexResult { - >::try_from(scalar)?.ok_or_else( - || vortex_err!(InvalidArgument: "Can't extract present value from null scalar"), - ) + >::try_from(scalar)? + .ok_or_else(|| vortex_err!("Can't extract present value from null scalar")) } } @@ -257,9 +249,7 @@ impl<'a> TryFrom<&'a Scalar> for Option { fn try_from(scalar: &'a Scalar) -> Result { Ok(scalar .as_utf8_opt() - .ok_or_else( - || vortex_err!(MismatchedTypes: "Expected utf8 scalar, found {}", scalar.dtype()), - )? + .ok_or_else(|| vortex_err!("Expected utf8 scalar, found {}", scalar.dtype()))? .value() .cloned()) } @@ -297,11 +287,9 @@ where fn try_from(value: &'a Scalar) -> Result { value .as_list_opt() - .ok_or_else( - || vortex_err!(MismatchedTypes: "Expected list scalar, found {}", value.dtype()), - )? + .ok_or_else(|| vortex_err!("Expected list scalar, found {}", value.dtype()))? .elements() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null list"))? + .ok_or_else(|| vortex_err!("Expected non-null list"))? .into_iter() .map(|e| T::try_from(&e)) .collect::>>() diff --git a/vortex-array/src/scalar/convert/primitive.rs b/vortex-array/src/scalar/convert/primitive.rs index 4f62e5372e8..0bf3ec87714 100644 --- a/vortex-array/src/scalar/convert/primitive.rs +++ b/vortex-array/src/scalar/convert/primitive.rs @@ -65,10 +65,10 @@ macro_rules! primitive_scalar { match value.value() { Some(ScalarValue::Primitive(pv)) => pv.cast::<$T>(), Some(_) => Err(vortex_err!( - MismatchedTypes: "Expected primitive scalar, found {}", + "Expected primitive scalar, found {}", value.dtype() )), - None => Err(vortex_err!(InvalidArgument: "Can't extract present value from null scalar")), + None => Err(vortex_err!("Can't extract present value from null scalar")), } } } @@ -166,13 +166,13 @@ impl TryFrom<&Scalar> for usize { type Error = VortexError; fn try_from(value: &Scalar) -> Result { - let prim_scalar = value.as_primitive_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected primitive scalar, found {}", value.dtype()), - )?; + let prim_scalar = value + .as_primitive_opt() + .ok_or_else(|| vortex_err!("Expected primitive scalar, found {}", value.dtype()))?; let prim = prim_scalar .as_::() - .ok_or_else(|| vortex_err!(Overflow: "cannot convert Null to usize"))?; + .ok_or_else(|| vortex_err!("cannot convert Null to usize"))?; Ok(usize::try_from(prim)?) } @@ -182,9 +182,9 @@ impl TryFrom<&Scalar> for Option { type Error = VortexError; fn try_from(value: &Scalar) -> Result { - let prim_scalar = value.as_primitive_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Expected primitive scalar, found {}", value.dtype()), - )?; + let prim_scalar = value + .as_primitive_opt() + .ok_or_else(|| vortex_err!("Expected primitive scalar, found {}", value.dtype()))?; Ok(prim_scalar.as_::().map(usize::try_from).transpose()?) } diff --git a/vortex-array/src/scalar/downcast.rs b/vortex-array/src/scalar/downcast.rs index 4a5d1d48e5d..91d17e14109 100644 --- a/vortex-array/src/scalar/downcast.rs +++ b/vortex-array/src/scalar/downcast.rs @@ -221,7 +221,7 @@ impl ScalarValue { pub fn as_bool(&self) -> bool { match self { ScalarValue::Bool(b) => *b, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Bool"), + _ => vortex_panic!("ScalarValue is not a Bool"), } } @@ -230,7 +230,7 @@ impl ScalarValue { pub fn as_primitive(&self) -> &PValue { match self { ScalarValue::Primitive(p) => p, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Primitive"), + _ => vortex_panic!("ScalarValue is not a Primitive"), } } @@ -239,7 +239,7 @@ impl ScalarValue { pub fn as_decimal(&self) -> &DecimalValue { match self { ScalarValue::Decimal(d) => d, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Decimal"), + _ => vortex_panic!("ScalarValue is not a Decimal"), } } @@ -247,7 +247,7 @@ impl ScalarValue { pub fn as_utf8(&self) -> &BufferString { match self { ScalarValue::Utf8(s) => s, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Utf8"), + _ => vortex_panic!("ScalarValue is not a Utf8"), } } @@ -255,7 +255,7 @@ impl ScalarValue { pub fn as_binary(&self) -> &ByteBuffer { match self { ScalarValue::Binary(b) => b, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Binary"), + _ => vortex_panic!("ScalarValue is not a Binary"), } } @@ -263,7 +263,7 @@ impl ScalarValue { pub fn as_list(&self) -> &[Option] { match self { ScalarValue::Tuple(elements) => elements, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Tuple"), + _ => vortex_panic!("ScalarValue is not a Tuple"), } } @@ -271,7 +271,7 @@ impl ScalarValue { pub fn into_bool(self) -> bool { match self { ScalarValue::Bool(b) => b, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Bool"), + _ => vortex_panic!("ScalarValue is not a Bool"), } } @@ -280,7 +280,7 @@ impl ScalarValue { pub fn into_primitive(self) -> PValue { match self { ScalarValue::Primitive(p) => p, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Primitive"), + _ => vortex_panic!("ScalarValue is not a Primitive"), } } @@ -289,7 +289,7 @@ impl ScalarValue { pub fn into_decimal(self) -> DecimalValue { match self { ScalarValue::Decimal(d) => d, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Decimal"), + _ => vortex_panic!("ScalarValue is not a Decimal"), } } @@ -297,7 +297,7 @@ impl ScalarValue { pub fn into_utf8(self) -> BufferString { match self { ScalarValue::Utf8(s) => s, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Utf8"), + _ => vortex_panic!("ScalarValue is not a Utf8"), } } @@ -305,7 +305,7 @@ impl ScalarValue { pub fn into_binary(self) -> ByteBuffer { match self { ScalarValue::Binary(b) => b, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Binary"), + _ => vortex_panic!("ScalarValue is not a Binary"), } } @@ -313,7 +313,7 @@ impl ScalarValue { pub fn into_list(self) -> Vec> { match self { ScalarValue::Tuple(elements) => elements, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Tuple"), + _ => vortex_panic!("ScalarValue is not a Tuple"), } } @@ -321,7 +321,7 @@ impl ScalarValue { pub fn as_union(&self) -> &UnionValue { match self { ScalarValue::Union(value) => value, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Union"), + _ => vortex_panic!("ScalarValue is not a Union"), } } @@ -329,7 +329,7 @@ impl ScalarValue { pub fn into_union(self) -> UnionValue { match self { ScalarValue::Union(value) => value, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Union"), + _ => vortex_panic!("ScalarValue is not a Union"), } } @@ -338,7 +338,7 @@ impl ScalarValue { pub fn as_variant(&self) -> &Scalar { match self { ScalarValue::Variant(value) => value, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Variant"), + _ => vortex_panic!("ScalarValue is not a Variant"), } } @@ -347,7 +347,7 @@ impl ScalarValue { pub fn into_variant(self) -> Scalar { match self { ScalarValue::Variant(value) => *value, - _ => vortex_panic!(MismatchedTypes: "ScalarValue is not a Variant"), + _ => vortex_panic!("ScalarValue is not a Variant"), } } } diff --git a/vortex-array/src/scalar/proto.rs b/vortex-array/src/scalar/proto.rs index 8bbb0e841a3..2c29e08a37f 100644 --- a/vortex-array/src/scalar/proto.rs +++ b/vortex-array/src/scalar/proto.rs @@ -199,14 +199,14 @@ impl Scalar { value .dtype .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Scalar missing dtype"))?, + .ok_or_else(|| vortex_err!("Scalar missing dtype"))?, session, )?; let pb_scalar_value: &pb::ScalarValue = value .value .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Scalar missing value"))?; + .ok_or_else(|| vortex_err!("Scalar missing value"))?; let value: Option = ScalarValue::from_proto(pb_scalar_value, &dtype, session)?; @@ -248,7 +248,7 @@ impl ScalarValue { let kind = value .kind .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Scalar value missing kind"))?; + .ok_or_else(|| vortex_err!("Scalar value missing kind"))?; // `DType::Extension` store their serialized values using the storage `DType`. let dtype = match dtype { @@ -272,7 +272,7 @@ impl ScalarValue { DType::Variant(_) => Some(ScalarValue::Variant(Box::new(Scalar::from_proto( v, session, )?))), - _ => vortex_bail!(Serde: "expected non-Variant scalar proto for dtype {dtype}"), + _ => vortex_bail!("expected non-Variant scalar proto for dtype {dtype}"), }, }) } @@ -282,7 +282,7 @@ impl ScalarValue { fn bool_from_proto(v: bool, dtype: &DType) -> VortexResult { vortex_ensure!( dtype.is_boolean(), - Serde: "expected Bool dtype for BoolValue, got {dtype}" + "expected Bool dtype for BoolValue, got {dtype}" ); Ok(ScalarValue::Bool(v)) @@ -295,7 +295,7 @@ fn bool_from_proto(v: bool, dtype: &DType) -> VortexResult { fn int64_from_proto(v: i64, dtype: &DType) -> VortexResult { vortex_ensure!( dtype.is_primitive(), - Serde: "expected Primitive dtype for Int64Value, got {dtype}" + "expected Primitive dtype for Int64Value, got {dtype}" ); let pvalue = match dtype.as_ptype() { @@ -310,10 +310,10 @@ fn int64_from_proto(v: i64, dtype: &DType) -> VortexResult { PType::U32 => v.to_u32().map(PValue::U32), PType::U64 => v.to_u64().map(PValue::U64), ftype @ (PType::F16 | PType::F32 | PType::F64) => vortex_bail!( - Serde: "expected signed integer ptype for serialized Int64Value, got float {ftype}" + "expected signed integer ptype for serialized Int64Value, got float {ftype}" ), } - .ok_or_else(|| vortex_err!(Serde: "Int64 value {v} out of range for dtype {dtype}"))?; + .ok_or_else(|| vortex_err!("Int64 value {v} out of range for dtype {dtype}"))?; Ok(ScalarValue::Primitive(pvalue)) } @@ -326,7 +326,7 @@ fn int64_from_proto(v: i64, dtype: &DType) -> VortexResult { fn uint64_from_proto(v: u64, dtype: &DType) -> VortexResult { vortex_ensure!( dtype.is_primitive(), - Serde: "expected Primitive dtype for Uint64Value, got {dtype}" + "expected Primitive dtype for Uint64Value, got {dtype}" ); let pvalue = match dtype.as_ptype() { @@ -342,11 +342,11 @@ fn uint64_from_proto(v: u64, dtype: &DType) -> VortexResult { PType::I64 => v.to_i64().map(PValue::I64), // f16 values used to be serialized as u64, so we need to be able to read an f16 from a u64. PType::F16 => v.to_u16().map(f16::from_bits).map(PValue::F16), - ftype @ (PType::F32 | PType::F64) => vortex_bail!( - Serde: "expected unsigned integer ptype for serialized Uint64Value, got {ftype}" - ), + ftype @ (PType::F32 | PType::F64) => { + vortex_bail!("expected unsigned integer ptype for serialized Uint64Value, got {ftype}") + } } - .ok_or_else(|| vortex_err!(Serde: "Uint64 value {v} out of range for dtype {dtype}"))?; + .ok_or_else(|| vortex_err!("Uint64 value {v} out of range for dtype {dtype}"))?; Ok(ScalarValue::Primitive(pvalue)) } @@ -355,11 +355,11 @@ fn uint64_from_proto(v: u64, dtype: &DType) -> VortexResult { fn f16_from_proto(v: u64, dtype: &DType) -> VortexResult { vortex_ensure!( matches!(dtype, DType::Primitive(PType::F16, _)), - Serde: "expected F16 dtype for F16Value, got {dtype}" + "expected F16 dtype for F16Value, got {dtype}" ); let bits = u16::try_from(v) - .map_err(|_| vortex_err!(Serde: "f16 bitwise representation has more than 16 bits: {v}"))?; + .map_err(|_| vortex_err!("f16 bitwise representation has more than 16 bits: {v}"))?; Ok(ScalarValue::Primitive(PValue::F16(f16::from_bits(bits)))) } @@ -368,7 +368,7 @@ fn f16_from_proto(v: u64, dtype: &DType) -> VortexResult { fn f32_from_proto(v: f32, dtype: &DType) -> VortexResult { vortex_ensure!( matches!(dtype, DType::Primitive(PType::F32, _)), - Serde: "expected F32 dtype for F32Value, got {dtype}" + "expected F32 dtype for F32Value, got {dtype}" ); Ok(ScalarValue::Primitive(PValue::F32(v))) @@ -378,7 +378,7 @@ fn f32_from_proto(v: f32, dtype: &DType) -> VortexResult { fn f64_from_proto(v: f64, dtype: &DType) -> VortexResult { vortex_ensure!( matches!(dtype, DType::Primitive(PType::F64, _)), - Serde: "expected F64 dtype for F64Value, got {dtype}" + "expected F64 dtype for F64Value, got {dtype}" ); Ok(ScalarValue::Primitive(PValue::F64(v))) @@ -390,9 +390,7 @@ fn string_from_proto(s: &str, dtype: &DType) -> VortexResult { match dtype { DType::Utf8(_) => Ok(ScalarValue::Utf8(BufferString::from(s))), DType::Binary(_) => Ok(ScalarValue::Binary(ByteBuffer::copy_from(s.as_bytes()))), - _ => vortex_bail!( - Serde: "expected Utf8 or Binary dtype for StringValue, got {dtype}" - ), + _ => vortex_bail!("expected Utf8 or Binary dtype for StringValue, got {dtype}"), } } @@ -437,11 +435,9 @@ fn bytes_from_proto(bytes: &[u8], dtype: &DType) -> VortexResult { .ok() .vortex_expect("Buffer has invalid number of bytes"), )), - l => vortex_bail!(Serde: "invalid decimal byte length: {l}"), + l => vortex_bail!("invalid decimal byte length: {l}"), })), - _ => vortex_bail!( - Serde: "expected Utf8, Binary, or Decimal dtype for BytesValue, got {dtype}" - ), + _ => vortex_bail!("expected Utf8, Binary, or Decimal dtype for BytesValue, got {dtype}"), } } @@ -461,7 +457,7 @@ fn list_from_proto( vortex_ensure_eq!( v.values.len(), fields.nfields(), - Serde: "ListValue has the wrong number of struct fields" + "ListValue has the wrong number of struct fields" ); v.values @@ -477,9 +473,7 @@ fn list_from_proto( .map(|entry| ScalarValue::from_proto(entry, &entry_dtype, session)) .collect::>>()? } - _ => vortex_bail!( - Serde: "expected a tuple-backed dtype for ListValue, got {dtype}" - ), + _ => vortex_bail!("expected a tuple-backed dtype for ListValue, got {dtype}"), }; Ok(ScalarValue::Tuple(values)) } @@ -491,28 +485,27 @@ fn union_from_proto( session: &VortexSession, ) -> VortexResult { let DType::Union(variants, _) = dtype else { - vortex_bail!(Serde: "expected Union dtype for UnionValue, got {dtype}"); + vortex_bail!("expected Union dtype for UnionValue, got {dtype}"); }; - let type_id = u8::try_from(value.type_id).map_err( - |_| vortex_err!(Serde: "union type ID {} is outside the u8 range", value.type_id), - )?; + let type_id = u8::try_from(value.type_id) + .map_err(|_| vortex_err!("union type ID {} is outside the u8 range", value.type_id))?; let child_index = variants.tag_to_child_index(type_id).ok_or_else(|| { vortex_err!( - Serde: "union type ID {type_id} is not present in {:?}", + "union type ID {type_id} is not present in {:?}", variants.type_ids() ) })?; let child_dtype = variants .variant_by_index(child_index) - .ok_or_else(|| vortex_err!(Serde: "union type ID {type_id} resolved out of bounds"))?; + .ok_or_else(|| vortex_err!("union type ID {type_id} resolved out of bounds"))?; let child_proto = value .value .as_deref() - .ok_or_else(|| vortex_err!(Serde: "UnionValue missing child value"))?; + .ok_or_else(|| vortex_err!("UnionValue missing child value"))?; let child_value = ScalarValue::from_proto(child_proto, &child_dtype, session)?; Scalar::validate(&child_dtype, child_value.as_ref()).map_err(|error| { @@ -531,7 +524,6 @@ mod tests { use std::sync::Arc; use vortex_buffer::BufferString; - use vortex_error::VortexErrorKind; use vortex_error::vortex_panic; use vortex_session::VortexSession; @@ -865,12 +857,10 @@ mod tests { }))), }; - assert_eq!( - ScalarValue::from_proto(&missing_child, &dtype, &session()) - .unwrap_err() - .kind(), - VortexErrorKind::Serde - ); + let err = ScalarValue::from_proto(&missing_child, &dtype, &session()) + .unwrap_err() + .to_string(); + assert!(err.contains("UnionValue missing child value"), "{err}"); let wrong_child_value = pb::ScalarValue { kind: Some(Kind::UnionValue(Box::new(PbUnionValue { @@ -881,11 +871,12 @@ mod tests { }))), }; - assert_eq!( - ScalarValue::from_proto(&wrong_child_value, &dtype, &session()) - .unwrap_err() - .kind(), - VortexErrorKind::Serde + let err = ScalarValue::from_proto(&wrong_child_value, &dtype, &session()) + .unwrap_err() + .to_string(); + assert!( + err.contains("expected Utf8 or Binary dtype for StringValue, got i32?"), + "{err}" ); Ok(()) @@ -988,7 +979,7 @@ mod tests { } _ => { vortex_panic!( - AssertionFailed: "Expected f16 primitive values, got {scalar_value:?} and {read_back:?}" + "Expected f16 primitive values, got {scalar_value:?} and {read_back:?}" ) } } @@ -1092,7 +1083,7 @@ mod tests { PValue::U32(v) => *v as u64, PValue::U64(v) => *v, _ => { - vortex_panic!(AssertionFailed: "Unexpected primitive type for {name}: {pv:?}") + vortex_panic!("Unexpected primitive type for {name}: {pv:?}") } }; assert_eq!( @@ -1101,7 +1092,7 @@ mod tests { ); } _ => { - vortex_panic!(AssertionFailed: "Unexpected type after roundtrip for {name}: {read_back:?}") + vortex_panic!("Unexpected type after roundtrip for {name}: {read_back:?}") } } } @@ -1141,7 +1132,7 @@ mod tests { PValue::I32(v) => *v as i64, PValue::I64(v) => *v, _ => { - vortex_panic!(AssertionFailed: "Unexpected primitive type for {name}: {pv:?}") + vortex_panic!("Unexpected primitive type for {name}: {pv:?}") } }; assert_eq!( @@ -1150,7 +1141,7 @@ mod tests { ); } _ => { - vortex_panic!(AssertionFailed: "Unexpected type after roundtrip for {name}: {read_back:?}") + vortex_panic!("Unexpected type after roundtrip for {name}: {read_back:?}") } } } diff --git a/vortex-array/src/scalar/scalar_impl.rs b/vortex-array/src/scalar/scalar_impl.rs index 3722f7368b6..8f3e58bd0e8 100644 --- a/vortex-array/src/scalar/scalar_impl.rs +++ b/vortex-array/src/scalar/scalar_impl.rs @@ -126,7 +126,7 @@ impl Scalar { /// Panics if `dtype` has no default value. pub fn default_value(dtype: &DType) -> Self { Self::try_default_value(dtype) - .unwrap_or_else(|| vortex_panic!(AssertionFailed: "{dtype} has no default value")) + .unwrap_or_else(|| vortex_panic!("{dtype} has no default value")) } /// Returns a valid default scalar, or [`None`] if `dtype` has no default. @@ -220,7 +220,7 @@ impl Scalar { let is_zero = match self.dtype() { DType::Null => { - vortex_panic!(AssertionFailed: "non-null value somehow had `DType::Null`") + vortex_panic!("non-null value somehow had `DType::Null`") } DType::Bool(_) => !value.as_bool(), DType::Primitive(..) => value.as_primitive().is_zero(), @@ -273,7 +273,7 @@ impl Scalar { vortex_ensure_eq!( primitive.ptype().byte_width(), ptype.byte_width(), - InvalidArgument: "can't reinterpret cast between integers of two different widths" + "can't reinterpret cast between integers of two different widths" ); Scalar::try_new( diff --git a/vortex-array/src/scalar/scalar_value.rs b/vortex-array/src/scalar/scalar_value.rs index 981beaf2969..eb74c1a0a0e 100644 --- a/vortex-array/src/scalar/scalar_value.rs +++ b/vortex-array/src/scalar/scalar_value.rs @@ -48,7 +48,7 @@ impl ScalarValue { /// Returns the zero / identity value for the given [`DType`]. pub(super) fn zero_value(dtype: &DType) -> Self { Self::try_zero_value(dtype) - .unwrap_or_else(|| vortex_panic!(AssertionFailed: "{dtype} has no non-null zero value")) + .unwrap_or_else(|| vortex_panic!("{dtype} has no non-null zero value")) } /// Returns the non-null zero value for `dtype`, or [`None`] if no such value exists. diff --git a/vortex-array/src/scalar/tests/casting.rs b/vortex-array/src/scalar/tests/casting.rs index f867eb00dea..4b27b1ead6d 100644 --- a/vortex-array/src/scalar/tests/casting.rs +++ b/vortex-array/src/scalar/tests/casting.rs @@ -281,11 +281,11 @@ mod tests { } fn serialize_metadata(&self, _metadata: &Self::Metadata) -> VortexResult> { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { @@ -339,11 +339,11 @@ mod tests { } fn serialize_metadata(&self, _metadata: &Self::Metadata) -> VortexResult> { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { diff --git a/vortex-array/src/scalar/truncation.rs b/vortex-array/src/scalar/truncation.rs index b9592b41631..66dd8cee969 100644 --- a/vortex-array/src/scalar/truncation.rs +++ b/vortex-array/src/scalar/truncation.rs @@ -43,7 +43,7 @@ impl ScalarTruncation for ByteBuffer { fn from_scalar(value: Scalar) -> VortexResult> { vortex_ensure!( value.dtype().is_binary(), - MismatchedTypes: "Expected binary scalar, got {}", + "Expected binary scalar, got {}", value.dtype() ); Ok(value.into_value().map(|b| b.into_binary())) @@ -79,7 +79,7 @@ impl ScalarTruncation for BufferString { fn from_scalar(value: Scalar) -> VortexResult> { vortex_ensure!( value.dtype().is_utf8(), - MismatchedTypes: "Expected utf8 scalar, got {}", + "Expected utf8 scalar, got {}", value.dtype() ); Ok(value.into_value().map(|b| b.into_utf8())) diff --git a/vortex-array/src/scalar/typed_view/binary.rs b/vortex-array/src/scalar/typed_view/binary.rs index bcaca5fa63a..3adfcba9aa0 100644 --- a/vortex-array/src/scalar/typed_view/binary.rs +++ b/vortex-array/src/scalar/typed_view/binary.rs @@ -67,7 +67,7 @@ impl<'a> BinaryScalar<'a> { /// Returns an error if the data type is not a binary type. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Binary(..)) { - vortex_bail!(MismatchedTypes: "Can only construct binary scalar from binary dtype, found {dtype}") + vortex_bail!("Can only construct binary scalar from binary dtype, found {dtype}") } Ok(Self { diff --git a/vortex-array/src/scalar/typed_view/bool.rs b/vortex-array/src/scalar/typed_view/bool.rs index 27bc72d0471..cace40ce5fe 100644 --- a/vortex-array/src/scalar/typed_view/bool.rs +++ b/vortex-array/src/scalar/typed_view/bool.rs @@ -61,7 +61,7 @@ impl<'a> BoolScalar<'a> { /// Returns an error if the data type is not a [`DType::Bool`]. pub fn try_new(dtype: &'a DType, value: Option<&ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Bool(_)) { - vortex_bail!(MismatchedTypes: "Expected bool scalar, found {}", dtype) + vortex_bail!("Expected bool scalar, found {}", dtype) } Ok(Self { dtype, diff --git a/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs b/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs index 0f491fcbfb5..ec7b57f538c 100644 --- a/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs +++ b/vortex-array/src/scalar/typed_view/decimal/arithmetic.rs @@ -69,7 +69,7 @@ pub(crate) fn decimal_numeric_result_dtype( .filter(|scale| *scale <= MAX_SCALE) else { vortex_bail!( - Overflow: "output scale {result_scale} of {input} {op} {input} is outside the \ + "output scale {result_scale} of {input} {op} {input} is outside the \ representable scale range of {} to {MAX_SCALE}", i8::MIN ); @@ -88,10 +88,7 @@ pub(crate) fn decimal_numeric_result_dtype( let result_precision = >::from(input.precision()) + >::from(result_scale); let result_precision = u8::try_from(result_precision).map_err(|_| { - vortex_err!( - InvalidArgument: - "decimal division result precision {result_precision} is invalid" - ) + vortex_err!("decimal division result precision {result_precision} is invalid") })?; DecimalDType::try_new(result_precision.min(MAX_PRECISION), result_scale) } diff --git a/vortex-array/src/scalar/typed_view/decimal/dvalue.rs b/vortex-array/src/scalar/typed_view/decimal/dvalue.rs index cced9573d18..5fe5a353e7c 100644 --- a/vortex-array/src/scalar/typed_view/decimal/dvalue.rs +++ b/vortex-array/src/scalar/typed_view/decimal/dvalue.rs @@ -133,7 +133,7 @@ impl DecimalValue { let factor = decimal_scale_factor(scale_delta as u32)?; value.checked_mul(&factor).ok_or_else(|| { vortex_err!( - Overflow: "Rescaling decimal from scale {} to {} overflows", + "Rescaling decimal from scale {} to {} overflows", from_scale, to_scale ) @@ -143,7 +143,7 @@ impl DecimalValue { let remainder = value % factor; if remainder != i256::ZERO { vortex_bail!( - InvalidArgument: "Rescaling decimal value {} from scale {} to {} would lose precision", + "Rescaling decimal value {} from scale {} to {} would lose precision", value, from_scale, to_scale @@ -174,7 +174,7 @@ impl DecimalValue { let decimal_value = Self::I256(value); decimal_value.normalize(decimal_dtype).ok_or_else(|| { vortex_err!( - Overflow: "decimal value {} does not fit in precision of {}", + "decimal value {} does not fit in precision of {}", decimal_value, decimal_dtype ) @@ -240,7 +240,7 @@ impl DecimalValue { fn decimal_scale_factor(exp: u32) -> VortexResult { i256::from_i128(10).checked_pow(exp).ok_or_else(|| { vortex_err!( - InvalidArgument: "decimal scale factor 10^{} cannot be represented in i256", + "decimal scale factor 10^{} cannot be represented in i256", exp ) }) diff --git a/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs b/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs index 6e4f436eab7..c9ea14a58ce 100644 --- a/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs +++ b/vortex-array/src/scalar/typed_view/decimal/integer_cast.rs @@ -54,7 +54,7 @@ impl DecimalToIntegerCast { pub(crate) fn error(&self, value: i256) -> VortexError { vortex_err!( - OutOfBounds: "Decimal value {} at scale {} out of range for {}", + "Decimal value {} at scale {} out of range for {}", value, self.scale, T::PTYPE diff --git a/vortex-array/src/scalar/typed_view/decimal/scalar.rs b/vortex-array/src/scalar/typed_view/decimal/scalar.rs index 8dee6959bcb..2c1c88319e0 100644 --- a/vortex-array/src/scalar/typed_view/decimal/scalar.rs +++ b/vortex-array/src/scalar/typed_view/decimal/scalar.rs @@ -123,7 +123,7 @@ impl<'a> DecimalScalar<'a> { } } _ => vortex_bail!( - MismatchedTypes: "Cannot cast decimal to {dtype}: decimal scalars can only be cast to decimal or primitive numeric types" + "Cannot cast decimal to {dtype}: decimal scalars can only be cast to decimal or primitive numeric types" ), } } @@ -163,7 +163,7 @@ impl<'a> DecimalScalar<'a> { // We could have ops between different types but need to add rules for type inference. if self.decimal_type != other.decimal_type { vortex_bail!( - MismatchedTypes: "decimal types must match: {} vs {}", + "decimal types must match: {} vs {}", self.decimal_type, other.decimal_type ); diff --git a/vortex-array/src/scalar/typed_view/decimal/tests.rs b/vortex-array/src/scalar/typed_view/decimal/tests.rs index 9720f5b459e..2600256688e 100644 --- a/vortex-array/src/scalar/typed_view/decimal/tests.rs +++ b/vortex-array/src/scalar/typed_view/decimal/tests.rs @@ -967,7 +967,7 @@ fn test_decimal_scalar_mul_widens_beyond_operand_storage() -> VortexResult<()> { let operand = DecimalValue::I64(100_000_000_000_000_000); let (value, result_dtype) = checked_op(operand, operand, dtype, NumericOperator::Mul)? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected an in-precision product"))?; + .ok_or_else(|| vortex_err!("expected an in-precision product"))?; assert_eq!(result_dtype, DecimalDType::new(37, 0)); assert_eq!( value, @@ -988,7 +988,7 @@ fn test_decimal_scalar_add_reserves_carry_digit() -> VortexResult<()> { dtype, NumericOperator::Add, )? - .ok_or_else(|| vortex_err!(InvalidArgument: "expected the carry digit to absorb the result"))?; + .ok_or_else(|| vortex_err!("expected the carry digit to absorb the result"))?; assert_eq!(result_dtype, DecimalDType::new(4, 0)); assert_eq!(value, DecimalValue::I16(1_001)); assert_eq!(value.decimal_type(), DecimalType::I16); @@ -1022,7 +1022,7 @@ fn test_decimal_scalar_div_reports_unrepresentable_intermediate() -> VortexResul let pow10 = |exp: u32| { i256::from_i128(10) .checked_pow(exp) - .ok_or_else(|| vortex_err!(AssertionFailed: "10^{exp} is representable as i256")) + .ok_or_else(|| vortex_err!("10^{exp} is representable as i256")) }; let lhs = DecimalValue::I256(pow10(75)?); let rhs = DecimalValue::I256(pow10(70)?); @@ -1044,9 +1044,7 @@ fn test_decimal_scalar_null_handling() -> VortexResult<()> { let result = null .as_decimal() .checked_binary_numeric(&value.as_decimal(), NumericOperator::Add)? - .ok_or_else( - || vortex_err!(Overflow: "a null operand yields a null result, not an overflow"), - )?; + .ok_or_else(|| vortex_err!("a null operand yields a null result, not an overflow"))?; assert!(result.is_null()); assert_eq!( result.dtype(), diff --git a/vortex-array/src/scalar/typed_view/extension/mod.rs b/vortex-array/src/scalar/typed_view/extension/mod.rs index 230b9ea32c9..27b1567869f 100644 --- a/vortex-array/src/scalar/typed_view/extension/mod.rs +++ b/vortex-array/src/scalar/typed_view/extension/mod.rs @@ -52,7 +52,7 @@ impl<'a> ExtScalar<'a> { /// been verified to be valid for the extension type. pub(crate) fn new_unchecked(dtype: &'a DType, value: Option<&'a ScalarValue>) -> Self { let DType::Extension(ext_dtype) = dtype else { - vortex_panic!(MismatchedTypes: "Expected extension scalar, found {}", dtype) + vortex_panic!("Expected extension scalar, found {}", dtype) }; Self { @@ -96,7 +96,7 @@ impl<'a> ExtScalar<'a> { } vortex_bail!( - MismatchedTypes: "cannot cast extension dtype with id {} and storage type {} to {}", + "cannot cast extension dtype with id {} and storage type {} to {}", self.ext_dtype.id(), self.ext_dtype.storage_dtype(), target_dtype diff --git a/vortex-array/src/scalar/typed_view/extension/tests.rs b/vortex-array/src/scalar/typed_view/extension/tests.rs index 2d1205486d2..d26acd20127 100644 --- a/vortex-array/src/scalar/typed_view/extension/tests.rs +++ b/vortex-array/src/scalar/typed_view/extension/tests.rs @@ -316,11 +316,11 @@ fn test_ext_scalar_with_metadata() { } fn serialize_metadata(&self, _metadata: &Self::Metadata) -> VortexResult> { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { diff --git a/vortex-array/src/scalar/typed_view/list.rs b/vortex-array/src/scalar/typed_view/list.rs index 5ac0a19d862..01e91800432 100644 --- a/vortex-array/src/scalar/typed_view/list.rs +++ b/vortex-array/src/scalar/typed_view/list.rs @@ -104,7 +104,7 @@ impl<'a> ListScalar<'a> { pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { let element_dtype = dtype .as_any_size_list_element_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected list scalar, found {}", dtype))?; + .ok_or_else(|| vortex_err!("Expected list scalar, found {}", dtype))?; Ok(Self { dtype, @@ -146,9 +146,7 @@ impl<'a> ListScalar<'a> { pub fn element_dtype(&self) -> &DType { self.dtype .as_any_size_list_element_opt() - .unwrap_or_else( - || vortex_panic!(AssertionFailed: "`ListScalar` somehow had dtype {}", self.dtype), - ) + .unwrap_or_else(|| vortex_panic!("`ListScalar` somehow had dtype {}", self.dtype)) .as_ref() } @@ -199,7 +197,7 @@ impl<'a> ListScalar<'a> { .as_any_size_list_element_opt() .ok_or_else(|| { vortex_err!( - MismatchedTypes: "Cannot cast {} to {}: list can only be cast to a list or fixed-size list", + "Cannot cast {} to {}: list can only be cast to a list or fixed-size list", self.dtype(), dtype ) @@ -210,7 +208,7 @@ impl<'a> ListScalar<'a> { && *size as usize != self.len() { vortex_bail!( - InvalidArgument: "tried to cast to a `FixedSizeList[{size}]` but had {} elements", + "tried to cast to a `FixedSizeList[{size}]` but had {} elements", self.len() ) } @@ -219,7 +217,7 @@ impl<'a> ListScalar<'a> { dtype.clone(), Some(ScalarValue::Tuple( self.elements - .ok_or_else(|| vortex_err!(AssertionFailed: "nullness should be handled in Scalar::cast"))? + .ok_or_else(|| vortex_err!("nullness should be handled in Scalar::cast"))? .iter() .map(|element| { // Recursively cast the elements of the list. diff --git a/vortex-array/src/scalar/typed_view/map.rs b/vortex-array/src/scalar/typed_view/map.rs index c6501e974f8..fd49f999325 100644 --- a/vortex-array/src/scalar/typed_view/map.rs +++ b/vortex-array/src/scalar/typed_view/map.rs @@ -67,7 +67,7 @@ impl<'a> MapScalar<'a> { /// Returns an error when `dtype` is not [`DType::Map`]. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !dtype.is_map() { - vortex_bail!(InvalidArgument: "Expected map scalar, found {dtype}") + vortex_bail!("Expected map scalar, found {dtype}") } Ok(Self { @@ -145,20 +145,20 @@ impl<'a> MapScalar<'a> { /// returns an error for direct null-map casts; callers should use [`Scalar::cast`] so null /// handling and sortedness checks stay centralized. pub(crate) fn cast(&self, dtype: &DType) -> VortexResult { - let target = dtype.as_map_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Cannot cast map to {dtype}: target must be a map"), - )?; + let target = dtype + .as_map_opt() + .ok_or_else(|| vortex_err!("Cannot cast map to {dtype}: target must be a map"))?; if target.keys_sorted() && !self.map_dtype().keys_sorted() { vortex_bail!( - MismatchedTypes: "Cannot cast {} to {dtype}: source does not assert sorted map keys", + "Cannot cast {} to {dtype}: source does not assert sorted map keys", self.dtype ); } let Some(entries) = self.entries else { vortex_bail!( - MismatchedTypes: "Cannot cast null map {} to {dtype}: Scalar::cast should handle nulls first", + "Cannot cast null map {} to {dtype}: Scalar::cast should handle nulls first", self.dtype ); }; diff --git a/vortex-array/src/scalar/typed_view/primitive/numeric_operator.rs b/vortex-array/src/scalar/typed_view/primitive/numeric_operator.rs index d7bcc8d0b4c..7a52a8ce485 100644 --- a/vortex-array/src/scalar/typed_view/primitive/numeric_operator.rs +++ b/vortex-array/src/scalar/typed_view/primitive/numeric_operator.rs @@ -51,7 +51,7 @@ impl TryFrom for NumericOperator { Operator::Sub => Ok(NumericOperator::Sub), Operator::Mul => Ok(NumericOperator::Mul), Operator::Div => Ok(NumericOperator::Div), - _ => Err(vortex_err!(InvalidArgument: "{op} is not a numeric operator")), + _ => Err(vortex_err!("{op} is not a numeric operator")), } } } diff --git a/vortex-array/src/scalar/typed_view/primitive/pvalue.rs b/vortex-array/src/scalar/typed_view/primitive/pvalue.rs index e5cc3a25090..bea7193e2d3 100644 --- a/vortex-array/src/scalar/typed_view/primitive/pvalue.rs +++ b/vortex-array/src/scalar/typed_view/primitive/pvalue.rs @@ -299,7 +299,7 @@ impl PValue { PValue::F64(f) => T::from_f64(f), }; let to = T::PTYPE; - res.ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot cast {self} to {to}")) + res.ok_or_else(|| vortex_err!("Cannot cast {self} to {to}")) } /// Returns true if the value of float type and is NaN. @@ -413,7 +413,7 @@ macro_rules! int_pvalue { ) { PValue::cast(&value) } else { - vortex_bail!(MismatchedTypes: "Cannot read primitive value {:?} as {}", value, PType::$PT) + vortex_bail!("Cannot read primitive value {:?} as {}", value, PType::$PT) } } } @@ -437,9 +437,10 @@ impl TryFrom for usize { type Error = VortexError; fn try_from(value: PValue) -> Result { - value.cast::()?.to_usize().ok_or_else( - || vortex_err!(Overflow: "Cannot read primitive value {:?} as usize", value), - ) + value + .cast::()? + .to_usize() + .ok_or_else(|| vortex_err!("Cannot read primitive value {:?} as usize", value)) } } @@ -556,24 +557,26 @@ impl CoercePValue for f16 { PValue::U32(u) => { vortex_ensure!( u <= u16::MAX as u32, - Overflow: "Cannot coerce U32 value to f16: value out of range" + "Cannot coerce U32 value to f16: value out of range" ); Ok(Self::from_bits(u as u16)) } PValue::U64(u) => { vortex_ensure!( u <= u16::MAX as u64, - Overflow: "Cannot coerce U64 value to f16: value out of range" + "Cannot coerce U64 value to f16: value out of range" ); Ok(Self::from_bits(u as u16)) } PValue::F16(u) => Ok(u), - PValue::F32(f) => ::from(f) - .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f32 to f16")), - PValue::F64(f) => ::from(f) - .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f64 to f16")), + PValue::F32(f) => { + ::from(f).ok_or_else(|| vortex_err!("Cannot convert f32 to f16")) + } + PValue::F64(f) => { + ::from(f).ok_or_else(|| vortex_err!("Cannot convert f64 to f16")) + } PValue::I8(_) | PValue::I16(_) | PValue::I32(_) | PValue::I64(_) => { - vortex_bail!(InvalidArgument: "Cannot coerce {value:?} to f16: type not supported for coercion") + vortex_bail!("Cannot coerce {value:?} to f16: type not supported for coercion") } } } @@ -593,17 +596,19 @@ impl CoercePValue for f32 { PValue::U64(u) => { vortex_ensure!( u <= u32::MAX as u64, - Overflow: "Cannot coerce U64 value to f32: value out of range" + "Cannot coerce U64 value to f32: value out of range" ); Ok(Self::from_bits(u as u32)) } - PValue::F16(f) => ::from(f) - .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f16 to f32")), + PValue::F16(f) => { + ::from(f).ok_or_else(|| vortex_err!("Cannot convert f16 to f32")) + } PValue::F32(f) => Ok(f), - PValue::F64(f) => ::from(f) - .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f64 to f32")), + PValue::F64(f) => { + ::from(f).ok_or_else(|| vortex_err!("Cannot convert f64 to f32")) + } PValue::I8(_) | PValue::I16(_) | PValue::I32(_) | PValue::I64(_) => { - vortex_bail!(InvalidArgument: "Unsupported PValue {value:?} type for f32") + vortex_bail!("Unsupported PValue {value:?} type for f32") } } } @@ -617,13 +622,15 @@ impl CoercePValue for f64 { PValue::U16(u) => Ok(Self::from_bits(u as u64)), PValue::U32(u) => Ok(Self::from_bits(u as u64)), PValue::U64(u) => Ok(Self::from_bits(u)), - PValue::F16(f) => ::from(f) - .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f16 to f64")), - PValue::F32(f) => ::from(f) - .ok_or_else(|| vortex_err!(MismatchedTypes: "Cannot convert f32 to f64")), + PValue::F16(f) => { + ::from(f).ok_or_else(|| vortex_err!("Cannot convert f16 to f64")) + } + PValue::F32(f) => { + ::from(f).ok_or_else(|| vortex_err!("Cannot convert f32 to f64")) + } PValue::F64(f) => Ok(f), PValue::I8(_) | PValue::I16(_) | PValue::I32(_) | PValue::I64(_) => { - vortex_bail!(InvalidArgument: "Unsupported PValue {value:?} type for f64") + vortex_bail!("Unsupported PValue {value:?} type for f64") } } } diff --git a/vortex-array/src/scalar/typed_view/primitive/scalar.rs b/vortex-array/src/scalar/typed_view/primitive/scalar.rs index b35c88dc4f4..a1e27d679ab 100644 --- a/vortex-array/src/scalar/typed_view/primitive/scalar.rs +++ b/vortex-array/src/scalar/typed_view/primitive/scalar.rs @@ -155,7 +155,7 @@ impl<'a> PrimitiveScalar<'a> { vortex_ensure_eq!( self.ptype, T::PTYPE, - MismatchedTypes: "Attempting to read a primitive scalar as the wrong type" + "Attempting to read a primitive scalar as the wrong type" ); if let Some(pv) = self.pvalue { @@ -180,7 +180,7 @@ impl<'a> PrimitiveScalar<'a> { *decimal_dtype, *nullability, )), - _ => vortex_bail!(MismatchedTypes: "Cannot cast primitive scalar to {dtype}"), + _ => vortex_bail!("Cannot cast primitive scalar to {dtype}"), } } @@ -222,7 +222,7 @@ impl<'a> PrimitiveScalar<'a> { pub fn as_(&self) -> Option { self.as_opt::().unwrap_or_else(|| { vortex_panic!( - Overflow: "cast {} to {}: value out of range", + "cast {} to {}: value out of range", self.ptype, type_name::() ) @@ -289,7 +289,7 @@ fn pvalue_to_decimal(pvalue: PValue, decimal_dtype: DecimalDType) -> VortexResul PValue::I32(v) => i256::from_i128(i128::from(v)), PValue::I64(v) => i256::from_i128(i128::from(v)), PValue::F16(_) | PValue::F32(_) | PValue::F64(_) => { - vortex_bail!(MismatchedTypes: "Cannot cast floating primitive {pvalue} to decimal {decimal_dtype}") + vortex_bail!("Cannot cast floating primitive {pvalue} to decimal {decimal_dtype}") } }; @@ -345,7 +345,7 @@ impl<'a> PrimitiveScalar<'a> { op: NumericOperator, ) -> Option> { if !self.dtype().eq_ignore_nullability(other.dtype()) { - vortex_panic!(MismatchedTypes: "types must match: {} {}", self.dtype(), other.dtype()); + vortex_panic!("types must match: {} {}", self.dtype(), other.dtype()); } let result_dtype = if self.dtype().is_nullable() { self.dtype() diff --git a/vortex-array/src/scalar/typed_view/struct_.rs b/vortex-array/src/scalar/typed_view/struct_.rs index e5fb960117f..c1903b9f1a4 100644 --- a/vortex-array/src/scalar/typed_view/struct_.rs +++ b/vortex-array/src/scalar/typed_view/struct_.rs @@ -116,7 +116,7 @@ impl<'a> StructScalar<'a> { /// Creates a new [`StructScalar`] from a [`DType`] and optional [`ScalarValue`]. pub(crate) fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Struct(..)) { - vortex_bail!(MismatchedTypes: "Expected struct scalar, found {}", dtype) + vortex_bail!("Expected struct scalar, found {}", dtype) } Ok(Self { @@ -204,7 +204,7 @@ impl<'a> StructScalar<'a> { pub fn cast(&self, dtype: &DType) -> VortexResult { let DType::Struct(st, _) = dtype else { vortex_bail!( - MismatchedTypes: "Cannot cast struct to {}: struct can only be cast to struct", + "Cannot cast struct to {}: struct can only be cast to struct", dtype ) }; @@ -212,7 +212,7 @@ impl<'a> StructScalar<'a> { if st.fields().len() != own_st.fields().len() { vortex_bail!( - MismatchedTypes: "Cannot cast between structs with different number of fields: {} and {}", + "Cannot cast between structs with different number of fields: {} and {}", own_st.fields().len(), st.fields().len() ); @@ -251,7 +251,7 @@ impl<'a> StructScalar<'a> { let struct_dtype = self .dtype .as_struct_fields_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Not a struct dtype"))?; + .ok_or_else(|| vortex_err!("Not a struct dtype"))?; let projected_dtype = DType::Struct( struct_dtype.project(projection)?, self.dtype().nullability(), @@ -281,14 +281,14 @@ impl Scalar { /// Creates a new struct scalar with the given fields, checking dtypes at runtime. pub fn struct_(dtype: DType, children: impl IntoIterator) -> Self { let DType::Struct(struct_fields, _) = &dtype else { - vortex_panic!(MismatchedTypes: "Expected struct dtype, found {}", dtype); + vortex_panic!("Expected struct dtype, found {}", dtype); }; let children: Vec = children.into_iter().collect(); let field_dtypes = struct_fields.field_dtypes(); if children.len() != field_dtypes.len() { vortex_panic!( - InvalidArgument: "Struct has {} fields but {} children were provided", + "Struct has {} fields but {} children were provided", field_dtypes.len(), children.len() ); @@ -297,7 +297,7 @@ impl Scalar { for (idx, (child, expected_dtype)) in children.iter().zip(field_dtypes).enumerate() { if child.dtype() != expected_dtype { vortex_panic!( - MismatchedTypes: "Field {} expected dtype {} but got {}", + "Field {} expected dtype {} but got {}", idx, expected_dtype, child.dtype() diff --git a/vortex-array/src/scalar/typed_view/union.rs b/vortex-array/src/scalar/typed_view/union.rs index aaa7e1d117a..60ff96dbb78 100644 --- a/vortex-array/src/scalar/typed_view/union.rs +++ b/vortex-array/src/scalar/typed_view/union.rs @@ -107,7 +107,7 @@ impl<'a> UnionScalar<'a> { /// non-union dtype, a null value for a non-nullable union, an unknown type ID, or a value that /// is invalid for the selected variant dtype. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { - vortex_ensure!(dtype.is_union(), MismatchedTypes: "Expected union scalar, found {dtype}"); + vortex_ensure!(dtype.is_union(), "Expected union scalar, found {dtype}"); Scalar::validate(dtype, value)?; @@ -125,7 +125,7 @@ impl<'a> UnionScalar<'a> { /// Panics if `dtype` is not a union dtype or a non-null `value` is not a union value. pub(crate) fn new_unchecked(dtype: &'a DType, value: Option<&'a ScalarValue>) -> Self { if !dtype.is_union() { - vortex_panic!(MismatchedTypes: "Expected union scalar, found {dtype}") + vortex_panic!("Expected union scalar, found {dtype}") } Self { diff --git a/vortex-array/src/scalar/typed_view/utf8.rs b/vortex-array/src/scalar/typed_view/utf8.rs index 268c8832af9..771ea0d5d0f 100644 --- a/vortex-array/src/scalar/typed_view/utf8.rs +++ b/vortex-array/src/scalar/typed_view/utf8.rs @@ -63,7 +63,7 @@ impl<'a> Utf8Scalar<'a> { /// Returns an error if the data type is not a UTF-8 type. pub fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Utf8(..)) { - vortex_bail!(MismatchedTypes: "Can only construct utf8 scalar from utf8 dtype, found {dtype}") + vortex_bail!("Can only construct utf8 scalar from utf8 dtype, found {dtype}") } Ok(Self { diff --git a/vortex-array/src/scalar/typed_view/variant.rs b/vortex-array/src/scalar/typed_view/variant.rs index eedeae0c3e1..ced2461e0cf 100644 --- a/vortex-array/src/scalar/typed_view/variant.rs +++ b/vortex-array/src/scalar/typed_view/variant.rs @@ -34,7 +34,7 @@ impl<'a> VariantScalar<'a> { #[inline] pub(crate) fn try_new(dtype: &'a DType, value: Option<&'a ScalarValue>) -> VortexResult { if !matches!(dtype, DType::Variant(_)) { - vortex_bail!(InvalidArgument: "Expected variant scalar, found {}", dtype) + vortex_bail!("Expected variant scalar, found {}", dtype) } Ok(Self { diff --git a/vortex-array/src/scalar/validate.rs b/vortex-array/src/scalar/validate.rs index 227bbfe5110..274adc4ca66 100644 --- a/vortex-array/src/scalar/validate.rs +++ b/vortex-array/src/scalar/validate.rs @@ -112,7 +112,7 @@ impl Scalar { match Self::validate_detailed(dtype, value) { Err(err) => err, Ok(()) => vortex_err!( - AssertionFailed: "scalar validation fast path rejected value {value:?} for dtype {dtype}, but the \ + "scalar validation fast path rejected value {value:?} for dtype {dtype}, but the \ detailed check accepted it" ), } @@ -123,7 +123,7 @@ impl Scalar { let Some(value) = value else { vortex_ensure!( dtype.is_nullable(), - InvalidArgument: "non-nullable dtype {dtype} cannot hold a null value", + "non-nullable dtype {dtype} cannot hold a null value", ); return Ok(()); }; @@ -131,17 +131,17 @@ impl Scalar { // From here onwards, we know that the value is not null. match dtype { DType::Null => { - vortex_bail!(InvalidArgument: "null dtype cannot hold a non-null value {value}"); + vortex_bail!("null dtype cannot hold a non-null value {value}"); } DType::Bool(_) => { vortex_ensure!( matches!(value, ScalarValue::Bool(_)), - MismatchedTypes: "bool dtype expected Bool value, got {value}", + "bool dtype expected Bool value, got {value}", ); } DType::Primitive(ptype, _) => { let ScalarValue::Primitive(pvalue) = value else { - vortex_bail!(MismatchedTypes: "primitive dtype {ptype} expected Primitive value, got {value}",); + vortex_bail!("primitive dtype {ptype} expected Primitive value, got {value}",); }; // Note that this is a backwards compatibility check for poor design in the @@ -153,34 +153,34 @@ impl Scalar { vortex_ensure!( f16_backcompat_still_works || pvalue.ptype() == *ptype, - MismatchedTypes: "primitive dtype {ptype} is not compatible with value {pvalue}", + "primitive dtype {ptype} is not compatible with value {pvalue}", ); } DType::Decimal(dec_dtype, _) => { let ScalarValue::Decimal(dvalue) = value else { - vortex_bail!(MismatchedTypes: "decimal dtype expected Decimal value, got {value}"); + vortex_bail!("decimal dtype expected Decimal value, got {value}"); }; vortex_ensure!( dvalue.fits_in_precision(*dec_dtype), - Overflow: "decimal value {dvalue} does not fit in precision of {dec_dtype}", + "decimal value {dvalue} does not fit in precision of {dec_dtype}", ); } DType::Utf8(_) => { vortex_ensure!( matches!(value, ScalarValue::Utf8(_)), - MismatchedTypes: "utf8 dtype expected Utf8 value, got {value}", + "utf8 dtype expected Utf8 value, got {value}", ); } DType::Binary(_) => { vortex_ensure!( matches!(value, ScalarValue::Binary(_)), - MismatchedTypes: "binary dtype expected Binary value, got {value}", + "binary dtype expected Binary value, got {value}", ); } DType::List(elem_dtype, _) => { let ScalarValue::Tuple(elements) = value else { - vortex_bail!(MismatchedTypes: "list dtype expected Tuple value, got {value}"); + vortex_bail!("list dtype expected Tuple value, got {value}"); }; for (i, element) in elements.iter().enumerate() { @@ -190,14 +190,14 @@ impl Scalar { } DType::FixedSizeList(elem_dtype, size, _) => { let ScalarValue::Tuple(elements) = value else { - vortex_bail!(MismatchedTypes: "fixed-size list dtype expected Tuple value, got {value}",); + vortex_bail!("fixed-size list dtype expected Tuple value, got {value}",); }; let len = elements.len(); vortex_ensure_eq!( len, *size as usize, - InvalidArgument: "fixed-size list scalar has the wrong number of elements", + "fixed-size list scalar has the wrong number of elements", ); for (i, element) in elements.iter().enumerate() { @@ -208,24 +208,24 @@ impl Scalar { } DType::Map(map, _) => { let ScalarValue::Tuple(entries) = value else { - vortex_bail!(MismatchedTypes: "map dtype expected Tuple value, got {value}"); + vortex_bail!("map dtype expected Tuple value, got {value}"); }; let key_dtype = map.key_dtype(); let value_dtype = map.value_dtype(); for (index, entry) in entries.iter().enumerate() { let entry = entry.as_ref().ok_or_else(|| { - vortex_error::vortex_err!(InvalidArgument: "map entry at index {index} cannot be null") + vortex_error::vortex_err!("map entry at index {index} cannot be null") })?; let ScalarValue::Tuple(values) = entry else { vortex_bail!( - MismatchedTypes: "map entry at index {index} expected Tuple value, got {entry}" + "map entry at index {index} expected Tuple value, got {entry}" ); }; vortex_ensure_eq!( values.len(), 2, - InvalidArgument: "map entry at index {index} has the wrong number of values", + "map entry at index {index} has the wrong number of values", ); Self::validate_detailed(&key_dtype, values[0].as_ref()) @@ -237,7 +237,7 @@ impl Scalar { } DType::Struct(fields, _) => { let ScalarValue::Tuple(values) = value else { - vortex_bail!(MismatchedTypes: "struct dtype expected Tuple value, got {value}"); + vortex_bail!("struct dtype expected Tuple value, got {value}"); }; let nfields = fields.nfields(); @@ -245,7 +245,7 @@ impl Scalar { vortex_ensure_eq!( nvalues, nfields, - InvalidArgument: "struct scalar has the wrong number of fields", + "struct scalar has the wrong number of fields", ); for (field, field_value) in fields.field_dtypes().zip(values.iter()) { @@ -254,13 +254,13 @@ impl Scalar { } DType::Union(variants, _) => { let ScalarValue::Union(union_value) = value else { - vortex_bail!(MismatchedTypes: "union dtype expected Union value, got {value}"); + vortex_bail!("union dtype expected Union value, got {value}"); }; let type_id = union_value.type_id(); let Some(child_index) = variants.tag_to_child_index(type_id) else { vortex_bail!( - NotFound: "union value has unknown type ID {type_id}; expected one of {:?}", + "union value has unknown type ID {type_id}; expected one of {:?}", variants.type_ids() ); }; @@ -279,13 +279,13 @@ impl Scalar { } DType::Variant(_) => { let ScalarValue::Variant(inner) = value else { - vortex_bail!(MismatchedTypes: "variant dtype expected Variant value, got {value}"); + vortex_bail!("variant dtype expected Variant value, got {value}"); }; Self::validate_detailed(inner.dtype(), inner.value())?; vortex_ensure!( !inner.is_null() || matches!(inner.dtype(), DType::Null), - InvalidArgument: "variant nulls must use a nested null scalar, got {}", + "variant nulls must use a nested null scalar, got {}", inner.dtype(), ); } diff --git a/vortex-array/src/scalar_fn/erased.rs b/vortex-array/src/scalar_fn/erased.rs index fa64feb68a0..ae951376778 100644 --- a/vortex-array/src/scalar_fn/erased.rs +++ b/vortex-array/src/scalar_fn/erased.rs @@ -94,7 +94,7 @@ impl ScalarFnRef { self.try_downcast::() .map_err(|this| { vortex_err!( - MismatchedTypes: "Failed to downcast ScalarFnRef {} to {}", + "Failed to downcast ScalarFnRef {} to {}", this.0.id(), type_name::(), ) diff --git a/vortex-array/src/scalar_fn/fns/between/mod.rs b/vortex-array/src/scalar_fn/fns/between/mod.rs index fd884a54884..9ba0173975d 100644 --- a/vortex-array/src/scalar_fn/fns/between/mod.rs +++ b/vortex-array/src/scalar_fn/fns/between/mod.rs @@ -286,14 +286,14 @@ impl ScalarFnVTable for Between { if !arr_dt.eq_ignore_nullability(lower_dt) { vortex_bail!( - MismatchedTypes: "Array dtype {} does not match lower dtype {}", + "Array dtype {} does not match lower dtype {}", arr_dt, lower_dt ); } if !arr_dt.eq_ignore_nullability(upper_dt) { vortex_bail!( - MismatchedTypes: "Array dtype {} does not match upper dtype {}", + "Array dtype {} does not match upper dtype {}", arr_dt, upper_dt ); @@ -389,7 +389,7 @@ mod tests { let lazy = data.apply(&between(col("x"), col("lo"), col("hi"), NON_STRICT))?; let Validity::Array(validity) = lazy.validity()? else { - vortex_bail!(AssertionFailed: "non-lazy validity"); + vortex_bail!("non-lazy validity"); }; assert_eq!( validity.encoding_id().to_string(), diff --git a/vortex-array/src/scalar_fn/fns/binary/boolean.rs b/vortex-array/src/scalar_fn/fns/binary/boolean.rs index 47bae8d5280..df23e5a87cb 100644 --- a/vortex-array/src/scalar_fn/fns/binary/boolean.rs +++ b/vortex-array/src/scalar_fn/fns/binary/boolean.rs @@ -138,7 +138,7 @@ pub(crate) fn execute_boolean( let rhs = rhs.execute::(ctx)?; let Some(result) = ::boolean(rhs.as_view(), &lhs.into_array(), op, ctx)? else { - vortex_bail!(AssertionFailed: "No boolean kernel for two BoolArrays"); + vortex_bail!("No boolean kernel for two BoolArrays"); }; Ok(result) } @@ -187,7 +187,7 @@ fn constant_array_boolean( ))), (Operator::Or, Some(false)) => Ok(Some(cast_bool_nullability(array, nullability)?)), (Operator::And | Operator::Or, None) => Ok(None), - (other, _) => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), + (other, _) => vortex_bail!("Not a boolean operator: {other}"), } } @@ -207,14 +207,14 @@ fn boolean_scalar_scalar( (None, _) | (_, None) => None, (Some(l), Some(r)) => Some(l | r), }, - other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), + other => vortex_bail!("Not a boolean operator: {other}"), }) } fn bool_scalar_value(scalar: &Scalar) -> VortexResult> { Ok(scalar .as_bool_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))? + .ok_or_else(|| vortex_err!("expected boolean scalar"))? .value()) } @@ -235,7 +235,7 @@ pub fn kleene_boolean_buffers( let values = match operator { Operator::And => lhs_values & &rhs_values, Operator::Or => lhs_values | &rhs_values, - other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), + other => vortex_bail!("Not a boolean operator: {other}"), }; return Ok(BoolArray::try_new(values, Validity::from(nullability))?.into_array()); } @@ -298,7 +298,7 @@ pub fn kleene_boolean_buffer_scalar( Validity::from_mask(valid, nullability), )? } - (other, _) => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), + (other, _) => vortex_bail!("Not a boolean operator: {other}"), }; Ok(result.into_array()) @@ -482,7 +482,7 @@ fn fused_boolean_word_sources( nullability, allocator, ), - other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), + other => vortex_bail!("Not a boolean operator: {other}"), } } @@ -642,7 +642,7 @@ where nullability, allocator, ), - other => vortex_bail!(MismatchedTypes: "Not a boolean operator: {other}"), + other => vortex_bail!("Not a boolean operator: {other}"), } } diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs b/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs index 6de49ed07b2..b569e791f32 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/boolean.rs @@ -29,11 +29,9 @@ impl BoolOperand { let value = constant .scalar() .as_bool_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected boolean scalar"))? + .ok_or_else(|| vortex_err!("expected boolean scalar"))? .value() - .ok_or_else( - || vortex_err!(AssertionFailed: "null constant handled by execute_compare"), - )?; + .ok_or_else(|| vortex_err!("null constant handled by execute_compare"))?; return Ok(Self::Constant { value, validity: if constant.scalar().dtype().is_nullable() { diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs b/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs index 3f5d8cae63f..7dc45fac2c2 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/bytes.rs @@ -77,10 +77,10 @@ fn constant_bytes(scalar: &Scalar) -> VortexResult> { .map(|s| s.as_str().as_bytes().to_vec()), DType::Binary(_) => scalar.as_binary().value().map(|b| b.to_vec()), _ => { - vortex_bail!(MismatchedTypes: "expected utf8 or binary scalar, got {}", scalar.dtype()) + vortex_bail!("expected utf8 or binary scalar, got {}", scalar.dtype()) } }; - value.ok_or_else(|| vortex_err!(AssertionFailed: "null constant handled by execute_compare")) + value.ok_or_else(|| vortex_err!("null constant handled by execute_compare")) } /// Compare `lhs_view` from `lhs` against `rhs_view` from `rhs` for equality. diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs b/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs index 47c0dd92299..e88e12f11d0 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/decimal.rs @@ -46,9 +46,11 @@ enum DecimalOperand { impl DecimalOperand { fn try_new(array: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { if let Some(constant) = array.as_opt::() { - let value = constant.scalar().as_decimal().decimal_value().ok_or_else( - || vortex_err!(AssertionFailed: "null constant handled by execute_compare"), - )?; + let value = constant + .scalar() + .as_decimal() + .decimal_value() + .ok_or_else(|| vortex_err!("null constant handled by execute_compare"))?; return Ok(Self::Constant { value, validity: if constant.scalar().dtype().is_nullable() { diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs b/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs index b1cb8589190..6593af28c6e 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/mod.rs @@ -137,7 +137,7 @@ pub(crate) fn execute_compare( if lhs.len() != rhs.len() { vortex_bail!( - InvalidArgument: "compare operator requires equal lengths, got {} and {}", + "compare operator requires equal lengths, got {} and {}", lhs.len(), rhs.len() ); @@ -183,7 +183,7 @@ fn compare_arrays( && !lhs.dtype().eq_ignore_nullability(rhs.dtype()) { vortex_bail!( - MismatchedTypes: "Cannot compare extension dtypes {} and {}", + "Cannot compare extension dtypes {} and {}", lhs.dtype(), rhs.dtype() ); @@ -195,7 +195,7 @@ fn compare_arrays( if !lhs.dtype().eq_ignore_nullability(rhs.dtype()) { vortex_bail!( - MismatchedTypes: "Cannot compare different DTypes {} and {}", + "Cannot compare different DTypes {} and {}", lhs.dtype(), rhs.dtype() ); @@ -216,7 +216,7 @@ fn compare_arrays( nested::compare_nested(lhs, rhs, op, nullability, ctx) } DType::Union(..) | DType::Variant(_) | DType::Extension(_) => { - vortex_bail!(InvalidArgument: "compare is not supported for dtype {}", lhs.dtype()) + vortex_bail!("compare is not supported for dtype {}", lhs.dtype()) } } } @@ -248,7 +248,7 @@ pub fn scalar_cmp(lhs: &Scalar, rhs: &Scalar, operator: CompareOperator) -> Vort // We use `partial_cmp` to ensure we do not lose a type mismatch error. let ordering = lhs.partial_cmp(rhs).ok_or_else(|| { vortex_err!( - MismatchedTypes: "Cannot compare scalars with incompatible types: {} and {}", + "Cannot compare scalars with incompatible types: {} and {}", lhs.dtype(), rhs.dtype() ) diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs b/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs index 6514a1a0336..ccccc3ca955 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/nested.rs @@ -147,7 +147,7 @@ fn build_values_comparator( ) -> VortexResult { if !lhs.dtype().eq_ignore_nullability(rhs.dtype()) { vortex_bail!( - MismatchedTypes: "Cannot compare different DTypes {} and {}", + "Cannot compare different DTypes {} and {}", lhs.dtype(), rhs.dtype() ); @@ -237,7 +237,7 @@ fn build_values_comparator( build_values_comparator(lhs.entries(), rhs.entries(), ctx)? } DType::Union(..) | DType::Variant(_) => { - vortex_bail!(InvalidArgument: "compare is not supported for dtype {}", lhs.dtype()) + vortex_bail!("compare is not supported for dtype {}", lhs.dtype()) } }) } diff --git a/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs b/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs index b38b21f67e4..a1da5a84097 100644 --- a/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs +++ b/vortex-array/src/scalar_fn/fns/binary/compare/primitive.rs @@ -57,7 +57,7 @@ fn compare_primitive_typed( let rhs = PrimitiveOperand::::try_new(rhs, ctx)?; if lhs.len() != rhs.len() { vortex_bail!( - InvalidArgument: "compare operator requires equal lengths, got {} and {}", + "compare operator requires equal lengths, got {} and {}", lhs.len(), rhs.len() ); diff --git a/vortex-array/src/scalar_fn/fns/binary/mod.rs b/vortex-array/src/scalar_fn/fns/binary/mod.rs index 2e2bdb53dcb..42cebc8401c 100644 --- a/vortex-array/src/scalar_fn/fns/binary/mod.rs +++ b/vortex-array/src/scalar_fn/fns/binary/mod.rs @@ -153,7 +153,7 @@ impl ScalarFnVTable for Binary { )); } vortex_bail!( - MismatchedTypes: "incompatible types for arithmetic operation: {} {}", + "incompatible types for arithmetic operation: {} {}", lhs, rhs ); @@ -164,13 +164,13 @@ impl ScalarFnVTable for Binary { && !lhs.is_extension() && !rhs.is_extension() { - vortex_bail!(MismatchedTypes: "Cannot compare different DTypes {} and {}", lhs, rhs); + vortex_bail!("Cannot compare different DTypes {} and {}", lhs, rhs); } if matches!(operator, Operator::And | Operator::Or) && !(lhs.is_boolean() && rhs.is_boolean()) { - vortex_bail!(MismatchedTypes: "'{operator}' requires bool operands, got {lhs} and {rhs}",); + vortex_bail!("'{operator}' requires bool operands, got {lhs} and {rhs}",); } Ok(DType::Bool((lhs.is_nullable() || rhs.is_nullable()).into())) diff --git a/vortex-array/src/scalar_fn/fns/binary/numeric/decimal.rs b/vortex-array/src/scalar_fn/fns/binary/numeric/decimal.rs index 86b3891c50b..8742ea66a93 100644 --- a/vortex-array/src/scalar_fn/fns/binary/numeric/decimal.rs +++ b/vortex-array/src/scalar_fn/fns/binary/numeric/decimal.rs @@ -255,10 +255,7 @@ where ::from(1_i8).vortex_expect("one fits every decimal working width"); for _ in 0..exp { factor = factor.checked_mul(&ten).ok_or_else(|| { - vortex_err!( - InvalidArgument: - "decimal scale factor 10^{exp} cannot be represented at the working width" - ) + vortex_err!("decimal scale factor 10^{exp} cannot be represented at the working width") })?; } Ok(factor) @@ -382,8 +379,8 @@ where ) => { let lhs = typed_constant::(lhs); let rhs = typed_constant::(rhs); - let value = Op::apply(lhs, rhs, constants) - .ok_or_else(|| vortex_err!(InvalidArgument: "{}", Op::ERROR))?; + let value = + Op::apply(lhs, rhs, constants).ok_or_else(|| vortex_err!("{}", Op::ERROR))?; let value = DecimalValue::from(value) .normalize(result_decimal_dtype) .vortex_expect("bounds-checked result fits the result precision"); @@ -394,7 +391,7 @@ where .into_array()); } } - .map_err(|_lane| vortex_err!(InvalidArgument: "{}", Op::ERROR))?; + .map_err(|_lane| vortex_err!("{}", Op::ERROR))?; Ok(decimal_array_narrowed( values, diff --git a/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs b/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs index 017882482db..c96aa433ba4 100644 --- a/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs +++ b/vortex-array/src/scalar_fn/fns/binary/numeric/mod.rs @@ -38,7 +38,7 @@ pub(crate) fn execute_numeric( ) -> VortexResult { vortex_ensure!( lhs.dtype().eq_ignore_nullability(rhs.dtype()), - MismatchedTypes: "numeric operator requires matching types, got {} and {}", + "numeric operator requires matching types, got {} and {}", lhs.dtype(), rhs.dtype() ); @@ -46,14 +46,14 @@ pub(crate) fn execute_numeric( let dtype = lhs.dtype(); vortex_ensure!( matches!(dtype, DType::Primitive(..) | DType::Decimal(..)), - MismatchedTypes: "numeric operator is not supported for dtype {}", + "numeric operator is not supported for dtype {}", dtype ); vortex_ensure_eq!( lhs.len(), rhs.len(), - InvalidArgument: "numeric operator requires equal lengths" + "numeric operator requires equal lengths" ); if lhs.is_empty() { diff --git a/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs b/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs index 23fbb172d6e..e750276e543 100644 --- a/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs +++ b/vortex-array/src/scalar_fn/fns/binary/numeric/row.rs @@ -69,9 +69,10 @@ impl RowFn for NumericBinary { args: &[DType], visitor: V, ) -> VortexResult { - let ptype = PType::try_from(args.first().ok_or_else( - || vortex_err!(InvalidArgument: "a numeric operator takes two operands, got none"), - )?)?; + let ptype = PType::try_from( + args.first() + .ok_or_else(|| vortex_err!("a numeric operator takes two operands, got none"))?, + )?; match_each_native_ptype!(ptype, |T| { match op { @@ -130,5 +131,5 @@ where #[cold] #[inline(never)] fn numeric_error(message: &'static str) -> VortexError { - vortex_err!(InvalidArgument: "{message}") + vortex_err!("{message}") } diff --git a/vortex-array/src/scalar_fn/fns/byte_length.rs b/vortex-array/src/scalar_fn/fns/byte_length.rs index 73c09a983cc..4a81f68681b 100644 --- a/vortex-array/src/scalar_fn/fns/byte_length.rs +++ b/vortex-array/src/scalar_fn/fns/byte_length.rs @@ -99,7 +99,7 @@ impl ScalarFnVTable for ByteLength { Ok(DType::Primitive(PType::U64, *nullable)) } other => { - vortex_bail!(InvalidArgument: "byte_length() requires Utf8 or Binary, got {other}") + vortex_bail!("byte_length() requires Utf8 or Binary, got {other}") } } } @@ -121,7 +121,7 @@ impl ScalarFnVTable for ByteLength { match input.dtype() { DType::Utf8(_) | DType::Binary(_) => byte_length(&input, nullability, ctx), other => { - vortex_bail!(InvalidArgument: "byte_length() requires Utf8 or Binary, got {other}") + vortex_bail!("byte_length() requires Utf8 or Binary, got {other}") } } } @@ -152,7 +152,7 @@ fn scalar_byte_length(scalar: &Scalar, nullability: Nullability) -> VortexResult .vortex_expect("null binary scalar") .len(), other => { - vortex_bail!(InvalidArgument: "byte_length() requires Utf8 or Binary, got {other}") + vortex_bail!("byte_length() requires Utf8 or Binary, got {other}") } }; let len: u64 = len.as_(); diff --git a/vortex-array/src/scalar_fn/fns/case_when.rs b/vortex-array/src/scalar_fn/fns/case_when.rs index 5e26eb5e9f0..1a2e7f6abb5 100644 --- a/vortex-array/src/scalar_fn/fns/case_when.rs +++ b/vortex-array/src/scalar_fn/fns/case_when.rs @@ -98,14 +98,14 @@ impl ScalarFnVTable for CaseWhen { fn serialize(&self, options: &Self::Options) -> VortexResult>> { vortex_ensure!( options.num_when_then_pairs > 0, - InvalidArgument: "CaseWhen must have at least one WHEN/THEN pair" + "CaseWhen must have at least one WHEN/THEN pair" ); let Some(num_children) = options .num_when_then_pairs .checked_mul(2) .and_then(|count| count.checked_add(u32::from(options.has_else))) else { - vortex_bail!(Overflow: "CaseWhen has too many children to serialize"); + vortex_bail!("CaseWhen has too many children to serialize"); }; Ok(Some(pb::CaseWhenOpts { num_children }.encode_to_vec())) } @@ -118,7 +118,7 @@ impl ScalarFnVTable for CaseWhen { let opts = pb::CaseWhenOpts::decode(metadata)?; if opts.num_children < 2 { vortex_bail!( - InvalidArgument: "CaseWhen expects at least 2 children, got {}", + "CaseWhen expects at least 2 children, got {}", opts.num_children ); } @@ -172,13 +172,13 @@ impl ScalarFnVTable for CaseWhen { fn return_dtype(&self, options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { if options.num_when_then_pairs == 0 { - vortex_bail!(InvalidArgument: "CaseWhen must have at least one WHEN/THEN pair"); + vortex_bail!("CaseWhen must have at least one WHEN/THEN pair"); } let expected_len = options.num_children(); if arg_dtypes.len() != expected_len { vortex_bail!( - InvalidArgument: "CaseWhen expects {expected_len} argument dtypes, got {}", + "CaseWhen expects {expected_len} argument dtypes, got {}", arg_dtypes.len() ); } @@ -193,7 +193,7 @@ impl ScalarFnVTable for CaseWhen { let then_i = &arg_dtypes[i * 2 + 1]; let Some(union) = zip_nullability_union(&result_dtype, then_i) else { vortex_bail!( - MismatchedTypes: "CaseWhen THEN dtypes must match (ignoring nullability), got {} and {}", + "CaseWhen THEN dtypes must match (ignoring nullability), got {} and {}", first_then, then_i ); @@ -205,7 +205,7 @@ impl ScalarFnVTable for CaseWhen { let else_dtype = &arg_dtypes[options.num_when_then_pairs as usize * 2]; let Some(union) = zip_nullability_union(&result_dtype, else_dtype) else { vortex_bail!( - MismatchedTypes: "CaseWhen THEN and ELSE dtypes must match (ignoring nullability), got {} and {}", + "CaseWhen THEN and ELSE dtypes must match (ignoring nullability), got {} and {}", first_then, else_dtype ); diff --git a/vortex-array/src/scalar_fn/fns/cast/mod.rs b/vortex-array/src/scalar_fn/fns/cast/mod.rs index 0f4da74ade8..f3d90cf05fc 100644 --- a/vortex-array/src/scalar_fn/fns/cast/mod.rs +++ b/vortex-array/src/scalar_fn/fns/cast/mod.rs @@ -91,7 +91,7 @@ impl ScalarFnVTable for Cast { DType::from_proto( proto .as_ref() - .ok_or_else(|| vortex_err!(Serde: "Missing target dtype in Cast expression"))?, + .ok_or_else(|| vortex_err!("Missing target dtype in Cast expression"))?, session, ) } @@ -140,7 +140,7 @@ impl ScalarFnVTable for Cast { match cast_canonical(canonical, target_dtype, ctx)? { Some(result) => Ok(result), None => vortex_bail!( - NotImplemented: "No CastKernel to cast canonical array {} from {} to {}", + "No CastKernel to cast canonical array {} from {} to {}", canonical.to_array_ref().encoding_id(), canonical.to_array_ref().dtype(), target_dtype, @@ -223,13 +223,13 @@ fn cast_canonical( CanonicalView::Struct(a) => struct_cast(a, dtype, ctx), CanonicalView::Union(_) => { vortex_bail!( - NotImplemented: "TODO(connor)[Union]: implement Union casting with conformance coverage for \ + "TODO(connor)[Union]: implement Union casting with conformance coverage for \ outer nullability changes, including validation of nullable-to-nonnullable casts" ) } CanonicalView::Extension(a) => ::cast(a, dtype), CanonicalView::Variant(_) => { - vortex_bail!(NotImplemented: "Variant arrays don't support casting") + vortex_bail!("Variant arrays don't support casting") } } } @@ -323,9 +323,9 @@ mod tests { ); let optimized = expr.bind(&test_harness::struct_dtype())?.optimize()?; - let scalar = optimized.as_opt::().ok_or_else( - || vortex_err!(MismatchedTypes: "expected a bare literal, got {optimized}"), - )?; + let scalar = optimized + .as_opt::() + .ok_or_else(|| vortex_err!("expected a bare literal, got {optimized}"))?; assert_eq!(scalar, &Scalar::primitive(3.0f64, Nullability::NonNullable)); Ok(()) } @@ -343,9 +343,9 @@ mod tests { ); let optimized = expr.bind(&test_harness::struct_dtype())?.optimize()?; - let scalar = optimized.as_opt::().ok_or_else( - || vortex_err!(MismatchedTypes: "expected a bare literal, got {optimized}"), - )?; + let scalar = optimized + .as_opt::() + .ok_or_else(|| vortex_err!("expected a bare literal, got {optimized}"))?; assert_eq!( scalar, &Scalar::primitive(3.19f64, Nullability::NonNullable) diff --git a/vortex-array/src/scalar_fn/fns/dynamic.rs b/vortex-array/src/scalar_fn/fns/dynamic.rs index 4c6e835997c..7ce5a17dd3b 100644 --- a/vortex-array/src/scalar_fn/fns/dynamic.rs +++ b/vortex-array/src/scalar_fn/fns/dynamic.rs @@ -85,7 +85,7 @@ impl ScalarFnVTable for DynamicComparison { let lhs = &arg_dtypes[0]; if !dynamic.rhs.dtype.eq_ignore_nullability(lhs) { vortex_bail!( - MismatchedTypes: "Incompatible dtypes for dynamic comparison: expected {} (ignore nullability) but got {}", + "Incompatible dtypes for dynamic comparison: expected {} (ignore nullability) but got {}", &dynamic.rhs.dtype, lhs ); diff --git a/vortex-array/src/scalar_fn/fns/ext_storage.rs b/vortex-array/src/scalar_fn/fns/ext_storage.rs index 75f054ae278..1e708cf2414 100644 --- a/vortex-array/src/scalar_fn/fns/ext_storage.rs +++ b/vortex-array/src/scalar_fn/fns/ext_storage.rs @@ -57,7 +57,7 @@ impl ScalarFnVTable for ExtStorage { fn return_dtype(&self, _options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { let DType::Extension(ext_dtype) = &arg_dtypes[0] else { - vortex_bail!(InvalidArgument: "ext_storage() requires Extension, got {}", arg_dtypes[0]); + vortex_bail!("ext_storage() requires Extension, got {}", arg_dtypes[0]); }; Ok(ext_dtype.storage_dtype().clone()) @@ -72,7 +72,7 @@ impl ScalarFnVTable for ExtStorage { let input = args.get(0)?; if !matches!(input.dtype(), DType::Extension(_)) { - vortex_bail!(InvalidArgument: "ext_storage() requires Extension, got {}", input.dtype()); + vortex_bail!("ext_storage() requires Extension, got {}", input.dtype()); } if let Some(scalar) = input.as_constant() { diff --git a/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs b/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs index 853f5449b0d..1fdcf1c2d76 100644 --- a/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs +++ b/vortex-array/src/scalar_fn/fns/fill_null/kernel.rs @@ -70,7 +70,7 @@ pub(super) fn short_circuit( ) -> VortexResult> { vortex_ensure!( !fill_value.is_null(), - InvalidArgument: "fill_null requires a non-null fill value" + "fill_null requires a non-null fill value" ); // If the array has no nulls, fill_null is a no-op (just cast for nullability). diff --git a/vortex-array/src/scalar_fn/fns/fill_null/mod.rs b/vortex-array/src/scalar_fn/fns/fill_null/mod.rs index 9450a945ac6..5d17aaa68b8 100644 --- a/vortex-array/src/scalar_fn/fns/fill_null/mod.rs +++ b/vortex-array/src/scalar_fn/fns/fill_null/mod.rs @@ -105,7 +105,7 @@ impl ScalarFnVTable for FillNull { fn return_dtype(&self, _options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { vortex_ensure!( arg_dtypes[0].eq_ignore_nullability(&arg_dtypes[1]), - MismatchedTypes: "fill_null requires input and fill value to have the same base type, got {} and {}", + "fill_null requires input and fill value to have the same base type, got {} and {}", arg_dtypes[0], arg_dtypes[1] ); @@ -137,7 +137,7 @@ impl ScalarFnVTable for FillNull { // than a constant. An empty input has no nulls to fill, so there is nothing to do. vortex_ensure!( input.is_empty(), - InvalidArgument: "fill_null fill_value must be a constant/scalar" + "fill_null fill_value must be a constant/scalar" ); let dtype = input .dtype() @@ -147,7 +147,7 @@ impl ScalarFnVTable for FillNull { vortex_ensure!( !fill_scalar.is_null(), - InvalidArgument: "fill_null requires a non-null fill value" + "fill_null requires a non-null fill value" ); let Some(columnar) = input.as_opt::() else { @@ -216,25 +216,19 @@ fn fill_null_canonical( } match canonical { CanonicalView::Bool(a) => ::fill_null(a, fill_value, ctx)? - .ok_or_else( - || vortex_err!(AssertionFailed: "FillNullKernel for BoolArray returned None"), - ), + .ok_or_else(|| vortex_err!("FillNullKernel for BoolArray returned None")), CanonicalView::Primitive(a) => { - ::fill_null(a, fill_value, ctx)?.ok_or_else( - || vortex_err!(AssertionFailed: "FillNullKernel for PrimitiveArray returned None"), - ) + ::fill_null(a, fill_value, ctx)? + .ok_or_else(|| vortex_err!("FillNullKernel for PrimitiveArray returned None")) } CanonicalView::Decimal(a) => ::fill_null(a, fill_value, ctx)? - .ok_or_else( - || vortex_err!(AssertionFailed: "FillNullKernel for DecimalArray returned None"), - ), + .ok_or_else(|| vortex_err!("FillNullKernel for DecimalArray returned None")), CanonicalView::VarBinView(a) => { - ::fill_null(a, fill_value, ctx)?.ok_or_else( - || vortex_err!(AssertionFailed: "FillNullKernel for VarBinViewArray returned None"), - ) + ::fill_null(a, fill_value, ctx)? + .ok_or_else(|| vortex_err!("FillNullKernel for VarBinViewArray returned None")) } other => vortex_bail!( - NotImplemented: "No FillNullKernel for canonical array {}", + "No FillNullKernel for canonical array {}", other.to_array_ref().encoding_id() ), } diff --git a/vortex-array/src/scalar_fn/fns/get_item.rs b/vortex-array/src/scalar_fn/fns/get_item.rs index b49c1020a4b..663e3eebdbf 100644 --- a/vortex-array/src/scalar_fn/fns/get_item.rs +++ b/vortex-array/src/scalar_fn/fns/get_item.rs @@ -157,7 +157,7 @@ impl ScalarFnVTable for GetItem { .as_struct_fields_opt() .and_then(|st| st.field(field_name)) .ok_or_else(|| { - vortex_err!(NotFound: "Couldn't find the {} field in the input scope", field_name) + vortex_err!("Couldn't find the {} field in the input scope", field_name) })?; // Match here to avoid cloning the dtype if nullability doesn't need to change @@ -189,7 +189,7 @@ impl ScalarFnVTable for GetItem { .field(field_name) .ok_or_else(|| { vortex_err!( - NotFound: "Field '{}' missing from constant struct array {}", + "Field '{}' missing from constant struct array {}", field_name, input.dtype() ) diff --git a/vortex-array/src/scalar_fn/fns/is_nan.rs b/vortex-array/src/scalar_fn/fns/is_nan.rs index f6aebc48630..c8059a4e6ab 100755 --- a/vortex-array/src/scalar_fn/fns/is_nan.rs +++ b/vortex-array/src/scalar_fn/fns/is_nan.rs @@ -38,7 +38,7 @@ impl RowFn for IsNan { ) -> VortexResult { let ptype = match args { [DType::Primitive(ptype, _)] if ptype.is_float() => *ptype, - _ => vortex_bail!(InvalidArgument: "is_nan expects a single float input, got {args:?}"), + _ => vortex_bail!("is_nan expects a single float input, got {args:?}"), }; match_each_float_ptype!(ptype, |T| { visitor.visit_bool::<(T,), false>(|(value,)| value.is_nan()) diff --git a/vortex-array/src/scalar_fn/fns/like/mod.rs b/vortex-array/src/scalar_fn/fns/like/mod.rs index 17402584eea..da0d094c201 100644 --- a/vortex-array/src/scalar_fn/fns/like/mod.rs +++ b/vortex-array/src/scalar_fn/fns/like/mod.rs @@ -145,11 +145,11 @@ impl ScalarFnVTable for Like { let pattern = &arg_dtypes[1]; if !input.is_utf8() { - vortex_bail!(InvalidArgument: "LIKE expression requires UTF8 input dtype, got {}", input); + vortex_bail!("LIKE expression requires UTF8 input dtype, got {}", input); } if !pattern.is_utf8() { vortex_bail!( - InvalidArgument: "LIKE expression requires UTF8 pattern dtype, got {}", + "LIKE expression requires UTF8 pattern dtype, got {}", pattern ); } @@ -244,9 +244,8 @@ pub(crate) fn execute_like( let compiled = match &cached { Some((bytes, compiled)) if *bytes == pattern_bytes => compiled, _ => { - let pattern_str = std::str::from_utf8(pattern_bytes).map_err( - |e| vortex_err!(InvalidArgument: "LIKE pattern is not valid UTF-8: {e}"), - )?; + let pattern_str = std::str::from_utf8(pattern_bytes) + .map_err(|e| vortex_err!("LIKE pattern is not valid UTF-8: {e}"))?; let compiled = LikePattern::compile( pattern_str, options.case_insensitive, diff --git a/vortex-array/src/scalar_fn/fns/like/pattern.rs b/vortex-array/src/scalar_fn/fns/like/pattern.rs index e6a89fb84ea..ced63d033d8 100644 --- a/vortex-array/src/scalar_fn/fns/like/pattern.rs +++ b/vortex-array/src/scalar_fn/fns/like/pattern.rs @@ -189,7 +189,7 @@ fn regex_like(pattern: &str, case_insensitive: bool) -> VortexResult { .case_insensitive(case_insensitive) .dot_matches_new_line(true) .build() - .map_err(|e| vortex_err!(InvalidArgument: "Unable to build regex from LIKE pattern: {e}")) + .map_err(|e| vortex_err!("Unable to build regex from LIKE pattern: {e}")) } #[cfg(test)] diff --git a/vortex-array/src/scalar_fn/fns/list_contains/mod.rs b/vortex-array/src/scalar_fn/fns/list_contains/mod.rs index 941767c08e8..5d92baac6f6 100644 --- a/vortex-array/src/scalar_fn/fns/list_contains/mod.rs +++ b/vortex-array/src/scalar_fn/fns/list_contains/mod.rs @@ -181,13 +181,13 @@ impl ScalarFnVTable for ListContains { let DType::List(element_dtype, _) = list_dtype else { vortex_bail!( - MismatchedTypes: "First argument to ListContains must be a List, got {:?}", + "First argument to ListContains must be a List, got {:?}", list_dtype ); }; if !element_dtype.eq_ignore_nullability(needle_dtype) { vortex_bail!( - MismatchedTypes: "Element type {} of list does not match search value {}", + "Element type {} of list does not match search value {}", element_dtype, needle_dtype, ); @@ -297,7 +297,7 @@ fn compute_contains_scalar( ) -> VortexResult { if !matches!(list.dtype(), DType::List(..)) { vortex_bail!( - MismatchedTypes: "First argument to ListContains must be a List, got {}", + "First argument to ListContains must be a List, got {}", list.dtype() ); } @@ -310,7 +310,7 @@ fn compute_contains_scalar( let list_scalar = list.as_list(); let elements = list_scalar .elements() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null list"))?; + .ok_or_else(|| vortex_err!("Expected non-null list"))?; if needle.is_null() { return Ok(if elements.is_empty() && !options.sql_null_semantics { @@ -334,11 +334,11 @@ fn compute_list_contains( ctx: &mut ExecutionCtx, ) -> VortexResult { let DType::List(elem_dtype, _) = array.dtype() else { - vortex_bail!(InvalidArgument: "Array must be of List type"); + vortex_bail!("Array must be of List type"); }; if !elem_dtype.as_ref().eq_ignore_nullability(value.dtype()) { vortex_bail!( - MismatchedTypes: "Element type {} of list does not match search value {}", + "Element type {} of list does not match search value {}", elem_dtype, value.dtype(), ); diff --git a/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs b/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs index 20f0e73ffdc..aaaf047c1d9 100644 --- a/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs +++ b/vortex-array/src/scalar_fn/fns/list_contains/prepared/data.rs @@ -94,15 +94,15 @@ impl PreparedSetData { pub(crate) fn try_from_literal(literal: ScalarFnRef) -> VortexResult { let (has_null_element, is_empty) = { let Some(list) = literal.as_opt::() else { - vortex_bail!(InvalidArgument: "A prepared set needs a literal list"); + vortex_bail!("A prepared set needs a literal list"); }; vortex_ensure!( matches!(list.dtype(), DType::List(..)), - MismatchedTypes: "A prepared set needs a list, got {}", + "A prepared set needs a list, got {}", list.dtype() ); let Some(elements) = list.as_list().element_values() else { - vortex_bail!(InvalidArgument: "A prepared set needs a non-null list"); + vortex_bail!("A prepared set needs a non-null list"); }; (elements.iter().any(Option::is_none), elements.is_empty()) }; @@ -157,7 +157,7 @@ impl PreparedSetData { /// The dtype of the list's elements. fn element_dtype(&self) -> &DType { let DType::List(element_dtype, _) = self.list_dtype() else { - vortex_panic!(AssertionFailed: "A prepared set always holds a list"); + vortex_panic!("A prepared set always holds a list"); }; element_dtype } @@ -234,7 +234,7 @@ impl PreparedSetData { if let Some(len) = needle_validity.maybe_len() { vortex_ensure!( len == bits.len(), - InvalidArgument: "Needle validity has {len} rows, but there are {} membership bits", + "Needle validity has {len} rows, but there are {} membership bits", bits.len() ); } @@ -258,7 +258,7 @@ impl PreparedSetData { let element_dtype = self.element_dtype(); if !element_dtype.eq_ignore_nullability(needle_dtype) { vortex_bail!( - MismatchedTypes: "Element type {} of list does not match search value {}", + "Element type {} of list does not match search value {}", element_dtype, needle_dtype, ); diff --git a/vortex-array/src/scalar_fn/fns/list_length.rs b/vortex-array/src/scalar_fn/fns/list_length.rs index 67f9c3049fb..a456511de14 100644 --- a/vortex-array/src/scalar_fn/fns/list_length.rs +++ b/vortex-array/src/scalar_fn/fns/list_length.rs @@ -79,7 +79,7 @@ impl ScalarFnVTable for ListLength { Ok(DType::Primitive(PType::U64, *nullable)) } other => { - vortex_bail!(InvalidArgument: "list_length() requires List or FixedSizeList, got {other}") + vortex_bail!("list_length() requires List or FixedSizeList, got {other}") } } } @@ -143,7 +143,7 @@ pub(crate) fn list_length( (lengths, l.list_validity()) } else { let dtype = any_list.dtype(); - vortex_bail!(InvalidArgument: "list_length() requires List, ListView, or FixedSizeList but got {dtype}") + vortex_bail!("list_length() requires List, ListView, or FixedSizeList but got {dtype}") }; // Cast to `U64` diff --git a/vortex-array/src/scalar_fn/fns/list_sum.rs b/vortex-array/src/scalar_fn/fns/list_sum.rs index 2baf541d058..c5818ef012e 100644 --- a/vortex-array/src/scalar_fn/fns/list_sum.rs +++ b/vortex-array/src/scalar_fn/fns/list_sum.rs @@ -73,12 +73,12 @@ impl ScalarFnVTable for ListSum { let elem_dtype = match &arg_dtypes[0] { DType::List(elem, _) | DType::FixedSizeList(elem, ..) => elem.as_ref(), other => { - vortex_bail!(InvalidArgument: "list_sum() requires List or FixedSizeList, got {other}") + vortex_bail!("list_sum() requires List or FixedSizeList, got {other}") } }; - SumV2.return_dtype(options, elem_dtype).ok_or_else( - || vortex_err!(MismatchedTypes: "list_sum() cannot sum elements of type {elem_dtype}"), - ) + SumV2 + .return_dtype(options, elem_dtype) + .ok_or_else(|| vortex_err!("list_sum() cannot sum elements of type {elem_dtype}")) } fn execute( @@ -92,7 +92,7 @@ impl ScalarFnVTable for ListSum { let elem_dtype = match input.dtype() { DType::List(elem, _) | DType::FixedSizeList(elem, ..) => elem.as_ref().clone(), other => { - vortex_bail!(InvalidArgument: "list_sum() requires List or FixedSizeList, got {other}") + vortex_bail!("list_sum() requires List or FixedSizeList, got {other}") } }; diff --git a/vortex-array/src/scalar_fn/fns/literal.rs b/vortex-array/src/scalar_fn/fns/literal.rs index 1d7aaa09a6a..cb6c3284523 100644 --- a/vortex-array/src/scalar_fn/fns/literal.rs +++ b/vortex-array/src/scalar_fn/fns/literal.rs @@ -55,7 +55,7 @@ impl ScalarFnVTable for Literal { Scalar::from_proto( ops.value .as_ref() - .ok_or_else(|| vortex_err!(NotFound: "Literal metadata missing value"))?, + .ok_or_else(|| vortex_err!("Literal metadata missing value"))?, session, ) } diff --git a/vortex-array/src/scalar_fn/fns/mask/kernel.rs b/vortex-array/src/scalar_fn/fns/mask/kernel.rs index 3732f1bcf0d..b03c2dd5509 100644 --- a/vortex-array/src/scalar_fn/fns/mask/kernel.rs +++ b/vortex-array/src/scalar_fn/fns/mask/kernel.rs @@ -82,7 +82,7 @@ where let parent_ref: ArrayRef = (*parent).clone(); let mask_child = parent_ref .nth_child(1) - .ok_or_else(|| vortex_err!(AssertionFailed: "Mask expression must have 2 children"))?; + .ok_or_else(|| vortex_err!("Mask expression must have 2 children"))?; if mask_child.as_opt::().is_none() && mask_child.as_opt::().is_none() { let can_attach_mask = @@ -120,7 +120,7 @@ where } let mask_child = parent .nth_child(1) - .ok_or_else(|| vortex_err!(AssertionFailed: "Mask expression must have 2 children"))?; + .ok_or_else(|| vortex_err!("Mask expression must have 2 children"))?; ::mask(array, mask_child, ctx) } } diff --git a/vortex-array/src/scalar_fn/fns/mask/mod.rs b/vortex-array/src/scalar_fn/fns/mask/mod.rs index 82244fdafd8..994c409adc3 100644 --- a/vortex-array/src/scalar_fn/fns/mask/mod.rs +++ b/vortex-array/src/scalar_fn/fns/mask/mod.rs @@ -94,7 +94,7 @@ impl ScalarFnVTable for Mask { vortex_ensure_eq!( arg_dtypes[1], DType::Bool(Nullability::NonNullable), - MismatchedTypes: "The mask argument to 'mask' must be a non-nullable boolean array" + "The mask argument to 'mask' must be a non-nullable boolean array" ); Ok(arg_dtypes[0].as_nullable()) } diff --git a/vortex-array/src/scalar_fn/fns/merge.rs b/vortex-array/src/scalar_fn/fns/merge.rs index 0470453d488..4913b120000 100644 --- a/vortex-array/src/scalar_fn/fns/merge.rs +++ b/vortex-array/src/scalar_fn/fns/merge.rs @@ -68,7 +68,7 @@ impl ScalarFnVTable for Merge { [0x00] => DuplicateHandling::RightMost, [0x01] => DuplicateHandling::Error, _ => { - vortex_bail!(InvalidArgument: "invalid metadata for Merge expression"); + vortex_bail!("invalid metadata for Merge expression"); } }; Ok(instance) @@ -90,10 +90,10 @@ impl ScalarFnVTable for Merge { for dtype in arg_dtypes { let Some(fields) = dtype.as_struct_fields_opt() else { - vortex_bail!(InvalidArgument: "merge expects struct input"); + vortex_bail!("merge expects struct input"); }; if dtype.is_nullable() { - vortex_bail!(InvalidArgument: "merge expects non-nullable input"); + vortex_bail!("merge expects non-nullable input"); } merge_nullability |= dtype.nullability(); @@ -111,7 +111,7 @@ impl ScalarFnVTable for Merge { if options == &DuplicateHandling::Error && !duplicate_names.is_empty() { vortex_bail!( - InvalidArgument: "merge: duplicate fields in children: {}", + "merge: duplicate fields in children: {}", duplicate_names.into_iter().format(", ") ) } @@ -136,7 +136,7 @@ impl ScalarFnVTable for Merge { for i in 0..args.num_inputs() { let array = args.get(i)?.execute::(ctx)?; if array.dtype().is_nullable() { - vortex_bail!(InvalidArgument: "merge expects non-nullable input"); + vortex_bail!("merge expects non-nullable input"); } for (field_name, field_array) in array @@ -157,7 +157,7 @@ impl ScalarFnVTable for Merge { if options == &DuplicateHandling::Error && !duplicate_names.is_empty() { vortex_bail!( - InvalidArgument: "merge: duplicate fields in children: {}", + "merge: duplicate fields in children: {}", duplicate_names.into_iter().format(", ") ) } @@ -180,7 +180,7 @@ impl ScalarFnVTable for Merge { let child_dtype = child.node_dtype()?; if !child_dtype.is_struct() || child_dtype.is_nullable() { vortex_bail!( - MismatchedTypes: "Merge child must return a non-nullable struct dtype, got {}", + "Merge child must return a non-nullable struct dtype, got {}", child_dtype ) } @@ -207,7 +207,7 @@ impl ScalarFnVTable for Merge { if options == &DuplicateHandling::Error && !duplicate_names.is_empty() { vortex_bail!( - InvalidArgument: "merge: duplicate fields in children: {}", + "merge: duplicate fields in children: {}", duplicate_names.into_iter().format(", ") ) } @@ -289,7 +289,7 @@ mod tests { let mut field_path = field_path.iter(); let Some(field) = field_path.next() else { - vortex_bail!(InvalidArgument: "empty field path"); + vortex_bail!("empty field path"); }; let mut array = array diff --git a/vortex-array/src/scalar_fn/fns/not/mod.rs b/vortex-array/src/scalar_fn/fns/not/mod.rs index dd9ef935be9..b4c0c1b3bb5 100644 --- a/vortex-array/src/scalar_fn/fns/not/mod.rs +++ b/vortex-array/src/scalar_fn/fns/not/mod.rs @@ -78,7 +78,7 @@ impl ScalarFnVTable for Not { let child_dtype = &arg_dtypes[0]; if !matches!(child_dtype, DType::Bool(_)) { vortex_bail!( - InvalidArgument: "Not expression expects a boolean child, got: {}", + "Not expression expects a boolean child, got: {}", child_dtype ); } diff --git a/vortex-array/src/scalar_fn/fns/operators.rs b/vortex-array/src/scalar_fn/fns/operators.rs index aa209531e46..3fdc921e39d 100644 --- a/vortex-array/src/scalar_fn/fns/operators.rs +++ b/vortex-array/src/scalar_fn/fns/operators.rs @@ -273,9 +273,9 @@ impl TryFrom for CompareOperator { type Error = VortexError; fn try_from(value: Operator) -> Result { - value.to_compare_operator().ok_or_else( - || vortex_error::vortex_err!(InvalidArgument: "{value} is not a comparison operator"), - ) + value + .to_compare_operator() + .ok_or_else(|| vortex_error::vortex_err!("{value} is not a comparison operator")) } } diff --git a/vortex-array/src/scalar_fn/fns/pack.rs b/vortex-array/src/scalar_fn/fns/pack.rs index 9eac75a8e89..c9e5a60ec3a 100644 --- a/vortex-array/src/scalar_fn/fns/pack.rs +++ b/vortex-array/src/scalar_fn/fns/pack.rs @@ -201,7 +201,7 @@ mod tests { let mut field_path = field_path.iter(); let Some(field) = field_path.next() else { - vortex_bail!(InvalidArgument: "empty field path"); + vortex_bail!("empty field path"); }; let mut array = array diff --git a/vortex-array/src/scalar_fn/fns/replace_time_zone.rs b/vortex-array/src/scalar_fn/fns/replace_time_zone.rs index 7c9d5f65f17..a07029cfe70 100644 --- a/vortex-array/src/scalar_fn/fns/replace_time_zone.rs +++ b/vortex-array/src/scalar_fn/fns/replace_time_zone.rs @@ -131,11 +131,11 @@ impl ScalarFnVTable for ReplaceTimeZone { fn return_dtype(&self, options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { let input = timestamp_options(&arg_dtypes[0])?; if input.unit == TimeUnit::Days { - vortex_bail!(InvalidArgument: "Timestamp cannot use day units"); + vortex_bail!("Timestamp cannot use day units"); } if !matches!(arg_dtypes[1], DType::Utf8(_) | DType::Null) { vortex_bail!( - MismatchedTypes: "replace_time_zone() requires a UTF-8 ambiguity policy, got {}", + "replace_time_zone() requires a UTF-8 ambiguity policy, got {}", arg_dtypes[1] ); } @@ -238,7 +238,7 @@ fn replace_scalar( let policy = policy .as_utf8() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "Missing ambiguity policy"))?; + .ok_or_else(|| vortex_err!("Missing ambiguity policy"))?; replace( i64::try_from(&storage)?, metadata.unit, @@ -261,7 +261,7 @@ fn timestamp_options(dtype: &DType) -> VortexResult<&TimestampOptions> { { return Ok(options); } - vortex_bail!(MismatchedTypes: "replace_time_zone() requires Timestamp, got {dtype}") + vortex_bail!("replace_time_zone() requires Timestamp, got {dtype}") } fn replace( @@ -274,7 +274,7 @@ fn replace( ) -> VortexResult> { if !matches!(policy, "raise" | "earliest" | "latest" | "null") { vortex_bail!( - InvalidArgument: "Invalid ambiguity policy {policy:?}: expected raise, earliest, latest, or null" + "Invalid ambiguity policy {policy:?}: expected raise, earliest, latest, or null" ); } // Keeping the same timezone does not introduce a new ambiguity to reject. @@ -286,7 +286,7 @@ fn replace( TimeUnit::Milliseconds => JiffTimestamp::from_millisecond(value)?, TimeUnit::Microseconds => JiffTimestamp::from_microsecond(value)?, TimeUnit::Nanoseconds => JiffTimestamp::from_nanosecond(i128::from(value))?, - TimeUnit::Days => vortex_bail!(InvalidArgument: "Timestamp cannot use day units"), + TimeUnit::Days => vortex_bail!("Timestamp cannot use day units"), }; let wall_time = source.to_datetime(timestamp); let ambiguous = target.to_ambiguous_timestamp(wall_time); @@ -306,7 +306,7 @@ fn replace( TimeUnit::Milliseconds => timestamp.as_millisecond(), TimeUnit::Microseconds => timestamp.as_microsecond(), TimeUnit::Nanoseconds => i64::try_from(timestamp.as_nanosecond()) - .map_err(|e| vortex_err!(Overflow: "Timestamp overflow: {e}"))?, + .map_err(|e| vortex_err!("Timestamp overflow: {e}"))?, TimeUnit::Days => unreachable!(), })) } @@ -476,9 +476,9 @@ mod tests { let optimized = expr.bind(&scope)?.optimize()?; // Stats pruning only matches bare literal operands, so the replacement must fold. - let scalar = optimized.as_opt::().ok_or_else( - || vortex_err!(MismatchedTypes: "expected a bare literal, got {optimized}"), - )?; + let scalar = optimized + .as_opt::() + .ok_or_else(|| vortex_err!("expected a bare literal, got {optimized}"))?; assert_eq!( scalar, &Scalar::extension_ref( diff --git a/vortex-array/src/scalar_fn/fns/select.rs b/vortex-array/src/scalar_fn/fns/select.rs index 29527ce591b..e410105d1b4 100644 --- a/vortex-array/src/scalar_fn/fns/select.rs +++ b/vortex-array/src/scalar_fn/fns/select.rs @@ -80,7 +80,7 @@ impl ScalarFnVTable for Select { let select_opts = prost_metadata .opts - .ok_or_else(|| vortex_err!(Serde: "SelectOpts missing opts field"))?; + .ok_or_else(|| vortex_err!("SelectOpts missing opts field"))?; let field_selection = match select_opts { Opts::Include(field_names) => FieldSelection::Include(FieldNames::from_iter( @@ -130,7 +130,7 @@ impl ScalarFnVTable for Select { let child_dtype = &arg_dtypes[0]; let child_struct_dtype = child_dtype .as_struct_fields_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Select child not a struct dtype"))?; + .ok_or_else(|| vortex_err!("Select child not a struct dtype"))?; let projected = match selection { FieldSelection::Include(fields) => child_struct_dtype.project(fields.as_ref())?, @@ -157,7 +157,7 @@ impl ScalarFnVTable for Select { let child_struct_dtype = child .dtype() .as_struct_fields_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Select child not a struct dtype"))?; + .ok_or_else(|| vortex_err!("Select child not a struct dtype"))?; let included = selection.normalize_to_included_fields(child_struct_dtype.names())?; let scalar = constant.scalar().as_struct().project(included.as_ref())?; @@ -193,7 +193,7 @@ impl ScalarFnVTable for Select { let struct_fields = struct_dtype.as_struct_fields_opt().ok_or_else(|| { vortex_err!( - MismatchedTypes: "Select child must return a struct dtype, however it was a {}", + "Select child must return a struct dtype, however it was a {}", struct_dtype ) })?; @@ -248,7 +248,7 @@ impl ScalarFnVTable for Select { .map(|name| { let idx = child_pack.names.find(name).ok_or_else(|| { vortex_err!( - NotFound: "Cannot find field {} in pack fields {:?}", + "Cannot find field {} in pack fields {:?}", name, child_pack.names ) @@ -315,7 +315,7 @@ impl FieldSelection { // Check that all of the field names exist in the available fields. if self.field_names().iter().any(|f| !available.contains(f)) { vortex_bail!( - InvalidArgument: "Select fields {:?} must be a subset of child fields {:?}", + "Select fields {:?} must be a subset of child fields {:?}", self, available_fields ); diff --git a/vortex-array/src/scalar_fn/fns/stat.rs b/vortex-array/src/scalar_fn/fns/stat.rs index 8609c68c7c3..c961ac10d53 100644 --- a/vortex-array/src/scalar_fn/fns/stat.rs +++ b/vortex-array/src/scalar_fn/fns/stat.rs @@ -132,7 +132,7 @@ impl ScalarFnVTable for StatFn { fn stat_dtype(aggregate_fn: &AggregateFnRef, input_dtype: &DType) -> VortexResult { let Some(dtype) = aggregate_fn.state_dtype(input_dtype) else { vortex_bail!( - InvalidArgument: "Aggregate function {} does not support input dtype {}", + "Aggregate function {} does not support input dtype {}", aggregate_fn, input_dtype ); diff --git a/vortex-array/src/scalar_fn/fns/variant_get/mod.rs b/vortex-array/src/scalar_fn/fns/variant_get/mod.rs index 0be78f8d6a9..ef493d0146e 100644 --- a/vortex-array/src/scalar_fn/fns/variant_get/mod.rs +++ b/vortex-array/src/scalar_fn/fns/variant_get/mod.rs @@ -122,7 +122,7 @@ impl ScalarFnVTable for VariantGet { let input_dtype = &arg_dtypes[0]; vortex_ensure!( matches!(input_dtype, DType::Variant(_)), - MismatchedTypes: "VariantGet input must be Variant, found {input_dtype}" + "VariantGet input must be Variant, found {input_dtype}" ); // Missing paths, traversal mismatches, and cast failures all produce nulls. @@ -367,7 +367,7 @@ impl VariantPathElement { pub fn from_proto(value: pb::VariantPathElement) -> VortexResult { match value .element - .ok_or_else(|| vortex_err!(NotFound: "Variant path element missing value"))? + .ok_or_else(|| vortex_err!("Variant path element missing value"))? { variant_path_element::Element::Field(field) => Ok(Self::field(field)), variant_path_element::Element::Index(index) => Ok(Self::index(index)), @@ -487,7 +487,7 @@ mod tests { .get(pos) .is_some_and(|byte| !matches!(byte, b'.' | b'[')) { - vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.' or '[' after '$'"); + vortex_bail!("Invalid Variant path {path:?}: expected '.' or '[' after '$'"); } while pos < path.len() { @@ -509,7 +509,7 @@ mod tests { pos = next_pos; } _ => { - vortex_bail!(InvalidArgument: "Invalid Variant path {path:?}: expected '.', '[', or end of path") + vortex_bail!("Invalid Variant path {path:?}: expected '.', '[', or end of path") } } } @@ -528,7 +528,7 @@ mod tests { } vortex_ensure!( pos > start, - InvalidArgument: "Invalid Variant path {path:?}: expected field name" + "Invalid Variant path {path:?}: expected field name" ); Ok((&path[start..pos], pos)) } @@ -544,15 +544,15 @@ mod tests { } vortex_ensure!( pos > start, - InvalidArgument: "Invalid Variant path {path:?}: expected list index" + "Invalid Variant path {path:?}: expected list index" ); vortex_ensure!( path.as_bytes().get(pos) == Some(&b']'), - InvalidArgument: "Invalid Variant path {path:?}: expected closing ']'" + "Invalid Variant path {path:?}: expected closing ']'" ); - let index = path[start..pos].parse().map_err( - |_| vortex_err!(Overflow: "Invalid Variant path {path:?}: list index is too large"), - )?; + let index = path[start..pos] + .parse() + .map_err(|_| vortex_err!("Invalid Variant path {path:?}: list index is too large"))?; Ok((index, pos + 1)) } @@ -826,7 +826,7 @@ mod tests { .execute::(&mut SESSION.create_execution_ctx())?; let canonical = result.execute::(&mut SESSION.create_execution_ctx())?; let Canonical::Variant(canonical_variant) = canonical else { - vortex_bail!(InvalidArgument: "expected Variant canonical array"); + vortex_bail!("expected Variant canonical array"); }; assert_eq!(variant.len(), 2); diff --git a/vortex-array/src/scalar_fn/fns/zip/mod.rs b/vortex-array/src/scalar_fn/fns/zip/mod.rs index 57de10db991..fa46512a4f0 100644 --- a/vortex-array/src/scalar_fn/fns/zip/mod.rs +++ b/vortex-array/src/scalar_fn/fns/zip/mod.rs @@ -117,7 +117,7 @@ impl ScalarFnVTable for Zip { fn return_dtype(&self, _options: &Self::Options, arg_dtypes: &[DType]) -> VortexResult { vortex_ensure!( matches!(arg_dtypes[2], DType::Bool(_)), - MismatchedTypes: "zip requires mask to be a boolean type, got {}", + "zip requires mask to be a boolean type, got {}", arg_dtypes[2] ); zip_return_dtype(&arg_dtypes[0], &arg_dtypes[1]) @@ -227,7 +227,7 @@ fn zip_impl( fn zip_return_dtype(if_true: &DType, if_false: &DType) -> VortexResult { zip_nullability_union(if_true, if_false).ok_or_else(|| { vortex_err!( - InvalidArgument: "zip requires if_true and if_false to have the same base type, got {} and {}", + "zip requires if_true and if_false to have the same base type, got {} and {}", if_true, if_false ) diff --git a/vortex-array/src/scalar_fn/foreign.rs b/vortex-array/src/scalar_fn/foreign.rs index e880e5370b3..667b4756c1c 100644 --- a/vortex-array/src/scalar_fn/foreign.rs +++ b/vortex-array/src/scalar_fn/foreign.rs @@ -116,7 +116,7 @@ impl ScalarFnVTable for ForeignScalarFnVTable { _args: &dyn ExecutionArgs, _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!(NotFound: "Cannot execute unknown scalar function '{}'", self.id); + vortex_bail!("Cannot execute unknown scalar function '{}'", self.id); } fn is_strict(&self, _options: &Self::Options) -> bool { diff --git a/vortex-array/src/scalar_fn/internal/row_count.rs b/vortex-array/src/scalar_fn/internal/row_count.rs index c7f17598f4b..bc217db75bf 100644 --- a/vortex-array/src/scalar_fn/internal/row_count.rs +++ b/vortex-array/src/scalar_fn/internal/row_count.rs @@ -80,7 +80,7 @@ impl ScalarFnVTable for RowCount { _args: &dyn ExecutionArgs, _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!(InvalidArgument: "RowCount must be substituted before evaluation") + vortex_bail!("RowCount must be substituted before evaluation") } fn is_strict(&self, _options: &Self::Options) -> bool { @@ -122,12 +122,12 @@ pub fn substitute_row_count(array: ArrayRef, replacement: &ArrayRef) -> VortexRe vortex_ensure_eq!( replacement.len(), array.len(), - AssertionFailed: "RowCount replacement length does not match scope length", + "RowCount replacement length does not match scope length", ); vortex_ensure_eq!( replacement.dtype(), array.dtype(), - AssertionFailed: "RowCount replacement dtype does not match scope dtype", + "RowCount replacement dtype does not match scope dtype", ); return Ok(replacement.clone()); } diff --git a/vortex-array/src/scalar_fn/typed.rs b/vortex-array/src/scalar_fn/typed.rs index ed649691605..ab6db6e098e 100644 --- a/vortex-array/src/scalar_fn/typed.rs +++ b/vortex-array/src/scalar_fn/typed.rs @@ -158,7 +158,7 @@ impl DynScalarFn for TypedScalarFnInstance { vortex_error::vortex_ensure_eq!( result.dtype(), &expected_dtype, - AssertionFailed: "Expression execution {} returned vector of invalid dtype", + "Expression execution {} returned vector of invalid dtype", self.vtable.id(), ); } diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/args.rs b/vortex-array/src/scalar_fn/unstable/row/batch/args.rs index 68debfb61f1..3f9d7ae7d3d 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/args.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/args.rs @@ -65,7 +65,7 @@ impl ExecutionArgs for BorrowedRowFnArgs<'_> { fn get(&self, index: usize) -> VortexResult { self.arrays.get(index).cloned().ok_or_else(|| { vortex_err!( - InvalidArgument: "row-function input index must be less than {}, got {index}", + "row-function input index must be less than {}, got {index}", self.arrays.len(), ) }) diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs b/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs index 59adb278ffe..6afea5798dd 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/execute/output.rs @@ -69,7 +69,7 @@ pub(crate) fn finalize_kernel_output( validate_output(id, result_dtype, expected_len, &values)?; vortex_ensure!( values.all_valid(ctx)?, - AssertionFailed: "the {id} row kernel must produce only valid rows, got at least one null row", + "the {id} row kernel must produce only valid rows, got at least one null row", ); cast_output_nullability(result_dtype, values) @@ -85,14 +85,14 @@ fn validate_output( vortex_ensure_eq!( values.len(), expected_len, - AssertionFailed: "the {id} kernel output has the wrong row count", + "the {id} kernel output has the wrong row count", ); let values_with_result_nullability = values.dtype().with_nullability(result_dtype.nullability()); vortex_ensure_eq!( values_with_result_nullability, *result_dtype, - AssertionFailed: "the {id} output dtype must match the result dtype except for outer nullability", + "the {id} output dtype must match the result dtype except for outer nullability", ); Ok(()) diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs b/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs index d3c44e800a1..1ae3d525437 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/planning.rs @@ -33,7 +33,7 @@ impl RowFnExecutionArgs { vortex_ensure_eq!( input.len(), row_count, - InvalidArgument: "the {id} input {index} has the wrong row count", + "the {id} input {index} has the wrong row count", ); } diff --git a/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs b/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs index d12a8864dc8..22309a0bd9c 100644 --- a/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs +++ b/vortex-array/src/scalar_fn/unstable/row/batch/tests.rs @@ -184,7 +184,7 @@ unsafe impl InputElement for FilterOnlyI64 { let values = ::decode(array, ctx)?; vortex_ensure!( !values.as_slice().contains(&i64::MIN), - AssertionFailed: "test input contains an invalid payload", + "test input contains an invalid payload", ); Ok(values) @@ -192,7 +192,7 @@ unsafe impl InputElement for FilterOnlyI64 { fn decode_constant(array: ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { let value = ::decode_constant(array, ctx)?; - vortex_ensure!(value != i64::MIN, AssertionFailed: "test input contains an invalid payload",); + vortex_ensure!(value != i64::MIN, "test input contains an invalid payload",); Ok(value) } @@ -347,7 +347,6 @@ impl RowFn for RepeatValue { ) -> VortexResult { vortex_ensure!( u32::try_from(*width).is_ok(), - InvalidArgument: "test.repeat_value width must fit in the fixed-size-list u32 list size, got {width}", ); @@ -384,7 +383,7 @@ impl RowFn for DeferredAdd { |&(), (lhs, rhs)| lhs.overflowing_add(rhs), |overflowed| { if overflowed { - vortex_bail!(Overflow: "deferred addition overflowed"); + vortex_bail!("deferred addition overflowed"); } Ok(()) @@ -459,7 +458,7 @@ impl RowFn for DenseRetryIncrement { |(value,)| value.overflowing_add(1), |overflowed| { if overflowed { - vortex_bail!(Overflow: "deferred increment overflowed"); + vortex_bail!("deferred increment overflowed"); } Ok(()) @@ -487,7 +486,6 @@ impl RowFn for FilteredRepeat { ) -> VortexResult { vortex_ensure!( u32::try_from(*width).is_ok(), - InvalidArgument: "test.filtered_repeat width must fit in u32, got {width}", ); @@ -563,8 +561,7 @@ fn test_fixed_size_list_sink_uses_runtime_width( let actual = execute_rows(&RepeatValue, &width, &args, &mut ctx)?; let expected = FixedSizeListArray::new( PrimitiveArray::from_iter(expected_elements).into_array(), - u32::try_from(width) - .map_err(|_| vortex_err!(InvalidArgument: "test width must fit in u32, got {width}"))?, + u32::try_from(width).map_err(|_| vortex_err!("test width must fit in u32, got {width}"))?, validity, row_count, ) @@ -637,7 +634,7 @@ impl RowFn for DeferredGreaterThan { |(lhs, rhs)| (lhs > rhs, lhs == i64::MIN), |failed| { if failed { - vortex_bail!(InvalidArgument: "deferred comparison failed"); + vortex_bail!("deferred comparison failed"); } Ok(()) @@ -729,7 +726,7 @@ fn test_kernel_output_rejects_nulls_at_function_boundary() -> VortexResult<()> { Ok(output) => match output.execute::(&mut ctx) { Err(error) => error, Ok(_) => { - vortex_bail!(InvalidArgument: "an invalid row kernel output passed boundary validation") + vortex_bail!("an invalid row kernel output passed boundary validation") } }, }; @@ -882,8 +879,7 @@ fn test_filtered_execution_preserves_runtime_sink_params( let actual = execute_rows(&FilteredRepeat, &width, &args, &mut ctx)?; let expected = FixedSizeListArray::new( PrimitiveArray::from_iter(expected_elements).into_array(), - u32::try_from(width) - .map_err(|_| vortex_err!(InvalidArgument: "test width must fit in u32, got {width}"))?, + u32::try_from(width).map_err(|_| vortex_err!("test width must fit in u32, got {width}"))?, validity, 2, ) @@ -1032,7 +1028,7 @@ fn test_deferred_bool_output_reports_valid_row_failure() -> VortexResult<()> { let error = match execute_rows(&DeferredGreaterThan::, &EmptyOptions, &args, &mut ctx) { Err(error) => error.to_string(), - Ok(_) => vortex_bail!(AssertionFailed: "a valid-row deferred failure was not reported"), + Ok(_) => vortex_bail!("a valid-row deferred failure was not reported"), }; assert!( diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs b/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs index 153d9bf999b..b73b255223c 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/owned.rs @@ -54,7 +54,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); + vortex_bail!("a decoded row input does not address exactly {row_count} rows"); }; Ok(Out::build_from( @@ -136,7 +136,7 @@ where vortex_ensure_eq!( valid.true_count(), filtered_len, - AssertionFailed: "the filtered batch must contain one row per valid row", + "the filtered batch must contain one row per valid row", ); let prepared = prepare(Args::const_values(&columns)); @@ -154,7 +154,7 @@ where if let Some(views) = Args::views_if_no_consts(&columns) { vortex_ensure!( Args::view_lens_match(&views, filtered_len), - AssertionFailed: "a decoded row input does not address exactly {filtered_len} rows", + "a decoded row input does not address exactly {filtered_len} rows", ); valid_rows.for_each_set_index(|index| { @@ -171,7 +171,7 @@ where } else { vortex_ensure!( Args::decoded_lens_match(&columns, filtered_len), - AssertionFailed: "a decoded row input does not address exactly {filtered_len} rows", + "a decoded row input does not address exactly {filtered_len} rows", ); valid_rows.for_each_set_index(|index| { @@ -215,7 +215,7 @@ where vortex_ensure_eq!( valid_rows.len(), row_count, - AssertionFailed: "the validity mask has the wrong row count", + "the validity mask has the wrong row count", ); let prepared = prepare(Args::const_values(&columns)); @@ -231,7 +231,7 @@ where if let Some(views) = Args::views_if_no_consts(&columns) { vortex_ensure!( Args::view_lens_match(&views, row_count), - AssertionFailed: "a decoded row input does not address exactly {row_count} rows", + "a decoded row input does not address exactly {row_count} rows", ); valid_rows.for_each_set_index(|index| { @@ -247,7 +247,7 @@ where } else { vortex_ensure!( Args::decoded_lens_match(&columns, row_count), - AssertionFailed: "a decoded row input does not address exactly {row_count} rows", + "a decoded row input does not address exactly {row_count} rows", ); valid_rows.for_each_set_index(|index| { @@ -290,7 +290,7 @@ where let output = &mut values.slots()[..row_count]; let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); + vortex_bail!("a decoded row input does not address exactly {row_count} rows"); }; let failure = source.map_checked_into(output, |elements| apply(&prepared, elements)); diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs b/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs index b7b20082869..5fb3d0cadc1 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/packed_bool.rs @@ -41,7 +41,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); + vortex_bail!("a decoded row input does not address exactly {row_count} rows"); }; let collect = |index| { @@ -82,7 +82,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); + vortex_bail!("a decoded row input does not address exactly {row_count} rows"); }; let mut failure = Fail::default(); @@ -136,7 +136,7 @@ where let row_count = args.row_count(); let Some(source) = decoded_source::(&columns, row_count) else { - vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows"); + vortex_bail!("a decoded row input does not address exactly {row_count} rows"); }; // NB: The collector must capture one borrow of the whole state. That shape is load-bearing for diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs b/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs index 53e83ef6c28..ebf67461e6c 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/retry.rs @@ -69,7 +69,7 @@ where // Keep this validation beside the views so LLVM sees their common length here. vortex_ensure!( Args::view_lens_match(&views, row_count), - AssertionFailed: "a decoded row input does not address exactly {row_count} rows", + "a decoded row input does not address exactly {row_count} rows", ); // SAFETY: `view_lens_match` checked that these exact retained views address `row_count` @@ -83,7 +83,7 @@ where // LTO. vortex_ensure!( Args::decoded_lens_match(&columns, row_count), - AssertionFailed: "a decoded row input does not address exactly {row_count} rows", + "a decoded row input does not address exactly {row_count} rows", ); let mut accumulated_failure = Fail::default(); diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs b/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs index f70471e47c6..46474590f78 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/sink.rs @@ -56,7 +56,7 @@ where vortex_ensure_eq!( sink_row_count, row_count, - AssertionFailed: "the output sink has the wrong row count", + "the output sink has the wrong row count", ); let views = Args::views_if_no_consts(&columns); @@ -140,7 +140,7 @@ where vortex_ensure_eq!( initialized_row_count, row_count, - AssertionFailed: "the initialized output sink has the wrong row count", + "the initialized output sink has the wrong row count", ); if let Some(views) = views { @@ -204,7 +204,7 @@ where vortex_ensure_eq!( valid.true_count(), filtered_len, - AssertionFailed: "the filtered batch must contain one row per valid row", + "the filtered batch must contain one row per valid row", ); let original_len = valid.len(); @@ -227,7 +227,7 @@ where vortex_ensure_eq!( initialized_row_count, original_len, - AssertionFailed: "the initialized output sink has the wrong row count", + "the initialized output sink has the wrong row count", ); let mut filtered_index = 0; @@ -280,7 +280,7 @@ where #[cold] #[inline(never)] fn decoded_length_error(row_count: usize) -> VortexResult<()> { - vortex_bail!(AssertionFailed: "a decoded row input does not address exactly {row_count} rows") + vortex_bail!("a decoded row input does not address exactly {row_count} rows") } /// State resolved before preparing the skip-invalid row loop. @@ -323,7 +323,7 @@ where vortex_ensure_eq!( valid_rows.len(), row_count, - AssertionFailed: "the validity mask has the wrong row count", + "the validity mask has the wrong row count", ); Ok(Some(ValidRowsSetup { @@ -401,7 +401,7 @@ mod tests { let input = PrimitiveArray::from_iter([10_i64, 20]).into_array(); let args = VecExecutionArgs::new(vec![input], 2); let Mask::Values(valid) = Mask::from_iter([false, true]) else { - vortex_bail!(InvalidArgument: "the test validity must be partially valid"); + vortex_bail!("the test validity must be partially valid"); }; let mut ctx = SESSION.create_execution_ctx(); @@ -419,7 +419,7 @@ mod tests { let error = match result { Err(error) => error, Ok(_) => { - vortex_bail!(AssertionFailed: "the sink must reject rows changed by its initializer") + vortex_bail!("the sink must reject rows changed by its initializer") } }; assert!( diff --git a/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs b/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs index f3893baa323..3fd72339f4d 100644 --- a/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs +++ b/vortex-array/src/scalar_fn/unstable/row/execute/tests.rs @@ -104,7 +104,7 @@ fn collect_owned( |_| (), |_, (value,)| apply(value), )? - .ok_or_else(|| vortex_err!(AssertionFailed: "canonical input must support selected rows")), + .ok_or_else(|| vortex_err!("canonical input must support selected rows")), Traversal::Filtered => execute_owned_infallible_filtered::<(i64,), Out, ()>( args, valid, @@ -233,7 +233,7 @@ fn packed_boolean_payload_uses_allocator( DenseAttempt::DeferredError(error) => return Err(error), } } - _ => vortex_bail!(InvalidArgument: "this test traversal requires packed Boolean output"), + _ => vortex_bail!("this test traversal requires packed Boolean output"), }; tracker.assert_owns(output.as_::().to_bit_buffer().inner().as_slice()); assert_eq!(tracker.live_allocations(), 1); @@ -268,7 +268,7 @@ where |_| (), |_, _, row| apply(row), )? - .ok_or_else(|| vortex_err!(AssertionFailed: "canonical input must support selected rows")), + .ok_or_else(|| vortex_err!("canonical input must support selected rows")), Traversal::Filtered => execute_sink_filtered::<(i64,), (), Sink, ApplyResult>( args, valid, @@ -277,7 +277,7 @@ where |_| (), |_, _, row| apply(row), ), - _ => vortex_bail!(InvalidArgument: "this test traversal requires an owned output"), + _ => vortex_bail!("this test traversal requires an owned output"), } } diff --git a/vortex-array/src/scalar_fn/unstable/row/row_fn.rs b/vortex-array/src/scalar_fn/unstable/row/row_fn.rs index 0d677e425c6..edf2f9371d0 100644 --- a/vortex-array/src/scalar_fn/unstable/row/row_fn.rs +++ b/vortex-array/src/scalar_fn/unstable/row/row_fn.rs @@ -75,7 +75,7 @@ pub trait RowFn: 'static + Sized + Clone + Send + Sync { _metadata: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!(Serde: "Expression {} is not deserializable", self.id()) + vortex_bail!("Expression {} is not deserializable", self.id()) } /// Choose element types for these input dtypes and visit the framework with them. diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs index 712efa9ff59..9b517ef89d9 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/bool.rs @@ -38,7 +38,7 @@ unsafe impl InputElement for bool { fn validate(dtype: &DType) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Bool(_)), - MismatchedTypes: "expected a Bool column, got {dtype}", + "expected a Bool column, got {dtype}", ); Ok(()) } @@ -50,13 +50,13 @@ unsafe impl InputElement for bool { fn decode_constant(array: ArrayRef, _ctx: &mut ExecutionCtx) -> VortexResult { let Some(constant) = array.as_opt::() else { vortex_bail!( - MismatchedTypes: "a Boolean batch constant must use the Constant encoding, got {}", + "a Boolean batch constant must use the Constant encoding, got {}", array.encoding_id() ); }; let scalar = constant.scalar(); let Some(ScalarValue::Bool(value)) = scalar.value() else { - vortex_bail!(InvalidArgument: "a Boolean batch constant must contain a non-null value, got {scalar}"); + vortex_bail!("a Boolean batch constant must contain a non-null value, got {scalar}"); }; Ok(*value) diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs index 4310af843aa..f20ad1410fa 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/primitive.rs @@ -38,9 +38,9 @@ unsafe impl InputElement for T { fn validate(dtype: &DType) -> VortexResult<()> { let expected = T::PTYPE; let DType::Primitive(ptype, _) = dtype else { - vortex_bail!(MismatchedTypes: "expected a {expected} column, got {dtype}"); + vortex_bail!("expected a {expected} column, got {dtype}"); }; - vortex_ensure_eq!(*ptype, expected, MismatchedTypes: "row input column has the wrong ptype"); + vortex_ensure_eq!(*ptype, expected, "row input column has the wrong ptype"); Ok(()) } @@ -51,14 +51,14 @@ unsafe impl InputElement for T { fn decode_constant(array: ArrayRef, _ctx: &mut ExecutionCtx) -> VortexResult { let Some(constant) = array.as_opt::() else { vortex_bail!( - MismatchedTypes: "a primitive batch constant must use the Constant encoding, got {}", + "a primitive batch constant must use the Constant encoding, got {}", array.encoding_id() ); }; let scalar = constant.scalar(); let Some(ScalarValue::Primitive(value)) = scalar.value() else { vortex_bail!( - InvalidArgument: "a primitive batch constant must contain a non-null {} value, got {scalar}", + "a primitive batch constant must contain a non-null {} value, got {scalar}", T::PTYPE ); }; diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs index 76080992ba7..77a0c13574d 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/element_tuple.rs @@ -247,7 +247,7 @@ impl ElementTuple for () { const DECODE_INFALLIBLE: bool = true; fn validate(dtypes: &[DType]) -> VortexResult<()> { - vortex_ensure_eq!(dtypes.len(), 0, InvalidArgument); + vortex_ensure_eq!(dtypes.len(), 0); Ok(()) } @@ -306,7 +306,7 @@ macro_rules! element_tuple { const DECODE_INFALLIBLE: bool = $($t::DECODE_INFALLIBLE &&)+ true; fn validate(dtypes: &[DType]) -> VortexResult<()> { - vortex_ensure_eq!(dtypes.len(), $arity, InvalidArgument); + vortex_ensure_eq!(dtypes.len(), $arity); $($t::validate(&dtypes[$idx])?;)+ Ok(()) diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs index 4b48da75141..16f639c4254 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/tuple/tests.rs @@ -155,7 +155,7 @@ fn test_batch_const_unwraps_filtered_masked_constant() -> VortexResult<()> { let filtered = masked.filter(Mask::from_iter([true, true, false]))?; let Some(const_array) = batch_const(&filtered) else { - vortex_bail!(AssertionFailed: "filtered masked constant must remain batch-constant"); + vortex_bail!("filtered masked constant must remain batch-constant"); }; assert!(const_array.is::()); @@ -171,7 +171,7 @@ fn test_batch_const_preserves_filtered_extension() -> VortexResult<()> { let filtered = extension.filter(Mask::from_iter([true, false, true]))?; let Some(const_array) = batch_const(&filtered) else { - vortex_bail!(AssertionFailed: "filtered extension storage must remain batch-constant"); + vortex_bail!("filtered extension storage must remain batch-constant"); }; assert_eq!(const_array.dtype(), extension.dtype()); diff --git a/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs b/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs index c506b864396..17b034dca94 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/element/utf8.rs @@ -237,13 +237,13 @@ fn decode_views(array: ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult VortexResult { let Some(constant) = array.as_opt::() else { vortex_bail!( - MismatchedTypes: "a Utf8 batch constant must use the Constant encoding, got {}", + "a Utf8 batch constant must use the Constant encoding, got {}", array.encoding_id() ); }; let scalar = constant.scalar(); let Some(ScalarValue::Utf8(value)) = scalar.value() else { - vortex_bail!(InvalidArgument: "a Utf8 batch constant must contain a non-null value, got {scalar}"); + vortex_bail!("a Utf8 batch constant must contain a non-null value, got {scalar}"); }; Ok(value.clone()) @@ -265,7 +265,7 @@ unsafe impl InputElement for Utf8Column { fn validate(dtype: &DType) -> VortexResult<()> { vortex_ensure!( matches!(dtype, DType::Utf8(_)), - MismatchedTypes: "expected a Utf8 column, got {dtype}" + "expected a Utf8 column, got {dtype}" ); Ok(()) @@ -447,7 +447,7 @@ mod tests { bytes: decoded_bytes, } = &column.0 else { - vortex_bail!(AssertionFailed: "expected offset storage"); + vortex_bail!("expected offset storage"); }; assert_eq!(decoded_bytes.as_ptr(), bytes.as_ptr()); assert_eq!( diff --git a/vortex-array/src/scalar_fn/unstable/row/types/sink/fixed_size_list.rs b/vortex-array/src/scalar_fn/unstable/row/types/sink/fixed_size_list.rs index 5a2f86580e3..e74bc7ca98f 100644 --- a/vortex-array/src/scalar_fn/unstable/row/types/sink/fixed_size_list.rs +++ b/vortex-array/src/scalar_fn/unstable/row/types/sink/fixed_size_list.rs @@ -126,7 +126,6 @@ unsafe impl OutputSink for FixedSizeListSink< let width = *params; let element_capacity = rows.checked_mul(width).ok_or_else(|| { vortex_err!( - InvalidArgument: "fixed-size-list sink capacity must fit in usize, got {rows} rows with width {width}" ) })?; diff --git a/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs b/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs index 0dac8dee5a0..f73325f285d 100644 --- a/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs +++ b/vortex-array/src/scalar_fn/unstable/row/visitor/check.rs @@ -84,7 +84,7 @@ pub(super) fn validate_owned_visit( let dtype = Out::element_dtype(); vortex_ensure!( !dtype.is_nullable(), - AssertionFailed: "row output elements must declare a non-nullable dtype, got {dtype}", + "row output elements must declare a non-nullable dtype, got {dtype}", ); Ok(dtype) @@ -103,7 +103,7 @@ where let dtype = Sink::storage_dtype(params); vortex_ensure!( !dtype.is_nullable(), - AssertionFailed: "row output sinks must declare a non-nullable dtype, got {dtype}", + "row output sinks must declare a non-nullable dtype, got {dtype}", ); Ok(dtype) diff --git a/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs b/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs index 63a7f320f6f..7e911681f7d 100644 --- a/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs +++ b/vortex-array/src/scalar_fn/unstable/row/visitor/plan.rs @@ -225,18 +225,18 @@ impl BatchPlan { pub(crate) fn ensure_reproduced_by(&self, actual: &Self) -> VortexResult<()> { vortex_ensure!( actual.policy == self.policy, - AssertionFailed: "row dispatch must select the planned nullable execution policy: planned {:?}, got {:?}", + "row dispatch must select the planned nullable execution policy: planned {:?}, got {:?}", self.policy, actual.policy, ); vortex_ensure_eq!( actual.storage_dtype, self.storage_dtype, - AssertionFailed: "row dispatch must select the planned storage dtype", + "row dispatch must select the planned storage dtype", ); vortex_ensure!( actual.output_label == self.output_label, - AssertionFailed: "row dispatch must declare the planned output dtype: planned {}, got {}", + "row dispatch must declare the planned output dtype: planned {}, got {}", self.output_dtype(), actual.output_dtype(), ); @@ -262,7 +262,7 @@ fn validate_output_label( ) -> VortexResult> { vortex_ensure!( !output_dtype.is_nullable(), - AssertionFailed: "a declared row output dtype must be non-nullable, got {output_dtype}", + "a declared row output dtype must be non-nullable, got {output_dtype}", ); if output_dtype == *storage_dtype { @@ -271,14 +271,14 @@ fn validate_output_label( let DType::Extension(output_label) = output_dtype else { vortex_bail!( - InvalidArgument: "a declared row output dtype must be an extension dtype over the storage dtype \ + "a declared row output dtype must be an extension dtype over the storage dtype \ {storage_dtype}, got {output_dtype}", ); }; vortex_ensure_eq!( *output_label.storage_dtype(), *storage_dtype, - AssertionFailed: "a declared row extension output dtype has the wrong storage dtype", + "a declared row extension output dtype has the wrong storage dtype", ); Ok(Some(output_label)) diff --git a/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs b/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs index 86dc478929b..22385bda489 100644 --- a/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs +++ b/vortex-array/src/scalar_fn/unstable/row/visitor/row_visitor.rs @@ -183,7 +183,7 @@ pub trait RowVisitor: private::Sealed + Sized { /// #[cold] /// #[inline(never)] /// fn integer_division_error() -> VortexError { - /// vortex_err!(Overflow: "integer division by zero or overflow") + /// vortex_err!("integer division by zero or overflow") /// } /// /// visitor.visit_into::<(i64, i64), UninitElementSink, _>( @@ -281,7 +281,7 @@ pub trait RowVisitor: private::Sealed + Sized { /// #[cold] /// #[inline(never)] /// fn integer_addition_error() -> VortexError { - /// vortex_err!(Overflow: "integer overflow in checked add") + /// vortex_err!("integer overflow in checked add") /// } /// /// visitor.visit_deferred::<(i64, i64), i64, bool>( @@ -350,7 +350,7 @@ pub trait RowVisitor: private::Sealed + Sized { /// #[cold] /// #[inline(never)] /// fn decimal_rescaling_overflow() -> VortexError { - /// vortex_err!(Overflow: "decimal rescaling overflowed") + /// vortex_err!("decimal rescaling overflowed") /// } /// /// visitor.visit_prepared_deferred::< diff --git a/vortex-array/src/scalar_fn/unstable/row/vtable.rs b/vortex-array/src/scalar_fn/unstable/row/vtable.rs index 4f3bd5225fe..bc4d793404f 100644 --- a/vortex-array/src/scalar_fn/unstable/row/vtable.rs +++ b/vortex-array/src/scalar_fn/unstable/row/vtable.rs @@ -156,7 +156,7 @@ fn ensure_arity(function: &F, actual: usize) -> VortexResult<()> { vortex_ensure_eq!( actual, expected, - InvalidArgument: "row function {} has the wrong arity", + "row function {} has the wrong arity", RowFn::id(function), ); @@ -394,7 +394,7 @@ mod tests { let error = match execute_rows(&function, &EmptyOptions, &args, &mut ctx) { Err(error) => error, Ok(_) => { - vortex_error::vortex_bail!(InvalidArgument: "dispatch must not change after planning") + vortex_error::vortex_bail!("dispatch must not change after planning") } }; let message = error.to_string(); @@ -423,7 +423,7 @@ mod tests { let error = match execute_rows(&function, &EmptyOptions, &args, &mut ctx) { Err(error) => error, Ok(_) => { - vortex_error::vortex_bail!(AssertionFailed: "dispatch must preserve its planned element types") + vortex_error::vortex_bail!("dispatch must preserve its planned element types") } }; diff --git a/vortex-array/src/scalar_fn/vtable.rs b/vortex-array/src/scalar_fn/vtable.rs index 66fbd7ed9a5..4cd658d4774 100644 --- a/vortex-array/src/scalar_fn/vtable.rs +++ b/vortex-array/src/scalar_fn/vtable.rs @@ -112,7 +112,7 @@ pub trait ScalarFnVTable: 'static + Sized + Clone + Send + Sync { _metadata: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!(Serde: "Expression {} is not deserializable", self.id()); + vortex_bail!("Expression {} is not deserializable", self.id()); } /// Returns the arity of this expression. @@ -576,7 +576,7 @@ impl ExecutionArgs for VecExecutionArgs { fn get(&self, index: usize) -> VortexResult { self.inputs.get(index).cloned().ok_or_else(|| { vortex_err!( - OutOfBounds: "Input index {} out of bounds (num_inputs={})", + "Input index {} out of bounds (num_inputs={})", index, self.inputs.len() ) diff --git a/vortex-array/src/serde.rs b/vortex-array/src/serde.rs index 57f257ecff8..e87d8bc7e77 100644 --- a/vortex-array/src/serde.rs +++ b/vortex-array/src/serde.rs @@ -110,9 +110,8 @@ impl ArrayRef { u16::try_from(padding).vortex_expect("padding fits into u16"), buffer.alignment().exponent(), Compression::None, - u32::try_from(buffer.len()).map_err( - |_| vortex_err!(Overflow: "All buffers must fit into u32 for serialization"), - )?, + u32::try_from(buffer.len()) + .map_err(|_| vortex_err!("All buffers must fit into u32 for serialization"))?, )); pos += buffer.len(); @@ -149,7 +148,7 @@ impl ArrayRef { // Finally, we write down the u32 length for the flatbuffer. buffers.push(ByteBuffer::from( u32::try_from(fb_length) - .map_err(|_| vortex_err!(Overflow: "Array metadata flatbuffer must fit into u32 for serialization. Array encoding tree is too large."))? + .map_err(|_| vortex_err!("Array metadata flatbuffer must fit into u32 for serialization. Array encoding tree is too large."))? .to_le_bytes() .to_vec(), )); @@ -171,7 +170,7 @@ impl ArraySerializationTree { fn try_new(session: &VortexSession, source: &ArrayRef) -> VortexResult { let Some(serialization) = session.array_serialize(source)? else { vortex_bail!( - Serde: "Array {} does not support serialization", + "Array {} does not support serialization", source.encoding_id() ); }; @@ -229,7 +228,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { let n_buffers_recursive = array.nbuffers_recursive(); if n_buffers_recursive > u16::MAX as usize { vortex_bail!( - Serde: "Array and all descendent arrays can have at most u16::MAX buffers: {}", + "Array and all descendent arrays can have at most u16::MAX buffers: {}", n_buffers_recursive ); }; @@ -251,7 +250,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { ) -> VortexResult>> { let encoding_idx = self.ctx.intern(&array.serialized_id).ok_or_else(|| { vortex_err!( - Serde: "Serialized array ID {} not permitted by ctx", + "Serialized array ID {} not permitted by ctx", array.serialized_id ) })?; @@ -260,7 +259,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { // Assign buffer indices for all child arrays. let nbuffers = u16::try_from(array.buffers.len()) - .map_err(|_| vortex_err!(Serde: "Array can have at most u16::MAX buffers"))?; + .map_err(|_| vortex_err!("Array can have at most u16::MAX buffers"))?; let mut child_buffer_idx = buffer_idx + nbuffers; let children = array @@ -273,7 +272,7 @@ impl<'a> ArrayNodeFlatBuffer<'a> { child_buffer_idx = u16::try_from(child.nbuffers_recursive()) .ok() .and_then(|nbuffers| nbuffers.checked_add(child_buffer_idx)) - .ok_or_else(|| vortex_err!(Serde: "Too many buffers (u16) for Array"))?; + .ok_or_else(|| vortex_err!("Too many buffers (u16) for Array"))?; Ok(msg) }) @@ -365,12 +364,12 @@ impl SerializedArray { let encoding_idx = self.flatbuffer().encoding(); let encoding_id = ctx .resolve(encoding_idx) - .ok_or_else(|| vortex_err!(NotFound: "Unknown encoding index: {}", encoding_idx))?; + .ok_or_else(|| vortex_err!("Unknown encoding index: {}", encoding_idx))?; let Some(plugin) = session.arrays().registry().get(&encoding_id) else { if session.allows_unknown() { return self.decode_foreign(encoding_id, dtype, len, ctx); } - vortex_bail!(NotFound: "Unknown encoding: {}", encoding_id); + vortex_bail!("Unknown encoding: {}", encoding_id); }; let children = SerializedArrayChildren { @@ -438,9 +437,9 @@ impl SerializedArray { .map(|idx| { let child = self.child(idx); let child_encoding_idx = child.flatbuffer().encoding(); - let child_encoding_id = ctx.resolve(child_encoding_idx).ok_or_else( - || vortex_err!(NotFound: "Unknown encoding index: {}", child_encoding_idx), - )?; + let child_encoding_id = ctx + .resolve(child_encoding_idx) + .ok_or_else(|| vortex_err!("Unknown encoding index: {}", child_encoding_idx))?; child .decode_foreign(child_encoding_id, dtype, len, ctx) .map(Some) @@ -485,7 +484,7 @@ impl SerializedArray { .vortex_expect("Expected array to have children"); if idx >= children.len() { vortex_panic!( - OutOfBounds: "Invalid child index {} for array with {} children", + "Invalid child index {} for array with {} children", idx, children.len() ); @@ -505,14 +504,14 @@ impl SerializedArray { let buffer_idx = self .flatbuffer() .buffers() - .ok_or_else(|| vortex_err!(Serde: "Array has no buffers"))? + .ok_or_else(|| vortex_err!("Array has no buffers"))? .get(idx); self.buffers .get(buffer_idx as usize) .cloned() .ok_or_else(|| { vortex_err!( - InvalidArgument: "Invalid buffer index {} for array with {} buffers", + "Invalid buffer index {} for array with {} buffers", buffer_idx, self.nbuffers() ) @@ -540,7 +539,7 @@ impl SerializedArray { self.buffers.get(start..start + count).map_or_else( || { vortex_bail!( - OutOfBounds: "buffer indices {}..{} out of range for {} buffers", + "buffer indices {}..{} out of range for {} buffers", start, start + count, self.buffers.len() @@ -576,7 +575,7 @@ impl SerializedArray { let fb_array = root::(fb_buffer.as_ref())?; let fb_root = fb_array .root() - .ok_or_else(|| vortex_err!(Serde: "Array must have a root node"))?; + .ok_or_else(|| vortex_err!("Array must have a root node"))?; let flatbuffer_loc = fb_root._tab.loc(); Ok((fb_buffer, flatbuffer_loc)) } @@ -679,10 +678,10 @@ impl SerializedArray { let start = offset .checked_add(fb_buf.padding() as usize) .ok_or_else(|| { - vortex_err!(Overflow: "Buffer {idx} offset overflows when adding its padding") + vortex_err!("Buffer {idx} offset overflows when adding its padding") })?; let end = start.checked_add(buffer_len).ok_or_else(|| { - vortex_err!(Overflow: "Buffer {idx} offset overflows when adding its length") + vortex_err!("Buffer {idx} offset overflows when adding its length") })?; // The alignment exponent comes from the flatbuffer and may be corrupt, so validate @@ -696,7 +695,7 @@ impl SerializedArray { // `VortexError` rather than panicking when slicing (see issue #8819). if end > segment.len() { vortex_bail!( - OutOfBounds: "Buffer {idx} at offset {start} with length {buffer_len} is out of \ + "Buffer {idx} at offset {start} with length {buffer_len} is out of \ bounds of the {}-byte segment", segment.len(), ); @@ -741,7 +740,7 @@ impl TryFrom for SerializedArray { fn try_from(value: ByteBuffer) -> Result { // The final 4 bytes contain the length of the flatbuffer. if value.len() < 4 { - vortex_bail!(Serde: "SerializedArray buffer is too short"); + vortex_bail!("SerializedArray buffer is too short"); } // We align each buffer individually, so we remove alignment requirements on the buffer. @@ -749,7 +748,7 @@ impl TryFrom for SerializedArray { let fb_length = u32::try_from_le_bytes(&value.as_slice()[value.len() - 4..])? as usize; if value.len() < 4 + fb_length { - vortex_bail!(Serde: "SerializedArray buffer is too short for flatbuffer"); + vortex_bail!("SerializedArray buffer is too short for flatbuffer"); } let fb_offset = value.len() - 4 - fb_length; @@ -824,7 +823,7 @@ mod tests { vortex_ensure_eq!( array.encoding_id(), self.id(), - Serde: "versioned primitive serializer received a different encoding", + "versioned primitive serializer received a different encoding", ); let serialized_id = if array.len() <= 4 { @@ -848,12 +847,12 @@ mod tests { vortex_ensure!( parts.serialized_id == old_primitive_id() || parts.serialized_id == new_primitive_id(), - Serde: "versioned primitive deserializer does not recognize {}", + "versioned primitive deserializer does not recognize {}", parts.serialized_id, ); vortex_ensure!( parts.serialized_id != old_primitive_id() || parts.len <= 4, - Serde: "old primitive wire ID cannot represent length {}", + "old primitive wire ID cannot represent length {}", parts.len, ); Ok(Array::::try_from_parts(ArrayVTable::deserialize( @@ -1053,7 +1052,7 @@ mod tests { let Some(err) = SerializedArray::from_flatbuffer_and_segment(array_tree, truncated).err() else { - vortex_bail!(AssertionFailed: "out-of-bounds buffer must be rejected"); + vortex_bail!("out-of-bounds buffer must be rejected"); }; assert!( err.to_string().contains("out of bounds"), @@ -1087,7 +1086,7 @@ mod tests { let segment = BufferHandle::new_host(ByteBuffer::from(vec![0u8; 4])); let Some(err) = SerializedArray::from_flatbuffer_and_segment(array_tree, segment).err() else { - vortex_bail!(InvalidArgument: "excessive buffer alignment must be rejected"); + vortex_bail!("excessive buffer alignment must be rejected"); }; assert!( err.to_string().contains("exceeds"), diff --git a/vortex-array/src/session/mod.rs b/vortex-array/src/session/mod.rs index ef18afd1ca9..e9d0d36a55f 100644 --- a/vortex-array/src/session/mod.rs +++ b/vortex-array/src/session/mod.rs @@ -133,7 +133,7 @@ pub trait ArraySessionExt: SessionExt { fn array_serialize(&self, array: &ArrayRef) -> VortexResult> { let Some(plugin) = self.arrays().serializer(&array.encoding_id()) else { vortex_bail!( - Serde: "Array {} is not registered for serialization", + "Array {} is not registered for serialization", array.encoding_id() ); }; @@ -145,7 +145,7 @@ pub trait ArraySessionExt: SessionExt { plugin .serialized_ids() .contains(&serialization.serialized_id), - Serde: "array serializer {} produced undeclared serialized ID {}", + "array serializer {} produced undeclared serialized ID {}", array.encoding_id(), serialization.serialized_id, ); diff --git a/vortex-array/src/stats/flatbuffers.rs b/vortex-array/src/stats/flatbuffers.rs index f0aa6b275d5..4d78c5bfe85 100644 --- a/vortex-array/src/stats/flatbuffers.rs +++ b/vortex-array/src/stats/flatbuffers.rs @@ -166,7 +166,7 @@ impl StatsSet { fba::Precision::Exact => Precision::Exact(value), fba::Precision::Inexact => Precision::Inexact(value), other => { - vortex_bail!(Serde: "Corrupted max_precision field: {other:?}") + vortex_bail!("Corrupted max_precision field: {other:?}") } }, ); @@ -188,7 +188,7 @@ impl StatsSet { fba::Precision::Exact => Precision::Exact(value), fba::Precision::Inexact => Precision::Inexact(value), other => { - vortex_bail!(Serde: "Corrupted min_precision field: {other:?}") + vortex_bail!("Corrupted min_precision field: {other:?}") } }, ); @@ -277,7 +277,7 @@ mod tests { &DType::Primitive(PType::F64, Nullability::Nullable), ) .as_exact() - .ok_or_else(|| vortex_err!(Serde: "sum must be exact after a round trip"))? + .ok_or_else(|| vortex_err!("sum must be exact after a round trip"))? .to_bits()) } diff --git a/vortex-array/src/stats/stats_set.rs b/vortex-array/src/stats/stats_set.rs index 937f0d4c636..eb898bd387c 100644 --- a/vortex-array/src/stats/stats_set.rs +++ b/vortex-array/src/stats/stats_set.rs @@ -136,7 +136,7 @@ impl StatsSet { pub(super) fn get_bool(&self, stat: Stat) -> Precision { self.get_ref(stat).map(|v| match v { ScalarValue::Bool(b) => *b, - _ => vortex_panic!(MismatchedTypes: "Failed to get stat {} as bool, found {}", stat, v), + _ => vortex_panic!("Failed to get stat {} as bool, found {}", stat, v), }) } @@ -372,7 +372,7 @@ impl MutTypedStatsSetRef<'_, '_> { .intersection(&m2) .vortex_expect("can always compare scalar") .ok_or_else(|| { - vortex_err!(InvalidArgument: "{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) + vortex_err!("{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) })?; if meet != m1 { self.set( @@ -410,7 +410,7 @@ impl MutTypedStatsSetRef<'_, '_> { .intersection(&m2) .vortex_expect("can always compare boolean") .ok_or_else(|| { - vortex_err!(InvalidArgument: "{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) + vortex_err!("{:?} bounds ({m1:?}, {m2:?}) do not overlap", S::STAT) })?; if intersection != m1 { self.set(S::STAT, intersection.into_value().map(ScalarValue::from)); diff --git a/vortex-array/src/test_harness/trace/mod.rs b/vortex-array/src/test_harness/trace/mod.rs index c3443b8826e..1e053cf5a7a 100644 --- a/vortex-array/src/test_harness/trace/mod.rs +++ b/vortex-array/src/test_harness/trace/mod.rs @@ -234,7 +234,7 @@ pub fn trace_op_with( ACTIVE_TRACE.with(|active| { let mut active = active.borrow_mut(); if active.is_some() { - return Err(vortex_err!(InvalidArgument: "trace_op captures cannot be nested")); + return Err(vortex_err!("trace_op captures cannot be nested")); } *active = Some(TraceRecorder::new(options)); Ok(()) diff --git a/vortex-array/src/test_harness/trace/tests.rs b/vortex-array/src/test_harness/trace/tests.rs index e8ef4b548a7..353fc669a54 100644 --- a/vortex-array/src/test_harness/trace/tests.rs +++ b/vortex-array/src/test_harness/trace/tests.rs @@ -158,14 +158,14 @@ impl VTable for StackParent { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(dtype, &test_dtype(), AssertionFailed: "unexpected stack parent dtype"); - vortex_ensure_eq!(len, 3, AssertionFailed: "unexpected stack parent length"); - vortex_ensure_eq!(slots.len(), 1, AssertionFailed: "unexpected stack parent slot count"); + vortex_ensure_eq!(dtype, &test_dtype(), "unexpected stack parent dtype"); + vortex_ensure_eq!(len, 3, "unexpected stack parent length"); + vortex_ensure_eq!(slots.len(), 1, "unexpected stack parent slot count"); let Some(child) = &slots[0] else { - vortex_bail!(InvalidArgument: "stack parent child slot is missing"); + vortex_bail!("stack parent child slot is missing"); }; - vortex_ensure_eq!(child.dtype(), dtype, AssertionFailed: "stack parent child dtype mismatch"); - vortex_ensure_eq!(child.len(), len, AssertionFailed: "stack parent child length mismatch"); + vortex_ensure_eq!(child.dtype(), dtype, "stack parent child dtype mismatch"); + vortex_ensure_eq!(child.len(), len, "stack parent child length mismatch"); Ok(()) } @@ -174,7 +174,7 @@ impl VTable for StackParent { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "StackParent buffer index {idx} out of bounds") + vortex_panic!("StackParent buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -197,7 +197,7 @@ impl VTable for StackParent { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "StackParent cannot be deserialized") + vortex_bail!("StackParent cannot be deserialized") } fn with_buffers( @@ -211,13 +211,13 @@ impl VTable for StackParent { fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { match idx { 0 => "child".to_string(), - _ => vortex_panic!(OutOfBounds: "StackParent slot index {idx} out of bounds"), + _ => vortex_panic!("StackParent slot index {idx} out of bounds"), } } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { let Some(child) = array.slots()[0].as_ref() else { - vortex_bail!(InvalidArgument: "stack parent child slot is missing"); + vortex_bail!("stack parent child slot is missing"); }; if !child.is::() { return Ok(ExecutionResult::execute_slot::(array, 0)); @@ -272,9 +272,9 @@ impl VTable for StackChild { len: usize, slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(dtype, &test_dtype(), AssertionFailed: "unexpected stack child dtype"); - vortex_ensure_eq!(len, 3, AssertionFailed: "unexpected stack child length"); - vortex_ensure!(slots.is_empty(), AssertionFailed: "stack child must not have slots"); + vortex_ensure_eq!(dtype, &test_dtype(), "unexpected stack child dtype"); + vortex_ensure_eq!(len, 3, "unexpected stack child length"); + vortex_ensure!(slots.is_empty(), "stack child must not have slots"); Ok(()) } @@ -283,7 +283,7 @@ impl VTable for StackChild { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "StackChild buffer index {idx} out of bounds") + vortex_panic!("StackChild buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -306,7 +306,7 @@ impl VTable for StackChild { _children: &dyn ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_bail!(Serde: "StackChild cannot be deserialized") + vortex_bail!("StackChild cannot be deserialized") } fn with_buffers( @@ -318,7 +318,7 @@ impl VTable for StackChild { } fn slot_name(_array: ArrayView<'_, Self>, idx: usize) -> String { - vortex_panic!(OutOfBounds: "StackChild slot index {idx} out of bounds") + vortex_panic!("StackChild slot index {idx} out of bounds") } fn execute(array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-array/src/validity.rs b/vortex-array/src/validity.rs index 5e96e53d16d..763325257c0 100644 --- a/vortex-array/src/validity.rs +++ b/vortex-array/src/validity.rs @@ -167,9 +167,11 @@ impl Validity { Ok(match self { Self::NonNullable | Self::AllValid => true, Self::AllInvalid => false, - Self::Array(a) => a.execute_scalar(index, ctx)?.as_bool().value().ok_or_else( - || vortex_err!(AssertionFailed: "validity value at index {index} is null"), - )?, + Self::Array(a) => a + .execute_scalar(index, ctx)? + .as_bool() + .value() + .ok_or_else(|| vortex_err!("validity value at index {index} is null"))?, }) } @@ -326,10 +328,10 @@ impl Validity { match (&self, patches) { (Validity::NonNullable, Validity::NonNullable) => return Ok(Validity::NonNullable), (Validity::NonNullable, _) => { - vortex_bail!(InvalidArgument: "Can't patch a non-nullable validity with nullable validity") + vortex_bail!("Can't patch a non-nullable validity with nullable validity") } (_, Validity::NonNullable) => { - vortex_bail!(InvalidArgument: "Can't patch a nullable validity with non-nullable validity") + vortex_bail!("Can't patch a nullable validity with non-nullable validity") } (Validity::AllValid, Validity::AllValid) => return Ok(Validity::AllValid), (Validity::AllInvalid, Validity::AllInvalid) => return Ok(Validity::AllInvalid), @@ -418,9 +420,7 @@ impl Validity { _ if len == 0 => Ok(Some(Validity::NonNullable)), Self::NonNullable => Ok(Some(Self::NonNullable)), Self::AllValid => Ok(Some(Self::NonNullable)), - Self::AllInvalid => { - Err(vortex_err!(InvalidArgument: "Cannot cast AllInvalid to NonNullable")) - } + Self::AllInvalid => Err(vortex_err!("Cannot cast AllInvalid to NonNullable")), Self::Array(_) => Ok(None), } } @@ -449,7 +449,7 @@ impl Validity { ) -> VortexResult { match nullability { Nullability::NonNullable => self.into_non_nullable(len, ctx).ok_or_else(|| { - vortex_err!(InvalidArgument: "Cannot cast array with invalid values to non-nullable type.") + vortex_err!("Cannot cast array with invalid values to non-nullable type.") }), Nullability::Nullable => Ok(self.into_nullable()), } diff --git a/vortex-arrow/src/convert.rs b/vortex-arrow/src/convert.rs index 00d3c935d39..0dbdc822a2d 100644 --- a/vortex-arrow/src/convert.rs +++ b/vortex-arrow/src/convert.rs @@ -252,9 +252,9 @@ where DataType::Date32 => TemporalArray::new_date(arr, TimeUnit::Days).into(), DataType::Date64 => TemporalArray::new_date(arr, TimeUnit::Milliseconds).into(), DataType::Duration(_) | DataType::Interval(_) => { - vortex_bail!(InvalidArgument: "Arrow {} arrays are not supported", value.data_type()) + vortex_bail!("Arrow {} arrays are not supported", value.data_type()) } - _ => vortex_panic!(MismatchedTypes: "Invalid temporal type: {}", value.data_type()), + _ => vortex_panic!("Invalid temporal type: {}", value.data_type()), }) } @@ -286,7 +286,7 @@ where let dtype = match T::DATA_TYPE { DataType::Binary | DataType::LargeBinary => DType::Binary(nullable.into()), DataType::Utf8 | DataType::LargeUtf8 => DType::Utf8(nullable.into()), - dt => vortex_panic!(MismatchedTypes: "Invalid data type for ByteArray: {dt}"), + dt => vortex_panic!("Invalid data type for ByteArray: {dt}"), }; let (offsets, referenced) = trim_offsets(value.offsets()); let bytes = value @@ -312,7 +312,7 @@ pub fn from_arrow_byte_view( let dtype = match T::DATA_TYPE { DataType::BinaryView => DType::Binary(nullable.into()), DataType::Utf8View => DType::Utf8(nullable.into()), - dt => vortex_panic!(MismatchedTypes: "Invalid data type for ByteViewArray: {dt}"), + dt => vortex_panic!("Invalid data type for ByteViewArray: {dt}"), }; let views_buffer = Buffer::from_byte_buffer( @@ -379,7 +379,7 @@ pub(crate) fn remove_nulls(data: arrow_data::ArrayData) -> VortexResult VortexResult( let elements_are_nullable = match value.data_type() { DataType::List(field) => field.is_nullable(), DataType::LargeList(field) => field.is_nullable(), - dt => vortex_panic!(MismatchedTypes: "Invalid data type for ListArray: {dt}"), + dt => vortex_panic!("Invalid data type for ListArray: {dt}"), }; let (offsets, referenced) = trim_offsets(value.offsets()); @@ -457,7 +457,7 @@ pub fn from_arrow_list_view( let elements_are_nullable = match array.data_type() { DataType::ListView(field) => field.is_nullable(), DataType::LargeListView(field) => field.is_nullable(), - dt => vortex_panic!(MismatchedTypes: "Invalid data type for ListViewArray: {dt}"), + dt => vortex_panic!("Invalid data type for ListViewArray: {dt}"), }; let elements = from_arrow_dyn(array.values().as_ref(), elements_are_nullable)?; @@ -478,7 +478,7 @@ pub fn from_arrow_fixed_size_list( nullable: bool, ) -> VortexResult { let DataType::FixedSizeList(field, list_size) = array.data_type() else { - vortex_panic!(MismatchedTypes: "Invalid data type for ListArray: {}", array.data_type()); + vortex_panic!("Invalid data type for ListArray: {}", array.data_type()); }; Ok(FixedSizeListArray::try_new( @@ -499,26 +499,26 @@ pub(crate) fn map_from_arrow_parts( ) -> VortexResult { let DType::Struct(struct_dtype, Nullability::NonNullable) = entries.dtype() else { vortex_bail!( - MismatchedTypes: "Arrow map entries must import as non-nullable struct, got {}", + "Arrow map entries must import as non-nullable struct, got {}", entries.dtype() ); }; vortex_ensure_eq!( struct_dtype.nfields(), 2, - InvalidArgument: "Arrow map entries struct must contain exactly two fields" + "Arrow map entries struct must contain exactly two fields" ); let key_dtype = struct_dtype .field_by_index(0) - .ok_or_else(|| vortex_err!(NotFound: "Arrow map entries struct missing key field"))?; + .ok_or_else(|| vortex_err!("Arrow map entries struct missing key field"))?; vortex_ensure!( !key_dtype.is_nullable(), - InvalidArgument: "Arrow map key field must be non-nullable" + "Arrow map key field must be non-nullable" ); let value_dtype = struct_dtype .field_by_index(1) - .ok_or_else(|| vortex_err!(NotFound: "Arrow map entries struct missing value field"))?; + .ok_or_else(|| vortex_err!("Arrow map entries struct missing value field"))?; let map_dtype = MapDType::try_new(key_dtype, value_dtype, keys_sorted)?; let entries_struct = entries.as_::(); let entries = StructArray::try_new( @@ -551,7 +551,7 @@ pub(crate) fn map_from_arrow_parts( /// Conversion of an Arrow map array into a Vortex `Map` array. pub fn from_arrow_map(array: &ArrowMapArray, nullable: bool) -> VortexResult { let DataType::Map(_, keys_sorted) = array.data_type() else { - vortex_panic!(MismatchedTypes: "Invalid data type for MapArray: {}", array.data_type()); + vortex_panic!("Invalid data type for MapArray: {}", array.data_type()); }; let entries = from_arrow_struct(array.entries(), false)?; map_from_arrow_parts( @@ -567,7 +567,7 @@ pub fn from_arrow_map(array: &ArrowMapArray, nullable: bool) -> VortexResult VortexResult { vortex_ensure!( nullable, - InvalidArgument: "Cannot convert an Arrow NullArray into a non-nullable Vortex array" + "Cannot convert an Arrow NullArray into a non-nullable Vortex array" ); Ok(NullArray::new(value.len()).into_array()) } @@ -606,7 +606,7 @@ pub fn nulls(nulls: Option<&NullBuffer>, nullable: bool) -> VortexResult VortexResult vortex_bail!(InvalidArgument: "Unsupported dictionary key type: {key_dt}"), + key_dt => vortex_bail!("Unsupported dictionary key type: {key_dt}"), }, dt => { - vortex_bail!(NotImplemented: "Array encoding not implemented for Arrow data type {dt}") + vortex_bail!("Array encoding not implemented for Arrow data type {dt}") } } } diff --git a/vortex-arrow/src/datum.rs b/vortex-arrow/src/datum.rs index 2587ffdcfff..d501ff1d920 100644 --- a/vortex-arrow/src/datum.rs +++ b/vortex-arrow/src/datum.rs @@ -120,7 +120,7 @@ pub fn from_arrow_columnar( if array.len() != 1 { vortex_panic!( - AssertionFailed: "Array length mismatch, expected {} got {} for encoding {}", + "Array length mismatch, expected {} got {} for encoding {}", len, array.len(), array.encoding_id() diff --git a/vortex-arrow/src/dtype.rs b/vortex-arrow/src/dtype.rs index f1b87bfcd26..0e35c05dc69 100644 --- a/vortex-arrow/src/dtype.rs +++ b/vortex-arrow/src/dtype.rs @@ -62,7 +62,7 @@ pub(crate) fn to_arrow_time_unit(value: TimeUnit) -> VortexResult TimeUnit::Milliseconds => ArrowTimeUnit::Millisecond, TimeUnit::Microseconds => ArrowTimeUnit::Microsecond, TimeUnit::Nanoseconds => ArrowTimeUnit::Nanosecond, - _ => vortex_bail!(MismatchedTypes: "Cannot convert {value} to Arrow TimeUnit"), + _ => vortex_bail!("Cannot convert {value} to Arrow TimeUnit"), }) } @@ -81,7 +81,7 @@ pub(crate) fn ptype_from_arrow(value: &DataType) -> VortexResult { DataType::Float32 => Ok(PType::F32), DataType::Float64 => Ok(PType::F64), _ => Err(vortex_err!( - InvalidArgument: "Arrow datatype {:?} cannot be converted to ptype", + "Arrow datatype {:?} cannot be converted to ptype", value )), } @@ -138,24 +138,24 @@ pub(crate) fn from_arrow_data_type( DataType::Map(entries, keys_sorted) => { vortex_ensure!( !entries.is_nullable(), - InvalidArgument: "Arrow map entries field must be non-nullable" + "Arrow map entries field must be non-nullable" ); let DataType::Struct(fields) = entries.data_type() else { vortex_bail!( - MismatchedTypes: "Arrow map entries field must have Struct type, got {:?}", + "Arrow map entries field must have Struct type, got {:?}", entries.data_type() ); }; vortex_ensure_eq!( fields.len(), 2, - InvalidArgument: "Arrow map entries struct must contain exactly two fields" + "Arrow map entries struct must contain exactly two fields" ); let key = &fields[0]; let value = &fields[1]; vortex_ensure!( !key.is_nullable(), - InvalidArgument: "Arrow map key field must be non-nullable" + "Arrow map key field must be non-nullable" ); DType::map( from_arrow_field_naive(key.as_ref())?, @@ -170,7 +170,7 @@ pub(crate) fn from_arrow_data_type( DataType::RunEndEncoded(_, value_type) => { from_arrow_data_type(value_type.data_type(), nullability)? } - _ => vortex_bail!(InvalidArgument: "Arrow data type not supported: {data_type:?}"), + _ => vortex_bail!("Arrow data type not supported: {data_type:?}"), }) } @@ -274,9 +274,9 @@ pub(crate) fn to_data_type_naive(dtype: &DType) -> VortexResult { DataType::Struct(Fields::from(fields)) } - DType::Union(..) => vortex_bail!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_bail!("TODO(connor)[Union]: unimplemented"), DType::Variant(_) => vortex_bail!( - InvalidArgument: "DType::Variant requires Arrow Field metadata; use to_arrow_schema or a Field helper" + "DType::Variant requires Arrow Field metadata; use to_arrow_schema or a Field helper" ), DType::Extension(ext_dtype) => { // NOTE: Temporal are the only builtin and default-loaded extension types, and they map @@ -292,7 +292,7 @@ pub(crate) fn to_data_type_naive(dtype: &DType) -> VortexResult { TimeUnit::Days => DataType::Date32, TimeUnit::Milliseconds => DataType::Date64, TimeUnit::Nanoseconds | TimeUnit::Microseconds | TimeUnit::Seconds => { - vortex_panic!(InvalidArgument: "Invalid TimeUnit {} for {}", unit, ext_dtype.id()) + vortex_panic!("Invalid TimeUnit {} for {}", unit, ext_dtype.id()) } }, TemporalMetadata::Time(unit) => match unit { @@ -301,13 +301,13 @@ pub(crate) fn to_data_type_naive(dtype: &DType) -> VortexResult { TimeUnit::Microseconds => DataType::Time64(ArrowTimeUnit::Microsecond), TimeUnit::Nanoseconds => DataType::Time64(ArrowTimeUnit::Nanosecond), TimeUnit::Days => { - vortex_panic!(InvalidArgument: "Invalid TimeUnit {} for {}", unit, ext_dtype.id()) + vortex_panic!("Invalid TimeUnit {} for {}", unit, ext_dtype.id()) } }, }); }; - vortex_bail!(InvalidArgument: "Unsupported extension type \"{}\"", ext_dtype.id()) + vortex_bail!("Unsupported extension type \"{}\"", ext_dtype.id()) } }) } diff --git a/vortex-arrow/src/executor/bool.rs b/vortex-arrow/src/executor/bool.rs index a0587fb37ee..f6815884b33 100644 --- a/vortex-arrow/src/executor/bool.rs +++ b/vortex-arrow/src/executor/bool.rs @@ -37,7 +37,7 @@ pub(super) fn to_arrow_bool( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::Bool(_)), - MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow Boolean array", + "Cannot convert Vortex array with dtype {} to an Arrow Boolean array", array.dtype() ); let bool_array = array.execute::(ctx)?; diff --git a/vortex-arrow/src/executor/byte.rs b/vortex-arrow/src/executor/byte.rs index 8e1cda30d09..c593bd24074 100644 --- a/vortex-arrow/src/executor/byte.rs +++ b/vortex-arrow/src/executor/byte.rs @@ -60,7 +60,7 @@ where { if !matches!(array.dtype(), DType::Utf8(_) | DType::Binary(_)) { vortex_bail!( - MismatchedTypes: "Cannot convert Vortex array with dtype {} to Arrow byte array type {}", + "Cannot convert Vortex array with dtype {} to Arrow byte array type {}", array.dtype(), T::DATA_TYPE ); @@ -142,7 +142,7 @@ fn validate_live_values_utf8( let value_at = |index: usize, start: usize, end: usize| -> VortexResult<&[u8]> { values .get(start..end) - .ok_or_else(|| vortex_err!(OutOfBounds: "Offsets {start}..{end} at index {index} are out of bounds")) + .ok_or_else(|| vortex_err!("Offsets {start}..{end} at index {index} are out of bounds")) }; let Some(nulls) = nulls.filter(|nulls| nulls.null_count() > 0) else { @@ -155,7 +155,7 @@ fn validate_live_values_utf8( let start = first.as_usize(); let bytes = value_at(0, start, last.as_usize())?; let validated = utf8_from_bytes(bytes) - .map_err(|err| vortex_err!(InvalidArgument: "Encountered non UTF-8 data: {err}"))?; + .map_err(|err| vortex_err!("Encountered non UTF-8 data: {err}"))?; for (index, offset) in offsets.iter().enumerate() { let boundary = offset .as_usize() @@ -163,7 +163,7 @@ fn validate_live_values_utf8( .filter(|boundary| validated.is_char_boundary(*boundary)); vortex_ensure!( boundary.is_some(), - InvalidArgument: "Offset {} at index {index} does not fall on a UTF-8 character boundary", + "Offset {} at index {index} does not fall on a UTF-8 character boundary", offset.as_usize() ); } @@ -176,7 +176,7 @@ fn validate_live_values_utf8( } let bytes = value_at(index, window[0].as_usize(), window[1].as_usize())?; utf8_from_bytes(bytes) - .map_err(|err| vortex_err!(InvalidArgument: "Encountered non UTF-8 data at index {index}: {err}"))?; + .map_err(|err| vortex_err!("Encountered non UTF-8 data at index {index}: {err}"))?; } Ok(()) } diff --git a/vortex-arrow/src/executor/decimal.rs b/vortex-arrow/src/executor/decimal.rs index 6896b81f814..d86406277bd 100644 --- a/vortex-arrow/src/executor/decimal.rs +++ b/vortex-arrow/src/executor/decimal.rs @@ -32,7 +32,7 @@ pub(super) fn to_arrow_decimal( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::Decimal(..)), - MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow {} array", + "Cannot convert Vortex array with dtype {} to an Arrow {} array", array.dtype(), data_type ); @@ -68,27 +68,24 @@ fn to_arrow_decimal32(array: DecimalArray, ctx: &mut ExecutionCtx) -> VortexResu .buffer::() .into_iter() .map(|x| { - x.to_i32().ok_or_else( - || vortex_err!(InvalidArgument: "i64 to i32 narrowing cannot be done safely"), - ) + x.to_i32() + .ok_or_else(|| vortex_err!("i64 to i32 narrowing cannot be done safely")) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, DecimalType::I128 => array .buffer::() .into_iter() .map(|x| { - x.to_i32().ok_or_else( - || vortex_err!(InvalidArgument: "i128 to i32 narrowing cannot be done safely"), - ) + x.to_i32() + .ok_or_else(|| vortex_err!("i128 to i32 narrowing cannot be done safely")) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, DecimalType::I256 => array .buffer::() .into_iter() .map(|x| { - x.to_i32().ok_or_else( - || vortex_err!(InvalidArgument: "i256 to i32 narrowing cannot be done safely"), - ) + x.to_i32() + .ok_or_else(|| vortex_err!("i256 to i32 narrowing cannot be done safely")) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, }; @@ -123,18 +120,16 @@ fn to_arrow_decimal64(array: DecimalArray, ctx: &mut ExecutionCtx) -> VortexResu .buffer::() .into_iter() .map(|x| { - x.to_i64().ok_or_else( - || vortex_err!(InvalidArgument: "i128 to i64 narrowing cannot be done safely"), - ) + x.to_i64() + .ok_or_else(|| vortex_err!("i128 to i64 narrowing cannot be done safely")) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, DecimalType::I256 => array .buffer::() .into_iter() .map(|x| { - x.to_i64().ok_or_else( - || vortex_err!(InvalidArgument: "i256 to i64 narrowing cannot be done safely"), - ) + x.to_i64() + .ok_or_else(|| vortex_err!("i256 to i64 narrowing cannot be done safely")) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, }; @@ -172,9 +167,8 @@ fn to_arrow_decimal128(array: DecimalArray, ctx: &mut ExecutionCtx) -> VortexRes .buffer::() .into_iter() .map(|x| { - x.to_i128().ok_or_else( - || vortex_err!(InvalidArgument: "i256 to i128 narrowing cannot be done safely"), - ) + x.to_i128() + .ok_or_else(|| vortex_err!("i256 to i128 narrowing cannot be done safely")) }) .process_results(|iter| Buffer::from_trusted_len_iter(iter))?, }; diff --git a/vortex-arrow/src/executor/dictionary.rs b/vortex-arrow/src/executor/dictionary.rs index fd2528d91aa..343c08357af 100644 --- a/vortex-arrow/src/executor/dictionary.rs +++ b/vortex-arrow/src/executor/dictionary.rs @@ -115,7 +115,7 @@ fn zeroed_codes_array(codes_type: &DataType, len: usize) -> VortexResult Arc::new(PrimitiveArray::::from_value(0, len)), DataType::UInt32 => Arc::new(PrimitiveArray::::from_value(0, len)), DataType::UInt64 => Arc::new(PrimitiveArray::::from_value(0, len)), - _ => vortex_bail!(InvalidArgument: "Unsupported dictionary codes type: {:?}", codes_type), + _ => vortex_bail!("Unsupported dictionary codes type: {:?}", codes_type), }) } @@ -150,7 +150,7 @@ fn make_dict_array( DataType::UInt64 => Arc::new(unsafe { DictionaryArray::new_unchecked(codes.as_primitive::().clone(), values) }), - _ => vortex_bail!(InvalidArgument: "Unsupported dictionary codes type: {:?}", codes_type), + _ => vortex_bail!("Unsupported dictionary codes type: {:?}", codes_type), }) } diff --git a/vortex-arrow/src/executor/fixed_size_list.rs b/vortex-arrow/src/executor/fixed_size_list.rs index 222b7279d2d..b830af710dd 100644 --- a/vortex-arrow/src/executor/fixed_size_list.rs +++ b/vortex-arrow/src/executor/fixed_size_list.rs @@ -26,7 +26,7 @@ pub(super) fn to_arrow_fixed_list( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::FixedSizeList(..)), - MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow FixedSizeList array", + "Cannot convert Vortex array with dtype {} to an Arrow FixedSizeList array", array.dtype() ); @@ -55,7 +55,7 @@ fn list_to_list( ) -> VortexResult { vortex_ensure!( Ok(list_size) == i32::try_from(array.list_size()), - InvalidArgument: "Cannot convert FixedSizeList with list size {} to Arrow array with list size {}", + "Cannot convert FixedSizeList with list size {} to Arrow array with list size {}", array.list_size(), list_size ); @@ -64,7 +64,7 @@ fn list_to_list( exporter.execute_arrow(array.elements().clone(), Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - InvalidArgument: "Cannot convert FixedSizeListArray to non-nullable Arrow array when elements are nullable" + "Cannot convert FixedSizeListArray to non-nullable Arrow array when elements are nullable" ); let null_buffer = to_arrow_null_buffer(array.validity()?, array.len(), ctx)?; diff --git a/vortex-arrow/src/executor/list.rs b/vortex-arrow/src/executor/list.rs index 115076927c4..8246f36155f 100644 --- a/vortex-arrow/src/executor/list.rs +++ b/vortex-arrow/src/executor/list.rs @@ -55,7 +55,7 @@ pub(super) fn to_arrow_list( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::List(..)), - MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow list array", + "Cannot convert Vortex array with dtype {} to an Arrow list array", array.dtype() ); @@ -123,7 +123,7 @@ fn list_to_list( exporter.execute_arrow(array.elements().clone(), Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - InvalidArgument: "Cannot convert to non-nullable Arrow array with null elements" + "Cannot convert to non-nullable Arrow array with null elements" ); let null_buffer = to_arrow_null_buffer(array.validity()?, array.len(), ctx)?; @@ -199,7 +199,7 @@ fn list_view_zctl( let elements = exporter.execute_arrow(elements, Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - InvalidArgument: "Cannot convert to non-nullable Arrow array with null elements" + "Cannot convert to non-nullable Arrow array with null elements" ); let null_buffer = to_arrow_null_buffer(validity, sizes.len(), ctx)?; diff --git a/vortex-arrow/src/executor/list_view.rs b/vortex-arrow/src/executor/list_view.rs index ea339d2cb63..2bae37f5835 100644 --- a/vortex-arrow/src/executor/list_view.rs +++ b/vortex-arrow/src/executor/list_view.rs @@ -35,7 +35,7 @@ pub(super) fn to_arrow_list_view( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::List(..)), - MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow list-view array", + "Cannot convert Vortex array with dtype {} to an Arrow list-view array", array.dtype() ); @@ -89,14 +89,14 @@ fn list_view_to_list_view( let elements = exporter.execute_arrow(elements, Some(elements_field.as_ref()), ctx)?; vortex_ensure!( elements_field.is_nullable() || elements.null_count() == 0, - InvalidArgument: "Elements field is non-nullable but elements array contains nulls" + "Elements field is non-nullable but elements array contains nulls" ); // The unchecked construction below needs the views in bounds of the *exported* elements, so // confirm the export preserved the length the Vortex invariant was checked against. vortex_ensure_eq!( elements.len(), n_elements, - AssertionFailed: "Arrow export changed the elements length" + "Arrow export changed the elements length" ); let offsets = offsets diff --git a/vortex-arrow/src/executor/map.rs b/vortex-arrow/src/executor/map.rs index 820a94cace1..fb6c9239b55 100644 --- a/vortex-arrow/src/executor/map.rs +++ b/vortex-arrow/src/executor/map.rs @@ -41,7 +41,7 @@ pub(super) fn to_arrow_map( vortex_ensure!( !keys_sorted || array.keys_sorted(), - InvalidArgument: "Cannot convert unsorted Vortex map to Arrow MapArray with keys_sorted=true" + "Cannot convert unsorted Vortex map to Arrow MapArray with keys_sorted=true" ); let entries = array.entries().clone(); @@ -50,7 +50,7 @@ pub(super) fn to_arrow_map( vortex_ensure_eq!( entries_list.data_type(), &entries_list_type, - AssertionFailed: "Arrow Map entries converted to an unexpected type" + "Arrow Map entries converted to an unexpected type" ); let entries_list = entries_list.as_list::(); diff --git a/vortex-arrow/src/executor/mod.rs b/vortex-arrow/src/executor/mod.rs index 308c4aca357..bc2256584fc 100644 --- a/vortex-arrow/src/executor/mod.rs +++ b/vortex-arrow/src/executor/mod.rs @@ -207,14 +207,14 @@ pub(crate) fn execute_arrow_naive( | DataType::Duration(_) | DataType::Interval(_) | DataType::Union(..) => { - vortex_bail!(InvalidArgument: "Conversion to Arrow type {resolved_type} is not supported"); + vortex_bail!("Conversion to Arrow type {resolved_type} is not supported"); } }?; vortex_ensure_eq!( arrow.len(), len, - AssertionFailed: "Arrow array length does not match Vortex array length after conversion to {:?}", + "Arrow array length does not match Vortex array length after conversion to {:?}", arrow ); diff --git a/vortex-arrow/src/executor/null.rs b/vortex-arrow/src/executor/null.rs index b04a6955dbf..7e5dac3e9c4 100644 --- a/vortex-arrow/src/executor/null.rs +++ b/vortex-arrow/src/executor/null.rs @@ -23,7 +23,7 @@ pub(super) fn to_arrow_null( ) -> VortexResult { vortex_ensure!( matches!(array.dtype(), DType::Null), - MismatchedTypes: "Cannot convert Vortex array with dtype {} to an Arrow Null array", + "Cannot convert Vortex array with dtype {} to an Arrow Null array", array.dtype() ); let null_array = array.execute::(ctx)?; diff --git a/vortex-arrow/src/executor/run_end.rs b/vortex-arrow/src/executor/run_end.rs index d4690802b38..ef8a124eef7 100644 --- a/vortex-arrow/src/executor/run_end.rs +++ b/vortex-arrow/src/executor/run_end.rs @@ -97,7 +97,7 @@ fn run_end_to_arrow( DataType::Int16 => build_run_array::(&arrow_ends, &arrow_values, offset, length), DataType::Int32 => build_run_array::(&arrow_ends, &arrow_values, offset, length), DataType::Int64 => build_run_array::(&arrow_ends, &arrow_values, offset, length), - _ => vortex_bail!(InvalidArgument: "Unsupported run-end index type: {:?}", ends_type), + _ => vortex_bail!("Unsupported run-end index type: {:?}", ends_type), } } @@ -111,9 +111,9 @@ where R::Native: std::ops::Sub + Ord, { let offset_native = R::Native::from_usize(offset) - .ok_or_else(|| vortex_err!(Overflow: "Offset {offset} exceeds run-end index capacity"))?; + .ok_or_else(|| vortex_err!("Offset {offset} exceeds run-end index capacity"))?; let length_native = R::Native::from_usize(length) - .ok_or_else(|| vortex_err!(Overflow: "Length {length} exceeds run-end index capacity"))?; + .ok_or_else(|| vortex_err!("Length {length} exceeds run-end index capacity"))?; let ends_prim = ends.as_primitive::(); if offset == 0 && ends_prim.values().last() == Some(&length_native) { @@ -171,7 +171,7 @@ fn constant_to_run_end( DataType::Int16 => build_constant_run_array::(len, &values), DataType::Int32 => build_constant_run_array::(len, &values), DataType::Int64 => build_constant_run_array::(len, &values), - _ => vortex_bail!(InvalidArgument: "Unsupported run-end index type: {:?}", ends_type), + _ => vortex_bail!("Unsupported run-end index type: {:?}", ends_type), } } @@ -179,9 +179,8 @@ fn build_constant_run_array( len: usize, values: &ArrowArrayRef, ) -> VortexResult { - let end = R::Native::from_usize(len).ok_or_else( - || vortex_err!(Overflow: "Array length {len} exceeds run-end index capacity"), - )?; + let end = R::Native::from_usize(len) + .ok_or_else(|| vortex_err!("Array length {len} exceeds run-end index capacity"))?; let run_ends = arrow_array::PrimitiveArray::::from_value(end, 1); Ok(Arc::new(RunArray::::try_new(&run_ends, values)?) as ArrowArrayRef) } @@ -314,7 +313,7 @@ mod tests { let ree_arrow = result .as_any() .downcast_ref::>() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int32 run-end array"))?; + .ok_or_else(|| vortex_err!("expected Int32 run-end array"))?; assert_eq!(ree_arrow.run_ends().values(), &[2, 4]); // The RunEnd fast path exports the values buffer zero-copy; the flat-then-recode @@ -323,7 +322,7 @@ mod tests { .values() .as_any() .downcast_ref::() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int64 values"))?; + .ok_or_else(|| vortex_err!("expected Int64 values"))?; assert_eq!(arrow_values.values().as_ptr(), values_ptr); let expected = RunArray::::try_new( &Int32Array::from(vec![2, 4]), @@ -370,13 +369,13 @@ mod tests { let ree = result .as_any() .downcast_ref::>() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int32 run-end array"))?; + .ok_or_else(|| vortex_err!("expected Int32 run-end array"))?; assert_eq!(ree.run_ends().values(), expected_ends); let values = ree .values() .as_any() .downcast_ref::() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Int64 values"))?; + .ok_or_else(|| vortex_err!("expected Int64 values"))?; assert_eq!(values.values(), expected_values); Ok(()) } diff --git a/vortex-arrow/src/executor/struct_.rs b/vortex-arrow/src/executor/struct_.rs index 2e3d80c534c..76946d8f01a 100644 --- a/vortex-arrow/src/executor/struct_.rs +++ b/vortex-arrow/src/executor/struct_.rs @@ -149,7 +149,7 @@ fn create_from_fields( vortex_ensure_eq!( vortex_fields.len(), fields.len(), - InvalidArgument: "StructArray field count must match the target Arrow type" + "StructArray field count must match the target Arrow type" ); let mut arrow_arrays = Vec::with_capacity(vortex_fields.len()); @@ -160,7 +160,7 @@ fn create_from_fields( exporter.execute_arrow(vx_field.clone(), Some(field.as_ref()), ctx)?; vortex_ensure!( field.is_nullable() || arrow_field.null_count() == 0, - InvalidArgument: "Cannot convert field '{}' to non-nullable Arrow field because it contains nulls", + "Cannot convert field '{}' to non-nullable Arrow field because it contains nulls", field.name() ); arrow_arrays.push(arrow_field); diff --git a/vortex-arrow/src/executor/temporal.rs b/vortex-arrow/src/executor/temporal.rs index 8a21939a07a..220afdb9bbc 100644 --- a/vortex-arrow/src/executor/temporal.rs +++ b/vortex-arrow/src/executor/temporal.rs @@ -147,7 +147,7 @@ fn validate_temporal_extension(array: &ArrayRef, target: &DataType) -> VortexRes }; let Some(temporal) = ext.metadata_opt::() else { vortex_bail!( - MismatchedTypes: "Cannot convert extension {} to Arrow type {target}", + "Cannot convert extension {} to Arrow type {target}", ext.id() ); }; @@ -171,18 +171,18 @@ fn validate_temporal_extension(array: &ArrayRef, target: &DataType) -> VortexRes let src_arrow_unit = crate::dtype::to_arrow_time_unit(*unit)?; if src_arrow_unit != *arrow_unit { vortex_bail!( - MismatchedTypes: "Cannot convert Timestamp({unit}) to Arrow Timestamp({arrow_unit:?}): unit mismatch" + "Cannot convert Timestamp({unit}) to Arrow Timestamp({arrow_unit:?}): unit mismatch" ); } if src_tz != tgt_tz { vortex_bail!( - MismatchedTypes: "Cannot convert Timestamp(tz={src_tz:?}) to Arrow Timestamp(tz={tgt_tz:?}): timezone mismatch" + "Cannot convert Timestamp(tz={src_tz:?}) to Arrow Timestamp(tz={tgt_tz:?}): timezone mismatch" ); } Ok(()) } (temporal, target) => vortex_bail!( - MismatchedTypes: "Cannot convert {} to Arrow type {target}", + "Cannot convert {} to Arrow type {target}", match temporal { TemporalMetadata::Date(unit) => format!("Date({unit})"), TemporalMetadata::Time(unit) => format!("Time({unit})"), diff --git a/vortex-arrow/src/run_end_import.rs b/vortex-arrow/src/run_end_import.rs index bc1966a38f9..abae401f506 100644 --- a/vortex-arrow/src/run_end_import.rs +++ b/vortex-arrow/src/run_end_import.rs @@ -36,7 +36,7 @@ where vortex_ensure_eq!( ends.len(), values.len(), - InvalidArgument: "Arrow run-end array must have one value per run end" + "Arrow run-end array must have one value per run end" ); // Arrow slices a RunArray by adjusting the logical offset/length while keeping the full diff --git a/vortex-arrow/src/scalar.rs b/vortex-arrow/src/scalar.rs index efd1c0bad4d..aa3cb6356bd 100644 --- a/vortex-arrow/src/scalar.rs +++ b/vortex-arrow/src/scalar.rs @@ -76,20 +76,20 @@ impl ToArrowDatum for Scalar { DType::Utf8(_) => utf8_to_arrow(value.as_utf8()), DType::Binary(_) => binary_to_arrow(value.as_binary()), DType::List(..) => { - vortex_bail!(InvalidArgument: "list scalar conversion is not supported") + vortex_bail!("list scalar conversion is not supported") } DType::FixedSizeList(..) => { - vortex_bail!(InvalidArgument: "fixed-size list scalar conversion is not supported") + vortex_bail!("fixed-size list scalar conversion is not supported") } DType::Map(..) => map_to_arrow(value.as_map()), DType::Struct(..) => { - vortex_bail!(InvalidArgument: "struct scalar conversion is not supported") + vortex_bail!("struct scalar conversion is not supported") } DType::Union(..) => { - vortex_bail!(InvalidArgument: "union scalar conversion is not supported") + vortex_bail!("union scalar conversion is not supported") } DType::Variant(_) => { - vortex_bail!(InvalidArgument: "Variant scalar conversion is not supported") + vortex_bail!("Variant scalar conversion is not supported") } DType::Extension(..) => extension_to_arrow(value.as_extension()), } @@ -121,7 +121,7 @@ fn primitive_to_arrow(scalar: PrimitiveScalar<'_>) -> Result, Vor /// Convert a [`DecimalScalar`] to an Arrow [`Datum`]. fn decimal_to_arrow(scalar: DecimalScalar<'_>) -> Result, VortexError> { let DType::Decimal(decimal_dtype, _) = scalar.dtype() else { - vortex_bail!(MismatchedTypes: "Expected decimal scalar, got {}", scalar.dtype()); + vortex_bail!("Expected decimal scalar, got {}", scalar.dtype()); }; let precision = decimal_dtype.precision(); let scale = decimal_dtype.scale(); @@ -132,7 +132,7 @@ fn decimal_to_arrow(scalar: DecimalScalar<'_>) -> Result, VortexE if precision <= 38 { let value = value.maybe_i128().ok_or_else(|| { vortex_err!( - Overflow: "Decimal value {value} cannot fit in Arrow Decimal128 for precision {precision}" + "Decimal value {value} cannot fit in Arrow Decimal128 for precision {precision}" ) })?; decimal128_scalar(value, precision, scale) @@ -209,7 +209,7 @@ fn map_to_arrow(scalar: MapScalar<'_>) -> Result, VortexError> { let entries_len = entries.len(); let entries_len = i32::try_from(entries_len).map_err(|_| { vortex_err!( - MismatchedTypes: "Cannot convert map scalar with {entries_len} entries to Arrow: MapArray offsets are i32" + "Cannot convert map scalar with {entries_len} entries to Arrow: MapArray offsets are i32" ) })?; let offsets = OffsetBuffer::new(vec![0_i32, entries_len].into()); @@ -249,7 +249,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr let ext_dtype = scalar.ext_dtype(); let Some(temporal) = ext_dtype.metadata_opt::() else { vortex_bail!( - MismatchedTypes: "Cannot convert extension scalar {} to Arrow", + "Cannot convert extension scalar {} to Arrow", ext_dtype.id() ) }; @@ -257,7 +257,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr let storage_scalar = scalar.to_storage_scalar(); let primitive = storage_scalar .as_primitive_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected primitive scalar"))?; + .ok_or_else(|| vortex_err!("Expected primitive scalar"))?; match temporal { TemporalMetadata::Timestamp(unit, tz) => { @@ -276,7 +276,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr timestamp_to_arrow_scalar!(value, tz.clone(), TimestampSecondArray) } TimeUnit::Days => { - vortex_bail!(InvalidArgument: "Unsupported TimeUnit {unit} for {}", ext_dtype.id()) + vortex_bail!("Unsupported TimeUnit {unit} for {}", ext_dtype.id()) } } } @@ -288,7 +288,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr value_to_arrow_scalar!(primitive.as_::(), Date32Array) } TimeUnit::Nanoseconds | TimeUnit::Microseconds | TimeUnit::Seconds => { - vortex_bail!(InvalidArgument: "Unsupported TimeUnit {unit} for {}", ext_dtype.id()) + vortex_bail!("Unsupported TimeUnit {unit} for {}", ext_dtype.id()) } }, TemporalMetadata::Time(unit) => match unit { @@ -305,7 +305,7 @@ fn extension_to_arrow(scalar: ExtScalar<'_>) -> Result, VortexErr value_to_arrow_scalar!(primitive.as_::(), Time32SecondArray) } TimeUnit::Days => { - vortex_bail!(InvalidArgument: "Unsupported TimeUnit {unit} for {}", ext_dtype.id()) + vortex_bail!("Unsupported TimeUnit {unit} for {}", ext_dtype.id()) } }, } @@ -860,11 +860,11 @@ mod tests { } fn serialize_metadata(&self, _options: &Self::Metadata) -> VortexResult> { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn deserialize_metadata(&self, _data: &[u8]) -> VortexResult { - vortex_bail!(NotImplemented: "not implemented") + vortex_bail!("not implemented") } fn validate_dtype(_ext_dtype: &ExtDType) -> VortexResult<()> { diff --git a/vortex-arrow/src/session.rs b/vortex-arrow/src/session.rs index a847bac834f..32108a4f599 100644 --- a/vortex-arrow/src/session.rs +++ b/vortex-arrow/src/session.rs @@ -333,7 +333,7 @@ impl ArrowSession { return Ok(field); } } - vortex_bail!(InvalidArgument: "extension type cannot be converted to Arrow without a plugin: {ext}"); + vortex_bail!("extension type cannot be converted to Arrow without a plugin: {ext}"); } DType::Variant(_) => { // TODO(Adam): This currently encodes information about parquet-variant @@ -371,7 +371,7 @@ impl ArrowSession { /// extensions are preserved via [`Self::to_arrow_field`]. pub fn to_arrow_schema(&self, dtype: &DType) -> VortexResult { let DType::Struct(struct_dtype, _) = dtype else { - vortex_bail!(InvalidArgument: "to_arrow_schema requires a top-level struct dtype, got {dtype}"); + vortex_bail!("to_arrow_schema requires a top-level struct dtype, got {dtype}"); }; let mut fields = Vec::with_capacity(struct_dtype.names().len()); for (name, field_dtype) in struct_dtype.names().iter().zip(struct_dtype.fields()) { @@ -447,22 +447,22 @@ impl ArrowSession { DataType::Map(entries, keys_sorted) => { vortex_ensure!( !entries.is_nullable(), - InvalidArgument: "Arrow map entries field must be non-nullable" + "Arrow map entries field must be non-nullable" ); let DataType::Struct(fields) = entries.data_type() else { vortex_bail!( - MismatchedTypes: "Arrow map entries field must have Struct type, got {:?}", + "Arrow map entries field must have Struct type, got {:?}", entries.data_type() ); }; vortex_ensure_eq!( fields.len(), 2, - InvalidArgument: "Arrow map entries struct must contain exactly two fields" + "Arrow map entries struct must contain exactly two fields" ); vortex_ensure!( !fields[0].is_nullable(), - InvalidArgument: "Arrow map key field must be non-nullable" + "Arrow map key field must be non-nullable" ); DType::map( self.from_arrow_field(fields[0].as_ref())?, @@ -516,7 +516,7 @@ impl ArrowSession { batch: RecordBatch, schema: &Schema, ) -> VortexResult { - vortex_ensure_eq!(batch.num_columns(), schema.fields().len(), InvalidArgument); + vortex_ensure_eq!(batch.num_columns(), schema.fields().len()); let length = batch.num_rows(); let names = FieldNames::from_iter( schema @@ -634,7 +634,7 @@ impl ArrowSession { vortex_ensure_eq!( arr.len(), len, - AssertionFailed: "Arrow importer {} returned {} elements for an array of {}", + "Arrow importer {} returned {} elements for an array of {}", plugin.arrow_ext_id(), arr.len(), len @@ -645,7 +645,7 @@ impl ArrowSession { vortex_ensure_eq!( arr.len(), len, - AssertionFailed: "Arrow importer {} declined and returned {} elements for an array of {}", + "Arrow importer {} declined and returned {} elements for an array of {}", plugin.arrow_ext_id(), arr.len(), len @@ -786,7 +786,7 @@ impl ArrowSession { DataType::Int32 => self.run_end_from_arrow::(array, &values_field), DataType::Int64 => self.run_end_from_arrow::(array, &values_field), ends_dt => vortex_bail!( - InvalidArgument: "Arrow run-end array run ends must be Int16, Int32 or Int64, got {ends_dt}" + "Arrow run-end array run ends must be Int16, Int32 or Int64, got {ends_dt}" ), } } @@ -822,7 +822,7 @@ impl ArrowSession { let run_array = array .as_any() .downcast_ref::>() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected an Arrow RunArray, got {}", array.data_type()))?; + .ok_or_else(|| vortex_err!("expected an Arrow RunArray, got {}", array.data_type()))?; let values = self.from_arrow_array_inner(ArrowArrayRef::clone(run_array.values()), values_field)?; run_end_from_arrow(run_array, values) @@ -901,7 +901,7 @@ impl ArrowExporter<'_> { vortex_ensure_eq!( arrow.len(), len, - AssertionFailed: "Arrow array length does not match Vortex array length after conversion to {:?}", + "Arrow array length does not match Vortex array length after conversion to {:?}", arrow ); return Ok(arrow); diff --git a/vortex-bench/src/conversions.rs b/vortex-bench/src/conversions.rs index 376a6d2085c..1398ea37835 100644 --- a/vortex-bench/src/conversions.rs +++ b/vortex-bench/src/conversions.rs @@ -549,8 +549,7 @@ fn wkb_field_to_little_endian(field: &ArrayRef, ctx: &mut ExecutionCtx) -> Vorte return Ok(None); } let wkb = values.bytes_at(i); - let geometry = read_wkb(wkb.as_slice()) - .map_err(|e| vortex_err!(InvalidArgument: "invalid WKB: {e}"))?; + let geometry = read_wkb(wkb.as_slice()).map_err(|e| vortex_err!("invalid WKB: {e}"))?; let mut encoded = Vec::with_capacity(wkb.len()); write_geometry( &mut encoded, @@ -559,7 +558,7 @@ fn wkb_field_to_little_endian(field: &ArrayRef, ctx: &mut ExecutionCtx) -> Vorte endianness: Endianness::LittleEndian, }, ) - .map_err(|e| vortex_err!(Serde: "re-encoding WKB as little-endian: {e}"))?; + .map_err(|e| vortex_err!("re-encoding WKB as little-endian: {e}"))?; Ok(Some(encoded)) }) .collect::>()?; diff --git a/vortex-bench/src/datasets/mod.rs b/vortex-bench/src/datasets/mod.rs index d7dde97f544..89b3a6782b2 100644 --- a/vortex-bench/src/datasets/mod.rs +++ b/vortex-bench/src/datasets/mod.rs @@ -183,7 +183,7 @@ impl BenchmarkDataset { ], BenchmarkDataset::ClickBench { .. } | BenchmarkDataset::ClickBenchSorted => &["hits"], BenchmarkDataset::PublicBi { .. } => { - vortex_panic!(NotImplemented: "PublicBi table names are not implemented") + vortex_panic!("PublicBi table names are not implemented") } BenchmarkDataset::SpatialBench { .. } => &["trip", "building", "customer", "zone"], BenchmarkDataset::StatPopGen { .. } => &["statpopgen"], diff --git a/vortex-bench/src/lib.rs b/vortex-bench/src/lib.rs index 2162c9a6f15..03172307dce 100644 --- a/vortex-bench/src/lib.rs +++ b/vortex-bench/src/lib.rs @@ -107,14 +107,14 @@ impl FromStr for Target { fn from_str(target_string: &str) -> Result { let split = target_string.split(":").collect_vec(); let [engine_str, format_str] = split.as_slice() else { - vortex_panic!(InvalidArgument: "invalid target string {}", target_string); + vortex_panic!("invalid target string {}", target_string); }; Ok(Self { engine: Engine::from_str(engine_str, true) - .map_err(|e| { + .map_err(|e| { vortex_err!( - MismatchedTypes: "cannot convert str ({}) to an Engine oneof([{}]), got error {}", + "cannot convert str ({}) to an Engine oneof([{}]), got error {}", *engine_str, Engine::value_variants().iter().join(","), e @@ -122,9 +122,9 @@ impl FromStr for Target { }) .vortex_expect("operation should succeed in benchmark"), format: Format::from_str(format_str, true) - .map_err(|e| { + .map_err(|e| { vortex_err!( - MismatchedTypes: "cannot convert str ({}) to a Format oneof([{}]), got error {}", + "cannot convert str ({}) to a Format oneof([{}]), got error {}", *format_str, Format::value_variants().iter().join(","), e diff --git a/vortex-bench/src/measurements.rs b/vortex-bench/src/measurements.rs index 01c9a89ce90..3403a7051cb 100644 --- a/vortex-bench/src/measurements.rs +++ b/vortex-bench/src/measurements.rs @@ -75,7 +75,7 @@ impl Div for MeasurementValue { MeasurementValue::Float(a as f64 / b as f64) } _ => { - vortex_panic!(MismatchedTypes: "Can't divide two measurement values of different kinds") + vortex_panic!("Can't divide two measurement values of different kinds") } } } @@ -102,7 +102,7 @@ impl Add for MeasurementValue { } (MeasurementValue::Int(a), MeasurementValue::Int(b)) => MeasurementValue::Int(a + b), _ => { - vortex_panic!(MismatchedTypes: "Can't subtract two measurement values of different kinds") + vortex_panic!("Can't subtract two measurement values of different kinds") } } } @@ -118,7 +118,7 @@ impl Sub for MeasurementValue { } (MeasurementValue::Int(a), MeasurementValue::Int(b)) => MeasurementValue::Int(a - b), _ => { - vortex_panic!(MismatchedTypes: "Can't subtract two measurement values of different kinds") + vortex_panic!("Can't subtract two measurement values of different kinds") } } } @@ -184,7 +184,7 @@ impl TimingMeasurement { pub fn mean_time(&self) -> Duration { let len = self.runs.len(); if len == 0 { - vortex_panic!(InvalidArgument: "cannot have no runs"); + vortex_panic!("cannot have no runs"); } let total_nanos: u128 = self.runs.iter().map(|d| d.as_nanos()).sum(); @@ -200,7 +200,7 @@ impl TimingMeasurement { pub fn median_time(&self) -> Duration { let len = self.runs.len(); if len == 0 { - vortex_panic!(InvalidArgument: "cannot have no runs"); + vortex_panic!("cannot have no runs"); } let mut sorted_runs = self.runs.clone(); @@ -259,7 +259,7 @@ impl QueryMeasurement { pub fn median_run(&self) -> Duration { let len = self.runs.len(); if len == 0 { - vortex_panic!(InvalidArgument: "cannot have no runs"); + vortex_panic!("cannot have no runs"); } let mut sorted_runs = self.runs.clone(); @@ -362,7 +362,7 @@ impl ToJson for CompressionTimingMeasurement { Format::Parquet => (format!("parquet_rs-zstd {}", self.name), Engine::Vortex), Format::Lance => (format!("lance {}", self.name), Engine::Vortex), _ => vortex_panic!( - NotImplemented: "CompressionTimingMeasurement only supports arrow-ipc, vortex, lance, and parquet formats" + "CompressionTimingMeasurement only supports arrow-ipc, vortex, lance, and parquet formats" ), }; diff --git a/vortex-bench/src/public_bi.rs b/vortex-bench/src/public_bi.rs index 35879cd6d2e..3e651df5bb7 100644 --- a/vortex-bench/src/public_bi.rs +++ b/vortex-bench/src/public_bi.rs @@ -150,11 +150,10 @@ impl PBIDatasets { let name = path .file_name() .into_string() - .map_err(|e| vortex_err!(InvalidArgument: "Not a unicode name: {e:?}"))?; + .map_err(|e| vortex_err!("Not a unicode name: {e:?}"))?; Ok(( - ::from_str(name.trim(), true).map_err( - |_e| vortex_err!(InvalidArgument: "unsupported dataset: {} {_e}", &name), - )?, + ::from_str(name.trim(), true) + .map_err(|_e| vortex_err!("unsupported dataset: {} {_e}", &name))?, PBIBenchmark { name, base_path: path.path(), @@ -168,7 +167,7 @@ impl PBIDatasets { pub fn get(&self, dataset: PBIDataset) -> &PBIBenchmark { self.benchmarks .get(&dataset) - .ok_or_else(|| vortex_err!(NotFound: "{:?} not found", dataset)) + .ok_or_else(|| vortex_err!("{:?} not found", dataset)) .unwrap() } } @@ -194,14 +193,14 @@ impl PBIBenchmark { let file_name = sql_file .file_name() .into_string() - .map_err(|e| vortex_err!(InvalidArgument: "Not a unicode name: {e:?}"))?; + .map_err(|e| vortex_err!("Not a unicode name: {e:?}"))?; let query_idx = file_name .strip_suffix(".sql") .ok_or_else(|| { - vortex_err!(InvalidArgument: "found non-sql file under queries folder {file_name}") + vortex_err!("found non-sql file under queries folder {file_name}") })? .parse() - .map_err(|_| vortex_err!(InvalidArgument: "non numeric filename {file_name}"))?; + .map_err(|_| vortex_err!("non numeric filename {file_name}"))?; let query = fs::read_to_string(sql_file.path())?; Ok((query_idx, query)) }) diff --git a/vortex-bench/src/runner.rs b/vortex-bench/src/runner.rs index d47b5cc5a51..d0795fca288 100644 --- a/vortex-bench/src/runner.rs +++ b/vortex-bench/src/runner.rs @@ -322,8 +322,8 @@ impl SqlBenchmarkRunner { tracing::debug!(%format, query_idx, "Running query"); self.run_query(query_idx, format, iterations, || { execute(&mut ctx, query_idx, format, query.as_str()).unwrap_or_else( - |err| { - vortex_panic!(AssertionFailed: "query {query_idx} failed: {err}"); + |err| { + vortex_panic!("query {query_idx} failed: {err}"); }, ) }); @@ -403,8 +403,8 @@ impl SqlBenchmarkRunner { let start = Instant::now(); let (timing, result) = execute(query_idx, &ctx, query.as_str()) .await - .unwrap_or_else(|err| { - vortex_panic!(AssertionFailed: "query {query_idx} failed: {err}"); + .unwrap_or_else(|err| { + vortex_panic!("query {query_idx} failed: {err}"); }); let elapsed = timing.unwrap_or_else(|| start.elapsed()); runs.push(elapsed); diff --git a/vortex-bench/src/statpopgen/builder.rs b/vortex-bench/src/statpopgen/builder.rs index cf406527c2e..4e11b4e43e4 100644 --- a/vortex-bench/src/statpopgen/builder.rs +++ b/vortex-bench/src/statpopgen/builder.rs @@ -277,7 +277,7 @@ impl<'a> GnomADBuilder<'a> { self.POS_builder.append_value( record .variant_start() - .ok_or_else(|| vortex_err!(InvalidArgument: "pos must not be null"))?? + .ok_or_else(|| vortex_err!("pos must not be null"))?? .get() as u64, ); self.ID_builder.append_value(record.ids().as_ref()); @@ -341,7 +341,7 @@ impl<'a> GnomADBuilder<'a> { .SB_builder .values() .append_option(parse_list_int32_format(value)?), - _ => vortex_bail!(NotFound: "unknown field {field}"), + _ => vortex_bail!("unknown field {field}"), } } } diff --git a/vortex-bench/src/statpopgen/vcf_conversion.rs b/vortex-bench/src/statpopgen/vcf_conversion.rs index 4eb1721803f..eaa8a1a81c6 100644 --- a/vortex-bench/src/statpopgen/vcf_conversion.rs +++ b/vortex-bench/src/statpopgen/vcf_conversion.rs @@ -29,16 +29,16 @@ pub fn builder_from_info(info: &Map) -> InfoArrayBuilder { (Number::Count(1), Type::Float) => InfoArrayBuilder::Float(Default::default()), (Number::Count(0), Type::Flag) => InfoArrayBuilder::Flag(Default::default()), (Number::Count(1), Type::Character) => { - vortex_panic!(NotImplemented: "Character INFO fields are not supported") + vortex_panic!("Character INFO fields are not supported") } (Number::Count(1), Type::String) => InfoArrayBuilder::String(Default::default()), (_, Type::Integer) => InfoArrayBuilder::ListInteger(Default::default()), (_, Type::Float) => InfoArrayBuilder::ListFloat(Default::default()), (_, Type::Flag) => { - vortex_panic!(NotImplemented: "Flag INFO fields with a count are not supported") + vortex_panic!("Flag INFO fields with a count are not supported") } (_, Type::Character) => { - vortex_panic!(NotImplemented: "Character INFO fields are not supported") + vortex_panic!("Character INFO fields are not supported") } (_, Type::String) => InfoArrayBuilder::ListString(Default::default()), } @@ -54,16 +54,16 @@ pub fn data_type_from_info(info: &Map) -> DataType { (Number::Count(1), Type::Float) => Float32, (Number::Count(0), Type::Flag) => Boolean, (Number::Count(1), Type::Character) => { - vortex_panic!(NotImplemented: "Character INFO fields are not supported") + vortex_panic!("Character INFO fields are not supported") } (Number::Count(1), Type::String) => Utf8, (_, Type::Integer) => list(Int32), (_, Type::Float) => list(Float32), (_, Type::Flag) => { - vortex_panic!(NotImplemented: "Flag INFO fields with a count are not supported") + vortex_panic!("Flag INFO fields with a count are not supported") } (_, Type::Character) => { - vortex_panic!(NotImplemented: "Character INFO fields are not supported") + vortex_panic!("Character INFO fields are not supported") } (_, Type::String) => list(Utf8), } @@ -74,7 +74,7 @@ pub fn value_int32(v: Option) -> VortexResult> { None => None, Some(Value::Integer(x)) => Some(x), - _ => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), + _ => vortex_bail!("expected int32 {:?}", v), }) } @@ -82,7 +82,7 @@ pub fn value_float32(v: Option) -> VortexResult> { Ok(match v { None => None, Some(Value::Float(x)) => Some(x), - _ => vortex_bail!(InvalidArgument: "expected f64 {:?}", v), + _ => vortex_bail!("expected f64 {:?}", v), }) } @@ -90,7 +90,7 @@ pub fn value_string(v: Option) -> VortexResult>> { Ok(match v { None => None, Some(Value::String(x)) => Some(x), - _ => vortex_bail!(InvalidArgument: "expected string {:?}", v), + _ => vortex_bail!("expected string {:?}", v), }) } @@ -98,7 +98,7 @@ pub fn value_boolean(v: Option) -> VortexResult { Ok(match v { None => false, Some(Value::Flag) => true, - _ => vortex_bail!(MismatchedTypes: "expected bool {:?}", v), + _ => vortex_bail!("expected bool {:?}", v), }) } @@ -109,9 +109,9 @@ pub fn value_list_int32<'a>( None => None, Some(Value::Array(a)) => match a { Array::Integer(values) => Some(values), - v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), + v => vortex_bail!("expected int32 {:?}", v), }, - v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), + v => vortex_bail!("expected int32 {:?}", v), }) } @@ -122,9 +122,9 @@ pub fn value_list_float32<'a>( None => None, Some(Value::Array(a)) => match a { Array::Float(values) => Some(values), - v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), + v => vortex_bail!("expected int32 {:?}", v), }, - v => vortex_bail!(InvalidArgument: "expected f64 {:?}", v), + v => vortex_bail!("expected f64 {:?}", v), }) } @@ -135,9 +135,9 @@ pub fn value_list_string<'a>( None => None, Some(Value::Array(a)) => match a { Array::String(values) => Some(values), - v => vortex_bail!(MismatchedTypes: "expected int32 {:?}", v), + v => vortex_bail!("expected int32 {:?}", v), }, - v => vortex_bail!(InvalidArgument: "expected string {:?}", v), + v => vortex_bail!("expected string {:?}", v), }) } @@ -146,7 +146,7 @@ pub fn parse_genotype(gt: Option) -> VortexResult> { return Ok(None); }; let EntryValue::Genotype(gt) = gt else { - vortex_bail!(InvalidArgument: "expected genotype {:?}", gt) + vortex_bail!("expected genotype {:?}", gt) }; match gt .iter() @@ -154,7 +154,7 @@ pub fn parse_genotype(gt: Option) -> VortexResult> { { [None, None] => Ok(None), [Some(l), Some(r)] => Ok(Some(l as u64 + r as u64)), - _ => vortex_bail!(AssertionFailed: "wtf {:?}", gt), + _ => vortex_bail!("wtf {:?}", gt), } } @@ -163,7 +163,7 @@ pub fn parse_int32_format(x: Option) -> VortexResult> { return Ok(None); }; let EntryValue::Integer(x) = x else { - vortex_bail!(MismatchedTypes: "expected int32 {:?}", x) + vortex_bail!("expected int32 {:?}", x) }; Ok(Some(x)) } @@ -179,7 +179,7 @@ pub fn parse_pgt_format(x: Option) -> VortexResult> { EntryValue::String(x) if x == "0|1" => Some(1), EntryValue::String(x) if x == "1|0" => Some(2), EntryValue::String(x) if x == "1|1" => Some(3), - _ => vortex_bail!(InvalidArgument: "expected biallelic phased genotype {:?}", x), + _ => vortex_bail!("expected biallelic phased genotype {:?}", x), }) } @@ -189,7 +189,7 @@ pub fn parse_string_format<'a>(x: Option>) -> VortexResult

() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null primitive scalar value"))?; + .ok_or_else(|| vortex_err!("Expected non-null primitive scalar value"))?; // Allocate output buffer on device let mut output_buffer = ctx.device_alloc::

(array_len)?; @@ -154,12 +154,12 @@ where let decimal_scalar = array.scalar().as_decimal(); let decimal_value = decimal_scalar .decimal_value() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected non-null decimal scalar value"))?; + .ok_or_else(|| vortex_err!("Expected non-null decimal scalar value"))?; // Cast the decimal value to the native type let value: D = decimal_value .cast::() - .ok_or_else(|| vortex_err!(Overflow: "Failed to cast decimal value to native type"))?; + .ok_or_else(|| vortex_err!("Failed to cast decimal value to native type"))?; // Allocate output buffer on device let mut output_buffer = ctx.device_alloc::(array_len)?; diff --git a/vortex-cuda/src/kernel/arrays/dict.rs b/vortex-cuda/src/kernel/arrays/dict.rs index c3d9754c6e5..e9bb20daa94 100644 --- a/vortex-cuda/src/kernel/arrays/dict.rs +++ b/vortex-cuda/src/kernel/arrays/dict.rs @@ -63,7 +63,7 @@ impl CudaExecute for DictExecutor { DType::Decimal(..) => execute_dict_decimal(dict_array, ctx).await, DType::Primitive(..) => execute_dict_prim(dict_array, ctx).await, DType::Utf8(..) | DType::Binary(..) => execute_dict_varbinview(dict_array, ctx).await, - dt => vortex_bail!(InvalidArgument: "unsupported decompress for DType={dt}"), + dt => vortex_bail!("unsupported decompress for DType={dt}"), } } } @@ -117,7 +117,7 @@ async fn execute_dict_bool_typed( codes: PrimitiveArray, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - vortex_ensure!(!codes.is_empty(), InvalidArgument: "cannot CUDA-decode an empty dictionary"); + vortex_ensure!(!codes.is_empty(), "cannot CUDA-decode an empty dictionary"); let codes_len = codes.len(); let values_len = values.len(); diff --git a/vortex-cuda/src/kernel/arrays/list.rs b/vortex-cuda/src/kernel/arrays/list.rs index 66236e4630e..167c12df9c4 100644 --- a/vortex-cuda/src/kernel/arrays/list.rs +++ b/vortex-cuda/src/kernel/arrays/list.rs @@ -50,7 +50,7 @@ impl CudaExecute for ListExecutor { ) -> VortexResult { let list = array .try_downcast::() - .map_err(|_| vortex_err!(MismatchedTypes: "Expected ListArray"))?; + .map_err(|_| vortex_err!("Expected ListArray"))?; let list_len = list.len(); let validity = execute_validity_cuda(list.list_validity(), list_len, ctx).await?; @@ -81,7 +81,7 @@ impl CudaExecute for ListExecutor { vortex_ensure_eq!( offsets.len(), list_len + 1, - InvalidArgument: "ListArray must have one more offset than lists" + "ListArray must have one more offset than lists" ); let offsets_ptype = offsets.ptype(); diff --git a/vortex-cuda/src/kernel/arrays/masked.rs b/vortex-cuda/src/kernel/arrays/masked.rs index 371708bd5bc..c318f7a8af9 100644 --- a/vortex-cuda/src/kernel/arrays/masked.rs +++ b/vortex-cuda/src/kernel/arrays/masked.rs @@ -37,7 +37,7 @@ impl CudaExecute for MaskedExecutor { ) -> VortexResult { let masked = array .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "Expected MaskedArray"))?; + .map_err(|_| vortex_err!("Expected MaskedArray"))?; let len = masked.len(); let validity = masked.masked_validity(); @@ -46,7 +46,7 @@ impl CudaExecute for MaskedExecutor { // output validity. Combining two device-resident bitmaps would need a CPU compute pass. if matches!(masked.child().validity()?, Validity::Array(_)) { vortex_bail!( - InvalidArgument: "MaskedArray child carries a per-element validity bitmap, which cannot be combined with the mask on the GPU" + "MaskedArray child carries a per-element validity bitmap, which cannot be combined with the mask on the GPU" ); } diff --git a/vortex-cuda/src/kernel/encodings/alp.rs b/vortex-cuda/src/kernel/encodings/alp.rs index 07db995116b..e543db1aca0 100644 --- a/vortex-cuda/src/kernel/encodings/alp.rs +++ b/vortex-cuda/src/kernel/encodings/alp.rs @@ -47,7 +47,7 @@ impl CudaExecute for ALPExecutor { ) -> VortexResult { let array = array .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "Expected ALPArray"))?; + .map_err(|_| vortex_err!("Expected ALPArray"))?; match_each_alp_float_ptype!(array.dtype().as_ptype(), |A| { decode_alp::(array, ctx).await @@ -66,7 +66,7 @@ where A::ALPInt: NativePType + DeviceRepr + Send + Sync + 'static, { let array_len = array.encoded().len(); - vortex_ensure!(array_len > 0, InvalidArgument: "ALP array must not be empty"); + vortex_ensure!(array_len > 0, "ALP array must not be empty"); // Get the exponent factors from the lookup tables. let exponents = array.exponents(); diff --git a/vortex-cuda/src/kernel/encodings/bitpacked.rs b/vortex-cuda/src/kernel/encodings/bitpacked.rs index df92f479877..3b28692722c 100644 --- a/vortex-cuda/src/kernel/encodings/bitpacked.rs +++ b/vortex-cuda/src/kernel/encodings/bitpacked.rs @@ -66,7 +66,7 @@ pub(crate) fn bitpacked_slice_view( let block_stop = offset_stop.div_ceil(PATCH_CHUNK_SIZE) * PATCH_CHUNK_SIZE; let BitWidthsView::Global(bit_width) = bp.bit_widths() else { - vortex_bail!(NotImplemented: "CUDA does not support BitPacked arrays with per-block bit widths"); + vortex_bail!("CUDA does not support BitPacked arrays with per-block bit widths"); }; let encoded_start = (block_start / 8) * bit_width as usize; let encoded_stop = (block_stop / 8) * bit_width as usize; @@ -122,8 +122,8 @@ impl CudaExecute for BitPackedExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let (array, patch_range) = Self::try_specialize(array)? - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected BitPackedArray"))?; + let (array, patch_range) = + Self::try_specialize(array)?.ok_or_else(|| vortex_err!("Expected BitPackedArray"))?; let ptype = array.ptype(array.dtype()); match_each_integer_ptype!(ptype, |A| { @@ -178,10 +178,10 @@ where validity, } = BitPacked::into_parts(array); let BitWidths::Global(bit_width) = bit_widths else { - vortex_bail!(NotImplemented: "CUDA does not support BitPacked arrays with per-block bit widths"); + vortex_bail!("CUDA does not support BitPacked arrays with per-block bit widths"); }; - vortex_ensure!(len > 0, InvalidArgument: "Non empty array"); + vortex_ensure!(len > 0, "Non empty array"); let offset = offset as usize; let device_input = ctx.ensure_on_device(packed).await?; diff --git a/vortex-cuda/src/kernel/encodings/date_time_parts.rs b/vortex-cuda/src/kernel/encodings/date_time_parts.rs index ae98090309d..35be0f0dd36 100644 --- a/vortex-cuda/src/kernel/encodings/date_time_parts.rs +++ b/vortex-cuda/src/kernel/encodings/date_time_parts.rs @@ -53,15 +53,15 @@ impl CudaExecute for DateTimePartsExecutor { let output_len = array.len(); let array = array .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "Expected DateTimePartsArray"))?; + .map_err(|_| vortex_err!("Expected DateTimePartsArray"))?; // Extract the temporal metadata from the dtype let DType::Extension(ext) = array.dtype().clone() else { - vortex_bail!(InvalidArgument: "DateTimePartsArray dtype must be an Extension type") + vortex_bail!("DateTimePartsArray dtype must be an Extension type") }; let Some(options) = ext.metadata_opt::() else { - vortex_bail!(MismatchedTypes: "DateTimePartsArray must have Timestamp metadata") + vortex_bail!("DateTimePartsArray must have Timestamp metadata") }; let time_unit = options.unit; @@ -94,7 +94,7 @@ impl CudaExecute for DateTimePartsExecutor { TimeUnit::Milliseconds => 1_000, TimeUnit::Seconds => 1, TimeUnit::Days => { - vortex_bail!(NotImplemented: "Cannot decode DateTimeParts with TimeUnit::Days") + vortex_bail!("Cannot decode DateTimeParts with TimeUnit::Days") } }; diff --git a/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs b/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs index e560e30c194..ee3814ca9fc 100644 --- a/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs +++ b/vortex-cuda/src/kernel/encodings/decimal_byte_parts.rs @@ -32,7 +32,7 @@ impl CudaExecute for DecimalBytePartsExecutor { ctx: &mut CudaExecutionCtx, ) -> VortexResult { let Ok(array) = array.try_downcast::() else { - vortex_bail!(MismatchedTypes: "cannot downcast to DecimalBytePartsArray") + vortex_bail!("cannot downcast to DecimalBytePartsArray") }; let decimal_dtype = *array @@ -43,7 +43,7 @@ impl CudaExecute for DecimalBytePartsExecutor { // Reassembling lower parts into wide decimals is not implemented on the GPU; the MSP // alone is not the value. if !array.lower_parts().is_empty() { - vortex_bail!(InvalidArgument: "DecimalBytePartsArray with lower parts is not supported on GPU") + vortex_bail!("DecimalBytePartsArray with lower parts is not supported on GPU") } let msp = array.msp().clone(); diff --git a/vortex-cuda/src/kernel/encodings/delta.rs b/vortex-cuda/src/kernel/encodings/delta.rs index 2213b7041e4..0d01b3789c9 100644 --- a/vortex-cuda/src/kernel/encodings/delta.rs +++ b/vortex-cuda/src/kernel/encodings/delta.rs @@ -60,7 +60,7 @@ impl CudaExecute for DeltaExecutor { ) -> VortexResult { let delta = array .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "Expected DeltaArray"))?; + .map_err(|_| vortex_err!("Expected DeltaArray"))?; decode_delta(delta, ctx).await } } @@ -98,11 +98,11 @@ async fn decode_delta(array: DeltaArray, ctx: &mut CudaExecutionCtx) -> VortexRe vortex_ensure_eq!( deltas_len % FL_CHUNK, 0, - InvalidArgument: "Delta deltas child must be padded to a multiple of {FL_CHUNK}, got {deltas_len}" + "Delta deltas child must be padded to a multiple of {FL_CHUNK}, got {deltas_len}" ); vortex_ensure!( offset + len <= deltas_len, - InvalidArgument: "Delta slice {offset}..{} exceeds its {deltas_len} decoded values", + "Delta slice {offset}..{} exceeds its {deltas_len} decoded values", offset + len ); let num_chunks = deltas_len / FL_CHUNK; @@ -110,7 +110,7 @@ async fn decode_delta(array: DeltaArray, ctx: &mut CudaExecutionCtx) -> VortexRe let required_bases = num_chunks * lanes; vortex_ensure!( bases.len() >= required_bases, - InvalidArgument: "Delta needs {required_bases} bases for {num_chunks} chunks, got {}", + "Delta needs {required_bases} bases for {num_chunks} chunks, got {}", bases.len() ); diff --git a/vortex-cuda/src/kernel/encodings/for_.rs b/vortex-cuda/src/kernel/encodings/for_.rs index ac5d98fb5f6..bcec39213a2 100644 --- a/vortex-cuda/src/kernel/encodings/for_.rs +++ b/vortex-cuda/src/kernel/encodings/for_.rs @@ -58,13 +58,12 @@ impl CudaExecute for FoRExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = Self::try_specialize(array) - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected FoRArray"))?; + let array = Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected FoRArray"))?; // Per-chunk references have no CUDA kernel yet, so decode them on the CPU. // TODO(mk): implement CUDA FoR decoding for blocked references. let FoRReferences::Global(reference) = array.references() else { - vortex_bail!(NotImplemented: "CUDA FoR decoding requires a global reference") + vortex_bail!("CUDA FoR decoding requires a global reference") }; let reference = reference.clone(); @@ -106,10 +105,10 @@ where P: NativePType + DeviceRepr + Send + Sync + 'static, { let array_len = array.encoded().len(); - vortex_ensure!(array_len > 0, InvalidArgument: "FoR encoded array must not be empty"); + vortex_ensure!(array_len > 0, "FoR encoded array must not be empty"); let FoRReferences::Global(reference) = array.references() else { - vortex_bail!(NotImplemented: "CUDA FoR decoding requires a global reference") + vortex_bail!("CUDA FoR decoding requires a global reference") }; let reference: P = reference .as_primitive() diff --git a/vortex-cuda/src/kernel/encodings/fsst.rs b/vortex-cuda/src/kernel/encodings/fsst.rs index bfc8caadee0..efa499b60ec 100644 --- a/vortex-cuda/src/kernel/encodings/fsst.rs +++ b/vortex-cuda/src/kernel/encodings/fsst.rs @@ -79,7 +79,7 @@ async fn cuda_validity( )), Validity::Array(array) => { let bool_array = array.try_downcast::().map_err(|array| { - vortex_err!(MismatchedTypes: "CUDA validity execution produced {}", array.dtype()) + vortex_err!("CUDA validity execution produced {}", array.dtype()) })?; let BoolDataParts { bits, meta } = bool_array.into_data().into_parts(len); let bit_offset = meta.offset(); @@ -107,8 +107,7 @@ impl CudaExecute for FSSTExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let fsst = Self::try_specialize(array) - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected FSSTArray"))?; + let fsst = Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected FSSTArray"))?; let dtype = fsst.dtype().clone(); let validity = fsst.codes().validity()?; diff --git a/vortex-cuda/src/kernel/encodings/onpair.rs b/vortex-cuda/src/kernel/encodings/onpair.rs index c4a98468243..6fe8152a19e 100644 --- a/vortex-cuda/src/kernel/encodings/onpair.rs +++ b/vortex-cuda/src/kernel/encodings/onpair.rs @@ -114,7 +114,7 @@ impl CudaExecute for OnPairExecutor { ) -> VortexResult { let onpair = array .as_typed::() - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected OnPairArray"))?; + .ok_or_else(|| vortex_err!("Expected OnPairArray"))?; decode_onpair(onpair, ctx).await } } @@ -153,7 +153,7 @@ async fn decode_onpair( vortex_ensure_eq!( row_total, total_size as u64, - Serde: "OnPair uncompressed_lengths total does not match the decoded codes size" + "OnPair uncompressed_lengths total does not match the decoded codes size" ); let row_offsets_view = row_offsets.cuda_view::()?; let bytes_view = bytes.cuda_view::()?; @@ -185,7 +185,7 @@ async fn decode_onpair( vortex_ensure_eq!( row_total, total_size as u64, - Serde: "OnPair uncompressed_lengths total does not match the decoded codes size" + "OnPair uncompressed_lengths total does not match the decoded codes size" ); let host_bytes = bytes.try_to_host()?.await?; @@ -238,7 +238,7 @@ pub(crate) async fn decode_onpair_varbin( vortex_ensure_eq!( row_total, total_size as u64, - Serde: "OnPair uncompressed_lengths total does not match the decoded codes size" + "OnPair uncompressed_lengths total does not match the decoded codes size" ); Ok(DecodedVarBin { @@ -310,7 +310,7 @@ async fn decode_onpair_bytes( PType::U8 => decode_window::(codes, codes_offsets, lengths, dict, ctx).await, PType::U16 => decode_window::(codes, codes_offsets, lengths, dict, ctx).await, other => { - vortex_bail!(MismatchedTypes: "OnPair codes must decompress to u8 or u16, got {other}") + vortex_bail!("OnPair codes must decompress to u8 or u16, got {other}") } } } @@ -384,7 +384,7 @@ where let mut status = ctx.device_alloc::(1)?; ctx.stream() .memset_zeros(&mut status) - .map_err(|e| vortex_err!(Io: "Failed to zero OnPair status flag: {e}"))?; + .map_err(|e| vortex_err!("Failed to zero OnPair status flag: {e}"))?; let staged = stage_codes(codes, &dict, &mut status, ctx).await?; @@ -452,7 +452,7 @@ where let scratch = ctx .stream() .clone_dtoh(&scratch) - .map_err(|e| vortex_err!(Io: "Failed to copy OnPair window scratch to host: {e}"))?; + .map_err(|e| vortex_err!("Failed to copy OnPair window scratch to host: {e}"))?; let [ token_start, token_end, @@ -462,19 +462,19 @@ where status, ] = scratch[..] else { - vortex_bail!(AssertionFailed: "OnPair window resolution returned no bounds"); + vortex_bail!("OnPair window resolution returned no bounds"); }; if status != 0 { - vortex_bail!(OutOfBounds: "OnPair code out of dictionary range"); + vortex_bail!("OnPair code out of dictionary range"); } let heap_size = usize::try_from(chunk_total)?; vortex_ensure!( token_start <= token_end, - InvalidArgument: "OnPair codes_offsets must be nondecreasing" + "OnPair codes_offsets must be nondecreasing" ); vortex_ensure!( token_end <= num_tokens_u64, - InvalidArgument: "OnPair codes_offsets end {token_end} exceeds codes len {num_tokens_u64}" + "OnPair codes_offsets end {token_end} exceeds codes len {num_tokens_u64}" ); if token_start == token_end { // No codes in the window (e.g. a slice covering only null rows). @@ -486,12 +486,12 @@ where let byte_end = usize::try_from(byte_end)?; vortex_ensure!( byte_start <= byte_end && byte_end <= heap_size, - OutOfBounds: "OnPair window bounds [{byte_start}, {byte_end}) exceed decoded heap size {heap_size}" + "OnPair window bounds [{byte_start}, {byte_end}) exceed decoded heap size {heap_size}" ); let total_size = byte_end - byte_start; // A conformant dictionary has no zero-length tokens, so a non-empty code window decodes to at // least one byte. - vortex_ensure!(total_size > 0, Serde: "OnPair has codes but decodes to zero bytes"); + vortex_ensure!(total_size > 0, "OnPair has codes but decodes to zero bytes"); // Decode only batches intersecting the visible token window. The kernel's drain gates 16-byte // stores on `out_start % 16` relative to the buffer base, so the base must be 16-aligned. @@ -643,7 +643,7 @@ async fn ensure_zero_lengths( .await? .into_primitive(); let total = sum_lengths(&lengths)?; - vortex_ensure_eq!(total, 0, Serde: "OnPair records decoded bytes but has no codes"); + vortex_ensure_eq!(total, 0, "OnPair records decoded bytes but has no codes"); Ok(()) } @@ -656,7 +656,7 @@ fn sum_lengths(lengths: &PrimitiveArray) -> VortexResult { for &length in lengths.as_slice::

() { acc = acc .checked_add(AsPrimitive::::as_(length)) - .ok_or_else(|| vortex_err!(Overflow: "OnPair decoded size overflow"))?; + .ok_or_else(|| vortex_err!("OnPair decoded size overflow"))?; } Ok(acc) }) @@ -717,7 +717,7 @@ mod tests { let onpair = onpair_compress(&varbin, DEFAULT_CONFIG, ctx.execution_ctx())?; vortex_ensure!( onpair.as_opt::().is_some(), - MismatchedTypes: "expected OnPair array, got {}", + "expected OnPair array, got {}", onpair.encoding_id() ); Ok(onpair) @@ -1031,7 +1031,7 @@ mod tests { &mut cuda_ctx, )? .try_downcast::() - .map_err(|array| vortex_err!(MismatchedTypes: "expected OnPair array, got {}", array.encoding_id()))?; + .map_err(|array| vortex_err!("expected OnPair array, got {}", array.encoding_id()))?; let output = decode_onpair_varbin(onpair, &mut cuda_ctx).await?; assert_eq!(output.dtype, DType::Utf8(Nullability::NonNullable)); diff --git a/vortex-cuda/src/kernel/encodings/runend.rs b/vortex-cuda/src/kernel/encodings/runend.rs index c1113d98299..5519e3de79c 100644 --- a/vortex-cuda/src/kernel/encodings/runend.rs +++ b/vortex-cuda/src/kernel/encodings/runend.rs @@ -55,11 +55,11 @@ impl CudaExecute for RunEndExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = Self::try_specialize(array) - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected RunEndArray"))?; + let array = + Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected RunEndArray"))?; if !array.dtype().is_primitive() { - vortex_bail!(NotImplemented: "RunEndExecutor only supports primitive types") + vortex_bail!("RunEndExecutor only supports primitive types") } let offset = array.offset(); @@ -103,10 +103,10 @@ async fn decode_runend_typed VortexResult { let num_runs = ends.len(); - vortex_ensure!(num_runs > 0, InvalidArgument: "run-end array must have at least one run"); + vortex_ensure!(num_runs > 0, "run-end array must have at least one run"); vortex_ensure!( output_len > 0, - InvalidArgument: "run-end output length must be greater than zero" + "run-end output length must be greater than zero" ); let PrimitiveDataParts { @@ -402,7 +402,7 @@ mod tests { .execute(runend_array.clone().into_array(), &mut cuda_ctx) .await?; let Validity::Array(validity) = gpu_result.clone().into_primitive().validity()? else { - vortex_bail!(InvalidArgument: "expected expanded validity bitmap"); + vortex_bail!("expected expanded validity bitmap"); }; let bits = &validity.buffer_handles()[0]; let logical_bytes = runend_array.len().div_ceil(8); diff --git a/vortex-cuda/src/kernel/encodings/sequence.rs b/vortex-cuda/src/kernel/encodings/sequence.rs index 2a018dcf3da..86bf56107d4 100644 --- a/vortex-cuda/src/kernel/encodings/sequence.rs +++ b/vortex-cuda/src/kernel/encodings/sequence.rs @@ -37,9 +37,9 @@ impl CudaExecute for SequenceExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = array.try_downcast::().map_err( - |_| vortex_err!(MismatchedTypes: "SequenceExecutor can only accept SequenceArray"), - )?; + let array = array + .try_downcast::() + .map_err(|_| vortex_err!("SequenceExecutor can only accept SequenceArray"))?; let len = array.len(); let nullability = array.dtype().nullability(); diff --git a/vortex-cuda/src/kernel/encodings/zigzag.rs b/vortex-cuda/src/kernel/encodings/zigzag.rs index 38af97f738a..33b22bdc29f 100644 --- a/vortex-cuda/src/kernel/encodings/zigzag.rs +++ b/vortex-cuda/src/kernel/encodings/zigzag.rs @@ -49,8 +49,8 @@ impl CudaExecute for ZigZagExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let array = Self::try_specialize(array) - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected ZigZagArray"))?; + let array = + Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected ZigZagArray"))?; // The encoded array is unsigned, we decode to signed of the same width. let encoded_ptype = array.encoded().dtype().as_ptype(); @@ -58,7 +58,7 @@ impl CudaExecute for ZigZagExecutor { vortex_ensure_eq!( output_ptype, encoded_ptype.to_signed(), - MismatchedTypes: "ZigZag output type must be the signed equivalent of the encoded type" + "ZigZag output type must be the signed equivalent of the encoded type" ); match_each_unsigned_integer_ptype!(encoded_ptype, |U| { @@ -76,7 +76,7 @@ where U: NativePType + DeviceRepr + Send + Sync + 'static, { let array_len = array.encoded().len(); - vortex_ensure!(array_len > 0, InvalidArgument: "ZigZag array must not be empty"); + vortex_ensure!(array_len > 0, "ZigZag array must not be empty"); // Execute child and copy to device let canonical = array.encoded().clone().execute_cuda(ctx).await?; @@ -110,7 +110,7 @@ where let mut output = ctx.device_alloc::(array_len)?; ctx.stream() .memcpy_dtod(&input_view, &mut output) - .map_err(|err| vortex_err!(Io: "Failed to copy shared ZigZag input: {err}"))?; + .map_err(|err| vortex_err!("Failed to copy shared ZigZag input: {err}"))?; ctx.launch_kernel(&cuda_function, array_len, |args| { args.arg(&mut output).arg(&array_len_u64); })?; diff --git a/vortex-cuda/src/kernel/encodings/zstd.rs b/vortex-cuda/src/kernel/encodings/zstd.rs index 3df0b11e129..0266fd573aa 100644 --- a/vortex-cuda/src/kernel/encodings/zstd.rs +++ b/vortex-cuda/src/kernel/encodings/zstd.rs @@ -109,7 +109,7 @@ pub async fn zstd_kernel_prepare( // Temporary internal buffer size for nvCOMP ZSTD decompression. let nvcomp_temp_buffer_size = nvcomp_zstd::get_decompress_temp_size(num_frames, output_size_max, output_size_total) - .map_err(|e| vortex_err!(Io: "nvcomp get_decompress_temp_size failed: {}", e))?; + .map_err(|e| vortex_err!("nvcomp get_decompress_temp_size failed: {}", e))?; // Async copy frames to the device. let frame_futs = frames @@ -200,8 +200,7 @@ impl CudaExecute for ZstdExecutor { array: ArrayRef, ctx: &mut CudaExecutionCtx, ) -> VortexResult { - let zstd = Self::try_specialize(array) - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected ZstdArray"))?; + let zstd = Self::try_specialize(array).ok_or_else(|| vortex_err!("Expected ZstdArray"))?; match zstd.dtype() { DType::Binary(_) | DType::Utf8(_) => decode_zstd(zstd, ctx).await, @@ -232,7 +231,7 @@ async fn decode_zstd(array: ZstdArray, ctx: &mut CudaExecutionCtx) -> VortexResu // nvCOMP doesn't support ZSTD dictionaries. if dictionary.is_some() { - return Err(vortex_err!(InvalidArgument: "ZSTD dictionary not supported on GPU")); + return Err(vortex_err!("ZSTD dictionary not supported on GPU")); } if frames.is_empty() { @@ -295,7 +294,7 @@ async fn decode_zstd(array: ZstdArray, ctx: &mut CudaExecutionCtx) -> VortexResu device_statuses_ptr as _, stream.cu_stream().cast(), ) - .map_err(|e| vortex_err!(Io: "nvcomp decompress_async failed: {}", e)) + .map_err(|e| vortex_err!("nvcomp decompress_async failed: {}", e)) } })?; drop(frame_ptr_records); @@ -345,7 +344,7 @@ async fn decode_zstd(array: ZstdArray, ctx: &mut CudaExecutionCtx) -> VortexResu })) } _ => { - vortex_bail!(NotImplemented: "CUDA ZSTD decompression does not yet support arrays with nulls") + vortex_bail!("CUDA ZSTD decompression does not yet support arrays with nulls") } } } diff --git a/vortex-cuda/src/kernel/encodings/zstd_buffers.rs b/vortex-cuda/src/kernel/encodings/zstd_buffers.rs index 7b7cc2e37b3..2ea33dff00b 100644 --- a/vortex-cuda/src/kernel/encodings/zstd_buffers.rs +++ b/vortex-cuda/src/kernel/encodings/zstd_buffers.rs @@ -43,7 +43,7 @@ impl CudaExecute for ZstdBuffersExecutor { ) -> VortexResult { let zstd_buffers = array .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "expected zstd buffers array"))?; + .map_err(|_| vortex_err!("expected zstd buffers array"))?; decode_zstd_buffers(zstd_buffers, ctx).await } } @@ -65,7 +65,7 @@ async fn decode_zstd_buffers( plan.output_size_max(), plan.output_size_total(), ) - .map_err(|e| vortex_err!(Io: "nvcomp get_decompress_temp_size failed: {}", e))?; + .map_err(|e| vortex_err!("nvcomp get_decompress_temp_size failed: {}", e))?; let device_frame_handles = move_frames_to_device(compressed_buffers, ctx).await?; let mut device_output = ctx.device_alloc::(plan.output_size_total())?; @@ -138,7 +138,7 @@ async fn decode_zstd_buffers( device_statuses_ptr as _, stream.cu_stream().cast(), ) - .map_err(|e| vortex_err!(Io: "nvcomp decompress_async failed: {}", e)) + .map_err(|e| vortex_err!("nvcomp decompress_async failed: {}", e)) } })?; drop(frame_ptr_records); @@ -200,14 +200,14 @@ async fn validate_decompress_results( { if status != sys::nvcompStatus_t_nvcompSuccess { return Err(vortex_err!( - Io: "nvcomp chunk {} failed with status {}", + "nvcomp chunk {} failed with status {}", idx, status )); } if actual != expected { return Err(vortex_err!( - MismatchedTypes: "nvcomp chunk {} decompressed size mismatch: expected {}, got {}", + "nvcomp chunk {} decompressed size mismatch: expected {}, got {}", idx, expected, actual diff --git a/vortex-cuda/src/kernel/filter/mod.rs b/vortex-cuda/src/kernel/filter/mod.rs index 973ca5d3f3b..1c925fa9526 100644 --- a/vortex-cuda/src/kernel/filter/mod.rs +++ b/vortex-cuda/src/kernel/filter/mod.rs @@ -52,7 +52,7 @@ impl CudaExecute for FilterExecutor { ) -> VortexResult { let filter_array = array .try_downcast::() - .map_err(|_| vortex_err!(InvalidArgument: "Expected FilterArray"))?; + .map_err(|_| vortex_err!("Expected FilterArray"))?; let child = filter_array.child().clone(); let mask = filter_array.data().filter_mask().clone(); @@ -84,7 +84,7 @@ impl CudaExecute for FilterExecutor { filter_varbinview(varbinview, m, ctx).await } c => { - vortex_bail!(NotImplemented: "CUDA filter kernel is not implemented for {}", c.dtype()) + vortex_bail!("CUDA filter kernel is not implemented for {}", c.dtype()) } } } @@ -109,7 +109,7 @@ async fn filter_sized(temp_bytes.max(1))?; @@ -124,7 +124,7 @@ async fn filter_sized() - .ok_or_else(|| vortex_err!(InvalidArgument: "Expected CudaDeviceBuffer for input, was {d_input:?}",))?; + .ok_or_else(|| vortex_err!("Expected CudaDeviceBuffer for input, was {d_input:?}",))?; let d_input_view = d_input_cuda.as_view::(); let (d_input_ptr, record_d_input) = d_input_view.device_ptr(stream); @@ -133,9 +133,7 @@ async fn filter_sized() - .ok_or_else( - || vortex_err!(InvalidArgument: "Expected CudaDeviceBuffer for packed flags"), - )?; + .ok_or_else(|| vortex_err!("Expected CudaDeviceBuffer for packed flags"))?; let d_packed_view = d_packed_cuda.as_view::(); let (d_packed_ptr, record_d_packed) = d_packed_view.device_ptr(stream); @@ -156,7 +154,7 @@ async fn filter_sized LaunchStrategyExt for S { let before = stream .record_event(Some(flags)) - .map_err(|e| vortex_err!(Io: "record_event: {e}"))?; + .map_err(|e| vortex_err!("record_event: {e}"))?; func()?; let after = stream .record_event(Some(flags)) - .map_err(|e| vortex_err!(Io: "record_event: {e}"))?; + .map_err(|e| vortex_err!("record_event: {e}"))?; self.on_complete( &CudaKernelEvents { @@ -183,10 +183,10 @@ pub(crate) fn launch_cuda_kernel_with_config( unsafe { launch_builder .launch(config) - .map_err(|e| vortex_err!(Io: "Failed to launch kernel: {}", e)) + .map_err(|e| vortex_err!("Failed to launch kernel: {}", e)) .and_then(|events| { events - .ok_or_else(|| vortex_err!(AssertionFailed: "CUDA events not recorded")) + .ok_or_else(|| vortex_err!("CUDA events not recorded")) .map(|(before_launch, after_launch)| CudaKernelEvents { before_launch, after_launch, @@ -246,7 +246,7 @@ impl KernelLoader { // Load the CUDA function from the compiled module. module .load_function(&kernel_name) - .map_err(|e| vortex_err!(Io: "Failed to load kernel function '{}': {}", kernel_name, e)) + .map_err(|e| vortex_err!("Failed to load kernel function '{}': {}", kernel_name, e)) } /// Loads a CUDA module from a fatbin embedded in the binary. @@ -254,12 +254,12 @@ impl KernelLoader { module_name: &str, cuda_context: &Arc, ) -> VortexResult> { - let fatbin = embedded_kernels::embedded_kernel(module_name).ok_or_else( - || vortex_err!(NotFound: "CUDA module {module_name} was not embedded at build time"), - )?; + let fatbin = embedded_kernels::embedded_kernel(module_name).ok_or_else(|| { + vortex_err!("CUDA module {module_name} was not embedded at build time") + })?; cuda_context .load_module(Ptx::from_binary(fatbin.to_vec())) - .map_err(|e| vortex_err!(Io: "Failed to load embedded CUDA module {module_name}: {e}")) + .map_err(|e| vortex_err!("Failed to load embedded CUDA module {module_name}: {e}")) } } diff --git a/vortex-cuda/src/kernel/patches/mod.rs b/vortex-cuda/src/kernel/patches/mod.rs index d5f4c8c6aa9..101d3c8ff7f 100644 --- a/vortex-cuda/src/kernel/patches/mod.rs +++ b/vortex-cuda/src/kernel/patches/mod.rs @@ -51,7 +51,7 @@ pub(crate) fn ptype_to_chunk_offset_type(ptype: PType) -> VortexResult Ok(ChunkOffsetType_CO_U16), PType::U32 => Ok(ChunkOffsetType_CO_U32), PType::U64 => Ok(ChunkOffsetType_CO_U64), - _ => vortex_bail!(InvalidArgument: "Invalid PType for chunk_offsets: {:?}", ptype), + _ => vortex_bail!("Invalid PType for chunk_offsets: {:?}", ptype), } } diff --git a/vortex-cuda/src/kernel/patches/types.rs b/vortex-cuda/src/kernel/patches/types.rs index 80c5611e4bd..77c9e15814e 100644 --- a/vortex-cuda/src/kernel/patches/types.rs +++ b/vortex-cuda/src/kernel/patches/types.rs @@ -58,7 +58,7 @@ pub(crate) async fn load_device_patches( let offset_within_chunk = patches.offset_within_chunk().unwrap_or_default(); // Get or compute chunk_offsets let Some(co) = patches.chunk_offsets() else { - vortex_bail!(NotImplemented: "cannot load CUDA patches without chunk_offsets") + vortex_bail!("cannot load CUDA patches without chunk_offsets") }; let (chunk_offsets, chunk_offset_ptype, n_chunks) = { diff --git a/vortex-cuda/src/kernel/slice/mod.rs b/vortex-cuda/src/kernel/slice/mod.rs index 542fa46f500..5bf5a485e08 100644 --- a/vortex-cuda/src/kernel/slice/mod.rs +++ b/vortex-cuda/src/kernel/slice/mod.rs @@ -29,7 +29,7 @@ impl CudaExecute for SliceExecutor { ) -> VortexResult { let slice_array = array.try_downcast::().map_err(|array| { vortex_err!( - InvalidArgument: "SliceExecutor requires input of SliceArray, was {}", + "SliceExecutor requires input of SliceArray, was {}", array.encoding_id() ) })?; @@ -62,7 +62,7 @@ impl CudaExecute for SliceExecutor { .into_array() .slice(range)? .execute::(ctx.execution_ctx()), - c => vortex_bail!(NotImplemented: "Slice kernel not implemented for {}", c.dtype()), + c => vortex_bail!("Slice kernel not implemented for {}", c.dtype()), } } } diff --git a/vortex-cuda/src/layout.rs b/vortex-cuda/src/layout.rs index b9864da6d5a..a8128963eee 100644 --- a/vortex-cuda/src/layout.rs +++ b/vortex-cuda/src/layout.rs @@ -167,10 +167,10 @@ impl VTable for CudaFlat { metadata: &CudaFlatLayoutMetadata, ) -> VortexResult { if args.segment_ids.len() != 1 { - vortex_bail!(InvalidArgument: "CudaFlatLayout must have exactly one segment ID"); + vortex_bail!("CudaFlatLayout must have exactly one segment ID"); } if args.children.nchildren() != 0 { - vortex_bail!(InvalidArgument: "CudaFlatLayout must not have children"); + vortex_bail!("CudaFlatLayout must not have children"); } let host_buffers = metadata .host_buffers @@ -186,11 +186,11 @@ impl VTable for CudaFlat { } fn child_dtype(_layout: &Layout, idx: usize) -> VortexResult { - vortex_bail!(OutOfBounds: "CudaFlatLayout has no child {idx}"); + vortex_bail!("CudaFlatLayout has no child {idx}"); } fn child_type(_layout: &Layout, _idx: usize) -> LayoutChildType { - vortex_panic!(OutOfBounds: "CudaFlatLayout has no children"); + vortex_panic!("CudaFlatLayout has no children"); } fn new_reader( @@ -435,7 +435,7 @@ impl LayoutStrategy for CudaFlatLayoutStrategy { ) -> VortexResult { let options = self.clone(); let Some(chunk) = stream.next().await else { - vortex_bail!(InvalidArgument: "CudaFlatLayoutStrategy needs a single chunk"); + vortex_bail!("CudaFlatLayoutStrategy needs a single chunk"); }; let (sequence_id, chunk) = chunk?; let row_count = chunk.len() as u64; @@ -499,7 +499,7 @@ impl LayoutStrategy for CudaFlatLayoutStrategy { let segment_id = segment_sink.write(sequence_id, buffers).await?; let None = stream.next().await else { - vortex_bail!(InvalidArgument: "CudaFlatLayoutStrategy received stream with more than a single chunk"); + vortex_bail!("CudaFlatLayoutStrategy received stream with more than a single chunk"); }; let host_buffer_map: HashMap = host_buffers diff --git a/vortex-cuda/src/pinned.rs b/vortex-cuda/src/pinned.rs index 1ec06799924..3ef8362d136 100644 --- a/vortex-cuda/src/pinned.rs +++ b/vortex-cuda/src/pinned.rs @@ -54,24 +54,24 @@ impl PinnedByteBuffer { ) -> VortexResult { vortex_ensure!( capacity < isize::MAX as usize, - Overflow: "pinned host buffer capacity is too large: {capacity}" + "pinned host buffer capacity is too large: {capacity}" ); vortex_ensure!( logical_len <= capacity, - Overflow: "pinned host buffer length {logical_len} exceeds capacity {capacity}" + "pinned host buffer length {logical_len} exceeds capacity {capacity}" ); let event = ctx .new_event(Some(CUevent_flags::CU_EVENT_DISABLE_TIMING)) - .map_err(|e| vortex_err!(Io: "failed to create pinned host buffer event: {e}"))?; + .map_err(|e| vortex_err!("failed to create pinned host buffer event: {e}"))?; // Bind explicitly rather than relying on event creation to bind this worker thread. ctx.bind_to_thread() - .map_err(|e| vortex_err!(Io: "failed to bind pinned host buffer context: {e}"))?; + .map_err(|e| vortex_err!("failed to bind pinned host buffer context: {e}"))?; // Keep file-I/O staging cacheable: cudarc's allocator uses write-combined memory, // which makes CPU reads expensive. let ptr = unsafe { result::malloc_host(capacity, 0) } - .map_err(|e| vortex_err!(Io: "failed to allocate pinned host buffer: {e}"))? + .map_err(|e| vortex_err!("failed to allocate pinned host buffer: {e}"))? .cast::(); - vortex_ensure!(!ptr.is_null(), Io: "CUDA returned a null pinned host buffer"); + vortex_ensure!(!ptr.is_null(), "CUDA returned a null pinned host buffer"); Ok(Self { ptr, capacity, @@ -84,7 +84,7 @@ impl PinnedByteBuffer { pub(crate) fn as_mut_slice(&mut self) -> VortexResult<&mut [u8]> { self.event .synchronize() - .map_err(|e| vortex_err!(Io: "failed to access pinned host buffer: {e}"))?; + .map_err(|e| vortex_err!("failed to access pinned host buffer: {e}"))?; Ok(unsafe { std::slice::from_raw_parts_mut(self.ptr, self.logical_len) }) } @@ -255,7 +255,7 @@ impl PinnedByteBufferPool { } self.ctx .bind_to_thread() - .map_err(|e| vortex_err!(Io: "Failed to bind CUDA context: {e}"))?; + .map_err(|e| vortex_err!("Failed to bind CUDA context: {e}"))?; let mut idx = 0usize; while idx < inflight.len() { if !inflight[idx].buffer.event.is_complete() { @@ -365,27 +365,27 @@ impl PooledPinnedBuffer { ) -> VortexResult<()> { vortex_ensure!( &self.pool.ctx == stream.context(), - InvalidArgument: "pinned buffer and transfer stream must use the same CUDA context" + "pinned buffer and transfer stream must use the same CUDA context" ); let pinned = self.inner.as_mut().vortex_expect("buffer already consumed"); vortex_ensure!( range.start <= range.end && range.end <= pinned.logical_len, - InvalidArgument: "invalid pinned host buffer range {:?} for length {}", + "invalid pinned host buffer range {:?} for length {}", range, pinned.logical_len ); vortex_ensure_eq!( range.len(), destination.len(), - InvalidArgument: "pinned host buffer range length does not match destination length" + "pinned host buffer range length does not match destination length" ); // Chain the old transfer before this stream replaces the completion fence, even for // buffers returned directly to a bucket. Check the wait before creating a source guard: // on failure, preserve the old fence rather than recording over it on this stream. - stream.wait(&pinned.event).map_err( - |error| vortex_err!(Io: "Failed to wait for pinned source transfer: {error}"), - )?; + stream + .wait(&pinned.event) + .map_err(|error| vortex_err!("Failed to wait for pinned source transfer: {error}"))?; let source = PinnedByteBufferView { buffer: pinned, range, @@ -411,10 +411,10 @@ impl PooledPinnedBuffer { let _leaked = ManuallyDrop::new(self.inner.take().vortex_expect("buffer already consumed")); return Err(vortex_err!( - Io: "H2D transfer fence failed: {error}; stream synchronization failed: {sync_error}" + "H2D transfer fence failed: {error}; stream synchronization failed: {sync_error}" )); } - return Err(vortex_err!(Io: "H2D transfer fence failed: {error}")); + return Err(vortex_err!("H2D transfer fence failed: {error}")); } let inner = self.inner.take().vortex_expect("buffer already consumed"); @@ -449,12 +449,11 @@ mod tests { use super::*; fn setup() -> VortexResult<(Arc, VortexCudaStream)> { - let ctx = - CudaContext::new(0).map_err(|e| vortex_err!(Io: "Failed to initialize CUDA: {e}"))?; + let ctx = CudaContext::new(0).map_err(|e| vortex_err!("Failed to initialize CUDA: {e}"))?; let pool = Arc::new(PinnedByteBufferPool::new(Arc::clone(&ctx))); let stream = VortexCudaStream( ctx.new_stream() - .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, ); Ok((pool, stream)) } @@ -513,7 +512,7 @@ mod tests { let mut expected = vec![0xA5u8; 12]; let mut destination = stream .clone_htod(&expected) - .map_err(|e| vortex_err!(Io: "Failed to initialize destination: {e}"))?; + .map_err(|e| vortex_err!("Failed to initialize destination: {e}"))?; let result = pinned.copy_to_device( &stream, start..end, @@ -566,7 +565,7 @@ mod tests { } stream .synchronize() - .map_err(|e| vortex_err!(Io: "Failed to sync stream: {e}"))?; + .map_err(|e| vortex_err!("Failed to sync stream: {e}"))?; let mut reused = pool.get(1024)?; assert_eq!(reused.as_mut_slice().as_ptr(), allocation); @@ -584,7 +583,7 @@ mod tests { stream .context() .new_stream() - .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, ); let second = reused.transfer_to_device(&other_stream)?; let host = second.copy_to_host_sync(Alignment::of::())?; @@ -617,11 +616,11 @@ mod tests { )> { // Other tests synchronize the primary context. Keep the gated DMA independent of them. let ctx = CudaContext::new_non_primary(0, 0) - .map_err(|e| vortex_err!(Io: "Failed to initialize CUDA: {e}"))?; + .map_err(|e| vortex_err!("Failed to initialize CUDA: {e}"))?; let pool = Arc::new(PinnedByteBufferPool::new(Arc::clone(&ctx))); let stream = VortexCudaStream( ctx.new_stream() - .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, ); if !automatic_tracking { // SAFETY: Each destination stays on its allocation stream. The pool fences sources. @@ -630,7 +629,7 @@ mod tests { let other = VortexCudaStream( pool.ctx .new_stream() - .map_err(|error| vortex_err!(AssertionFailed: "{error}"))?, + .map_err(|error| vortex_err!("{error}"))?, ); Ok((pool, stream, other)) } @@ -662,7 +661,7 @@ mod tests { stream .context() .bind_to_thread() - .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; + .map_err(|e| vortex_err!("{e}"))?; unsafe extern "C" fn wait(data: *mut std::ffi::c_void) { // SAFETY: Registration transfers sole ownership of the boxed receiver here. let receiver = unsafe { Box::from_raw(data.cast::>()) }; @@ -676,7 +675,7 @@ mod tests { result::stream::launch_host_function(stream.cu_stream(), wait, data.cast()).map_err( |error| { drop(Box::from_raw(data)); - vortex_err!(Io: "Failed to block test stream: {error}") + vortex_err!("Failed to block test stream: {error}") }, )?; } @@ -716,9 +715,7 @@ mod tests { pinned.as_mut_slice().fill(0x5A); let mut first = stream.device_alloc::(len)?; let mut second = other.device_alloc::(len)?; - pool.ctx - .synchronize() - .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; + pool.ctx.synchronize().map_err(|e| vortex_err!("{e}"))?; // Declare the gate last so unwinding releases it before CUDA allocations are dropped. let gate = block_stream(&stream)?; submit_to_bucket(pinned, &stream, &mut first)?; @@ -726,9 +723,7 @@ mod tests { pinned.copy_to_device(&other, 0..len, &mut second.slice_mut(..))?; assert_source_retained(&pool)?; drop(gate); - other - .synchronize() - .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; + other.synchronize().map_err(|e| vortex_err!("{e}"))?; pool.reclaim_completed()?; assert!(pool.inflight.lock().is_empty()); pool.get(len)?.as_mut_slice().fill(0xA5); @@ -748,7 +743,7 @@ mod tests { let mut first = stream.device_alloc::(len)?; let mut second = other .clone_htod(&vec![0xCCu8; len]) - .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; + .map_err(|e| vortex_err!("{e}"))?; submit_to_bucket(pinned, &stream, &mut first)?; let pinned = pool.get(len)?; // Consumed by wait -> bind_to_thread -> check_err; the error text checks that path. @@ -811,11 +806,11 @@ mod tests { fn rejects_transfer_between_contexts() -> VortexResult<()> { let (pool, _) = setup()?; let context = CudaContext::new_non_primary(0, 0) - .map_err(|e| vortex_err!(Io: "Failed to create context: {e}"))?; + .map_err(|e| vortex_err!("Failed to create context: {e}"))?; let stream = VortexCudaStream( context .new_stream() - .map_err(|e| vortex_err!(Io: "Failed to create stream: {e}"))?, + .map_err(|e| vortex_err!("Failed to create stream: {e}"))?, ); let mut pinned = pool.get(1024)?; pinned.as_mut_slice().fill(0xFF); diff --git a/vortex-cuda/src/pooled_read_at.rs b/vortex-cuda/src/pooled_read_at.rs index 777f5b27914..96b8697090c 100644 --- a/vortex-cuda/src/pooled_read_at.rs +++ b/vortex-cuda/src/pooled_read_at.rs @@ -131,7 +131,7 @@ impl VortexReadAt for PooledObjectStoreReadAt { async move { let end = offset.checked_add(length as u64).ok_or_else(|| { vortex_err!( - Overflow: "Object store read range overflow: offset={}, length={}", + "Object store read range overflow: offset={}, length={}", offset, length ) @@ -170,7 +170,7 @@ impl VortexReadAt for PooledObjectStoreReadAt { let end = filled + bytes.len(); vortex_ensure!( end <= length, - Io: "Object store stream returned more bytes than expected (expected {} bytes, got at least {} bytes, range: {:?})", + "Object store stream returned more bytes than expected (expected {} bytes, got at least {} bytes, range: {:?})", length, end, range @@ -182,7 +182,7 @@ impl VortexReadAt for PooledObjectStoreReadAt { vortex_ensure_eq!( filled, length, - Io: "Object store stream returned too few bytes (range: {:?})", + "Object store stream returned too few bytes (range: {:?})", range ); } @@ -251,9 +251,8 @@ impl VortexReadAt for PooledByteBufferReadAt { let pool = Arc::clone(&self.pool); async move { - let offset = usize::try_from(offset).map_err( - |_| vortex_err!(Overflow: "Byte buffer read offset overflow: offset={}", offset), - )?; + let offset = usize::try_from(offset) + .map_err(|_| vortex_err!("Byte buffer read offset overflow: offset={}", offset))?; let src = &buffer.as_ref()[offset..offset + length]; let mut target = pool.get(length)?; diff --git a/vortex-cuda/src/pooled_read_at/file.rs b/vortex-cuda/src/pooled_read_at/file.rs index 7cab5a5042c..afa8d736f2e 100644 --- a/vortex-cuda/src/pooled_read_at/file.rs +++ b/vortex-cuda/src/pooled_read_at/file.rs @@ -140,7 +140,7 @@ unsafe extern "C" { fn page_size() -> VortexResult { // SAFETY: getpagesize has no preconditions. let page = usize::try_from(unsafe { getpagesize() })?; - vortex_ensure!(page.is_power_of_two(), AssertionFailed: "invalid page size {page}"); + vortex_ensure!(page.is_power_of_two(), "invalid page size {page}"); Ok(page) } @@ -286,7 +286,7 @@ impl MappedFile { .attribute( CUdevice_attribute::CU_DEVICE_ATTRIBUTE_PAGEABLE_MEMORY_ACCESS_USES_HOST_PAGE_TABLES, ) - .map_err(|error| vortex_err!(Io: "Failed to query pageable memory access: {error}"))?; + .map_err(|error| vortex_err!("Failed to query pageable memory access: {error}"))?; if uses_host_page_tables != 1 { return Ok(None); } @@ -350,7 +350,7 @@ impl MappedFile { self.stream .context() .bind_to_thread() - .map_err(|error| vortex_err!(Io: "Failed to bind CUDA context: {error}"))?; + .map_err(|error| vortex_err!("Failed to bind CUDA context: {error}"))?; // The guard records the queued copies as the output's write when this scope ends, // including on error, so frees and readers on other streams wait for them. let (base, write) = output.device_ptr_mut(&self.stream); @@ -377,7 +377,7 @@ impl MappedFile { // SAFETY: The source range is mapped and in bounds, the target covers `pad + length` // bytes, and both share the same offset within 16 bytes, as the kernel requires. unsafe { launch.launch(config) } - .map_err(|error| vortex_err!(Io: "Failed to launch mapped copy: {error}"))?; + .map_err(|error| vortex_err!("Failed to launch mapped copy: {error}"))?; } drop(write); Ok(output) @@ -503,7 +503,7 @@ impl PooledFileReadAt { let permit = Arc::clone(&self.read_slots) .acquire_owned() .await - .map_err(|error| vortex_err!(Io: "file read semaphore closed: {error}"))?; + .map_err(|error| vortex_err!("file read semaphore closed: {error}"))?; self.handle .spawn_blocking(move || { // A started blocking read cannot be cancelled. Keep its permit and buffer owners @@ -543,7 +543,7 @@ impl VortexReadAt for PooledFileReadAt { async move { vortex_ensure!( offset.checked_add(u64::try_from(length)?).is_some(), - Overflow: "file read range overflow: offset={offset}, length={length}" + "file read range overflow: offset={offset}, length={length}" ); if let Some(buffer) = reader.read_mapped(offset, length).await? { return Ok(buffer); diff --git a/vortex-cuda/src/pooled_read_at/file/direct.rs b/vortex-cuda/src/pooled_read_at/file/direct.rs index cecf2cc818c..afe9dc73f63 100644 --- a/vortex-cuda/src/pooled_read_at/file/direct.rs +++ b/vortex-cuda/src/pooled_read_at/file/direct.rs @@ -86,7 +86,7 @@ impl FileReadBackend for DirectFileReadBackend { let address = buffer.as_mut_slice().as_ptr() as usize; vortex_ensure!( address.is_multiple_of(self.constraints.memory_alignment), - InvalidArgument: "pinned buffer address {address:#x} is not aligned to {} bytes", + "pinned buffer address {address:#x} is not aligned to {} bytes", self.constraints.memory_alignment ); @@ -106,7 +106,7 @@ impl FileReadBackend for DirectFileReadBackend { } fn direct_io_range(offset: u64, length: usize, alignment: usize) -> VortexResult { - vortex_ensure!(alignment > 0, InvalidArgument: "direct I/O alignment must be non-zero"); + vortex_ensure!(alignment > 0, "direct I/O alignment must be non-zero"); if length == 0 { return Ok(DirectIoRange { read_offset: offset, @@ -117,18 +117,18 @@ fn direct_io_range(offset: u64, length: usize, alignment: usize) -> VortexResult let alignment_u64 = u64::try_from(alignment)?; let length_u64 = u64::try_from(length)?; - let requested_end = offset.checked_add(length_u64).ok_or_else( - || vortex_err!(Overflow: "direct I/O range overflow: offset={offset}, length={length}"), - )?; + let requested_end = offset.checked_add(length_u64).ok_or_else(|| { + vortex_err!("direct I/O range overflow: offset={offset}, length={length}") + })?; let read_offset = offset - offset % alignment_u64; let read_end = requested_end .checked_next_multiple_of(alignment_u64) - .ok_or_else(|| vortex_err!(Overflow: "direct I/O aligned end overflow"))?; + .ok_or_else(|| vortex_err!("direct I/O aligned end overflow"))?; let read_length = usize::try_from(read_end - read_offset)?; let slice_start = usize::try_from(offset - read_offset)?; - let slice_end = slice_start.checked_add(length).ok_or_else( - || vortex_err!(Overflow: "direct I/O range overflow: offset={offset}, length={length}"), - )?; + let slice_end = slice_start.checked_add(length).ok_or_else(|| { + vortex_err!("direct I/O range overflow: offset={offset}, length={length}") + })?; Ok(DirectIoRange { read_offset, @@ -204,11 +204,11 @@ fn direct_io_constraints(file: &File) -> VortexResult { } vortex_ensure!( memory_alignment.is_power_of_two(), - InvalidArgument: "direct I/O memory alignment must be a power of two, got {memory_alignment}" + "direct I/O memory alignment must be a power of two, got {memory_alignment}" ); vortex_ensure!( offset_alignment.is_power_of_two(), - InvalidArgument: "direct I/O offset alignment must be a power of two, got {offset_alignment}" + "direct I/O offset alignment must be a power of two, got {offset_alignment}" ); Ok(DirectIoConstraints { diff --git a/vortex-cuda/src/pooled_read_at/file/tests.rs b/vortex-cuda/src/pooled_read_at/file/tests.rs index a304a347993..c2a5121c216 100644 --- a/vortex-cuda/src/pooled_read_at/file/tests.rs +++ b/vortex-cuda/src/pooled_read_at/file/tests.rs @@ -75,7 +75,7 @@ impl FileReadBackend for FakeFileReadBackend { self.requests.lock().push((offset, length)); let end = offset .checked_add(u64::try_from(length)?) - .ok_or_else(|| vortex_err!(Overflow: "overflow reached fake backend"))?; + .ok_or_else(|| vortex_err!("overflow reached fake backend"))?; let alignment = if self.padded { 4096 } else { 1 }; let prefix = usize::try_from(offset % alignment as u64)?; let source_len = (prefix + length).next_multiple_of(alignment); @@ -96,9 +96,9 @@ impl FileReadBackend for FakeFileReadBackend { release, finished: completion, }) - .map_err(|_| vortex_err!(Io: "fake read controller dropped"))?; + .map_err(|_| vortex_err!("fake read controller dropped"))?; wait.recv_timeout(WAIT) - .map_err(|error| vortex_err!(Io: "fake read was not released: {error}"))?; + .map_err(|error| vortex_err!("fake read was not released: {error}"))?; Some(finished) } else { None diff --git a/vortex-cuda/src/session.rs b/vortex-cuda/src/session.rs index 10085c162d8..2d4ff54e65f 100644 --- a/vortex-cuda/src/session.rs +++ b/vortex-cuda/src/session.rs @@ -135,14 +135,14 @@ impl CudaSession { // loaded, so catch any unwind here to uphold this constructor's no-panic contract. match catch_unwind(AssertUnwindSafe(|| -> VortexResult { let context = CudaContext::new(0) - .map_err(|err| vortex_err!(Io: "failed to initialize CUDA device 0: {err}"))?; + .map_err(|err| vortex_err!("failed to initialize CUDA device 0: {err}"))?; let this = Self::new(context); initialize_cuda(&this); Ok(this) })) { Ok(result) => result, Err(_) => Err(vortex_err!( - Io: "failed to initialize CUDA: the driver library is unavailable" + "failed to initialize CUDA: the driver library is unavailable" )), } } diff --git a/vortex-cuda/src/stream.rs b/vortex-cuda/src/stream.rs index 1f1396f2185..a6515b1f8db 100644 --- a/vortex-cuda/src/stream.rs +++ b/vortex-cuda/src/stream.rs @@ -57,7 +57,7 @@ impl VortexCudaStream { // SAFETY: No safety guarantees for allocations on the GPU. unsafe { self.alloc::(len) - .map_err(|e| vortex_err!(Io: "Failed to allocate device memory: {}", e)) + .map_err(|e| vortex_err!("Failed to allocate device memory: {}", e)) } } @@ -101,7 +101,7 @@ impl VortexCudaStream { let mut values = cuda_slice.slice_mut(..host_slice.len()); self.memcpy_htod(host_slice, &mut values) - .map_err(|e| vortex_err!(Io: "Failed to schedule H2D copy: {}", e))?; + .map_err(|e| vortex_err!("Failed to schedule H2D copy: {}", e))?; zero_padding(self, &mut cuda_slice, host_slice.len())?; @@ -143,7 +143,7 @@ impl VortexCudaStream { let mut values = cuda_slice.slice_mut(..data.len()); self.memcpy_htod(data, &mut values) - .map_err(|e| vortex_err!(Io: "Failed to schedule H2D copy: {}", e))?; + .map_err(|e| vortex_err!("Failed to schedule H2D copy: {}", e))?; zero_padding(self, &mut cuda_slice, data.len())?; @@ -161,7 +161,7 @@ fn padded_device_allocation_len(byte_count: usize) -> VortexResult { let element_size = size_of::(); vortex_ensure!( element_size != 0, - InvalidArgument: "cannot copy zero-sized values to CUDA device" + "cannot copy zero-sized values to CUDA device" ); let min_allocation_bytes = byte_count.next_multiple_of(CUDF_VALIDITY_BUFFER_PADDING); Ok(min_allocation_bytes.div_ceil(element_size)) @@ -184,7 +184,7 @@ pub(crate) fn zero_padding( let mut padding = cuda_slice.slice_mut(initialized_count..); stream .memset_zeros(&mut padding) - .map_err(|e| vortex_err!(Io: "Failed to zero device buffer padding: {}", e)) + .map_err(|e| vortex_err!("Failed to zero device buffer padding: {}", e)) } /// Registers a callback and asynchronously waits for its completion. @@ -208,7 +208,7 @@ pub(crate) async fn await_stream_callback(stream: &CudaStream) -> VortexResult<( rx.recv() .await - .map_err(|e| vortex_err!(Io: "CUDA stream callback channel closed unexpectedly: {}", e)) + .map_err(|e| vortex_err!("CUDA stream callback channel closed unexpectedly: {}", e)) } /// Registers a host function callback on the stream. @@ -229,7 +229,7 @@ fn register_stream_callback(stream: &CudaStream) -> VortexResult VortexResult VortexResult<()> { - let context = CudaContext::new(0) - .map_err(|e| vortex_err!(Io: "Failed to create CUDA context: {e}"))?; + let context = + CudaContext::new(0).map_err(|e| vortex_err!("Failed to create CUDA context: {e}"))?; let pool = VortexCudaStreamPool::new(context, 3); assert_eq!(pool.max_capacity(), 3); @@ -118,8 +118,8 @@ mod tests { #[crate::test] fn round_robin_reuse() -> VortexResult<()> { - let context = CudaContext::new(0) - .map_err(|e| vortex_err!(Io: "Failed to create CUDA context: {e}"))?; + let context = + CudaContext::new(0).map_err(|e| vortex_err!("Failed to create CUDA context: {e}"))?; let pool = VortexCudaStreamPool::new(context, 3); let streams = (0..pool.max_capacity()) .map(|_| pool.stream()) @@ -143,8 +143,8 @@ mod tests { #[crate::test] fn concurrent_initialization_respects_capacity() -> VortexResult<()> { - let context = CudaContext::new(0) - .map_err(|e| vortex_err!(Io: "Failed to create CUDA context: {e}"))?; + let context = + CudaContext::new(0).map_err(|e| vortex_err!("Failed to create CUDA context: {e}"))?; for capacity in [1, 4] { let pool = VortexCudaStreamPool::new(Arc::clone(&context), capacity); let barrier = Barrier::new(32); diff --git a/vortex-datafusion/examples/vortex_table.rs b/vortex-datafusion/examples/vortex_table.rs index baedac2f61b..90a7ba5e1e4 100644 --- a/vortex-datafusion/examples/vortex_table.rs +++ b/vortex-datafusion/examples/vortex_table.rs @@ -67,7 +67,7 @@ async fn main() -> anyhow::Result<()> { let table_url = ListingTableUrl::parse( filepath .to_str() - .ok_or_else(|| vortex_err!(InvalidArgument: "Path is not valid UTF-8"))?, + .ok_or_else(|| vortex_err!("Path is not valid UTF-8"))?, )?; let config = ListingTableConfig::new(table_url) .with_listing_options(ListingOptions::new(format)) diff --git a/vortex-datafusion/src/convert/scalars.rs b/vortex-datafusion/src/convert/scalars.rs index 49244291223..08d403af301 100644 --- a/vortex-datafusion/src/convert/scalars.rs +++ b/vortex-datafusion/src/convert/scalars.rs @@ -66,7 +66,7 @@ impl TryToDataFusion for Scalar { Some(v32) => ScalarValue::Decimal32(Some(v32), precision, scale), None => { vortex_bail!( - InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", + "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -78,7 +78,7 @@ impl TryToDataFusion for Scalar { Some(v64) => ScalarValue::Decimal64(Some(v64), precision, scale), None => { vortex_bail!( - InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", + "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -90,7 +90,7 @@ impl TryToDataFusion for Scalar { Some(v128) => ScalarValue::Decimal128(Some(v128), precision, scale), None => { vortex_bail!( - InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", + "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -104,7 +104,7 @@ impl TryToDataFusion for Scalar { } None => { vortex_bail!( - InvalidArgument: "invalid ScalarValue {value} for decimal with precision {precision}", + "invalid ScalarValue {value} for decimal with precision {precision}", ) } }, @@ -122,20 +122,20 @@ impl TryToDataFusion for Scalar { .map(|b| Vec::::from(b.into_bytes())), ), dtype @ DType::List(..) => vortex_bail!( - MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), dtype @ DType::FixedSizeList(..) => vortex_bail!( - MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), dtype @ DType::Map(..) => vortex_bail!( - MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), DType::Struct(..) => struct_to_df(self)?, dtype @ DType::Union(..) => vortex_bail!( - MismatchedTypes: "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" + "cannot convert Vortex scalar dtype {dtype} to DataFusion ScalarValue: unsupported scalar type" ), DType::Variant(_) => { - vortex_bail!(NotImplemented: "Variant scalars aren't supported with DF") + vortex_bail!("Variant scalars aren't supported with DF") } DType::Extension(ext) => { let storage_scalar = self.as_extension().to_storage_scalar(); @@ -318,7 +318,7 @@ pub fn scalar_from_df(value: &ScalarValue, session: &VortexSession) -> VortexRes ScalarValue::Dictionary(_, v) => scalar_from_df(v.as_ref(), session)?, ScalarValue::Struct(array) => struct_from_df(array, session), ScalarValue::RunEndEncoded(_, _, v) => scalar_from_df(v.as_ref(), session)?, - _ => vortex_bail!(MismatchedTypes: "Can't convert {value:?} value to a Vortex scalar"), + _ => vortex_bail!("Can't convert {value:?} value to a Vortex scalar"), }) } @@ -338,11 +338,12 @@ fn struct_to_df(scalar: &Scalar) -> VortexResult { } else { scalar .field_by_idx(idx) - .ok_or_else(|| vortex_err!(NotFound: "missing struct field {name}"))? + .ok_or_else(|| vortex_err!("missing struct field {name}"))? }; - let array = child.try_to_df()?.to_array().map_err( - |e| vortex_err!(InvalidArgument: "failed to build struct field array: {e}"), - )?; + let array = child + .try_to_df()? + .to_array() + .map_err(|e| vortex_err!("failed to build struct field array: {e}"))?; Ok(( Field::new(name.as_ref(), array.data_type().clone(), nullable), array, @@ -357,7 +358,7 @@ fn struct_to_df(scalar: &Scalar) -> VortexResult { StructArray::new_null(fields, 1) } else { StructArray::try_new(fields, arrays, None) - .map_err(|e| vortex_err!(InvalidArgument: "failed to build struct scalar array: {e}"))? + .map_err(|e| vortex_err!("failed to build struct scalar array: {e}"))? }; Ok(ScalarValue::Struct(Arc::new(struct_array))) } diff --git a/vortex-datafusion/src/convert/stats/tests.rs b/vortex-datafusion/src/convert/stats/tests.rs index 58acf2bfc30..e2e7e0fc67f 100644 --- a/vortex-datafusion/src/convert/stats/tests.rs +++ b/vortex-datafusion/src/convert/stats/tests.rs @@ -18,7 +18,7 @@ fn bounds_stats(value: &DFScalarValue) -> VortexResult<(StatsSet, DType)> { let value = scalar .value() .cloned() - .ok_or_else(|| vortex_err!(AssertionFailed: "expected non-null bounds"))?; + .ok_or_else(|| vortex_err!("expected non-null bounds"))?; let mut stats = StatsSet::of(Stat::Min, VortexPrecision::exact(value.clone())); stats.set(Stat::Max, VortexPrecision::exact(value)); stats.set(Stat::NullCount, VortexPrecision::exact(0u64)); diff --git a/vortex-datafusion/src/persistent/format.rs b/vortex-datafusion/src/persistent/format.rs index d33983291a5..7e69693400b 100644 --- a/vortex-datafusion/src/persistent/format.rs +++ b/vortex-datafusion/src/persistent/format.rs @@ -652,7 +652,7 @@ impl FileFormat for VortexFormat { return Ok(Statistics { num_rows: DFPrecision::Exact( usize::try_from(row_count) - .map_err(|_| vortex_err!(Overflow: "Row count overflow")) + .map_err(|_| vortex_err!("Row count overflow")) .vortex_expect("Row count overflow"), ), total_byte_size: DFPrecision::Absent, @@ -713,7 +713,7 @@ impl FileFormat for VortexFormat { Ok(Statistics { num_rows: DFPrecision::Exact( usize::try_from(row_count) - .map_err(|_| vortex_err!(Overflow: "Row count overflow")) + .map_err(|_| vortex_err!("Row count overflow")) .vortex_expect("Row count overflow"), ), total_byte_size, @@ -891,7 +891,7 @@ mod tests { let value = scalar .value() .cloned() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected non-null scalar"))?; + .ok_or_else(|| vortex_err!("expected non-null scalar"))?; let target_dtype = expected.data_type(); let (value, expected) = if exact { (Precision::Exact(value), DFPrecision::Exact(expected)) @@ -927,7 +927,7 @@ mod tests { let value = scalar .value() .cloned() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected non-null scalar"))?; + .ok_or_else(|| vortex_err!("expected non-null scalar"))?; assert_eq!( scalar_stat_to_df(stat, Precision::Exact(value), scalar.dtype(), &target_dtype), DFPrecision::Absent diff --git a/vortex-datafusion/src/v2/source.rs b/vortex-datafusion/src/v2/source.rs index 04807bb9d34..ae7902b3e30 100644 --- a/vortex-datafusion/src/v2/source.rs +++ b/vortex-datafusion/src/v2/source.rs @@ -242,7 +242,7 @@ impl VortexDataSourceBuilder { } let DType::Struct(fields, ..) = projection.return_dtype(self.data_source.dtype())? else { - vortex_bail!(MismatchedTypes: "Projection does not evaluate to a struct"); + vortex_bail!("Projection does not evaluate to a struct"); }; // We now compute initial statistics. diff --git a/vortex-duckdb/src/convert/dtype.rs b/vortex-duckdb/src/convert/dtype.rs index b911e168e03..28b6a841b4b 100644 --- a/vortex-duckdb/src/convert/dtype.rs +++ b/vortex-duckdb/src/convert/dtype.rs @@ -89,7 +89,7 @@ impl FromLogicalType for DType { ) -> VortexResult { Ok(match logical_type.as_type_id() { DUCKDB_TYPE::DUCKDB_TYPE_INVALID => { - vortex_bail!(InvalidArgument: "invalid duckdb type") + vortex_bail!("invalid duckdb type") } DUCKDB_TYPE::DUCKDB_TYPE_SQLNULL => DType::Null, DUCKDB_TYPE::DUCKDB_TYPE_BOOLEAN => DType::Bool(nullability), @@ -102,10 +102,10 @@ impl FromLogicalType for DType { DUCKDB_TYPE::DUCKDB_TYPE_UINTEGER => DType::Primitive(U32, nullability), DUCKDB_TYPE::DUCKDB_TYPE_UBIGINT => DType::Primitive(U64, nullability), DUCKDB_TYPE::DUCKDB_TYPE_HUGEINT => { - vortex_bail!(NotImplemented: "I128 is not in Vortex type system") + vortex_bail!("I128 is not in Vortex type system") } DUCKDB_TYPE::DUCKDB_TYPE_UHUGEINT => { - vortex_bail!(NotImplemented: "U128 is not in Vortex type system") + vortex_bail!("U128 is not in Vortex type system") } DUCKDB_TYPE::DUCKDB_TYPE_FLOAT => DType::Primitive(F32, nullability), DUCKDB_TYPE::DUCKDB_TYPE_DOUBLE => DType::Primitive(F64, nullability), @@ -212,7 +212,7 @@ impl FromLogicalType for DType { | DUCKDB_TYPE::DUCKDB_TYPE_BIGNUM | DUCKDB_TYPE::DUCKDB_TYPE_STRING_LITERAL | DUCKDB_TYPE::DUCKDB_TYPE_INTEGER_LITERAL) => { - vortex_bail!(InvalidArgument: "{other:?} -> DType conversion is not supported") + vortex_bail!("{other:?} -> DType conversion is not supported") } }) } @@ -271,9 +271,9 @@ impl TryFrom<&DType> for LogicalType { return LogicalType::map_type(&key_logical_type, &value_logical_type); } // TODO(connor): Union - DType::Union(..) => vortex_bail!(NotImplemented: "Vortex Union isn't supported"), + DType::Union(..) => vortex_bail!("Vortex Union isn't supported"), DType::Variant(_) => { - vortex_bail!(NotImplemented: "Vortex Variant array aren't supported") + vortex_bail!("Vortex Variant array aren't supported") } DType::Extension(ext_dtype) => { // Handle first-party extension types that have DuckDB equivalents. @@ -298,7 +298,7 @@ impl TryFrom<&DType> for LogicalType { return LogicalType::geometry_type(spatial_metadata.crs.as_deref()); } - vortex_bail!(InvalidArgument: "Unsupported extension type \"{}\"", ext_dtype.id()); + vortex_bail!("Unsupported extension type \"{}\"", ext_dtype.id()); } }; @@ -321,14 +321,14 @@ fn temporal_to_duckdb(temporal: TemporalMetadata) -> VortexResult { TimeUnit::Microseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIMESTAMP, TimeUnit::Milliseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIMESTAMP_MS, TimeUnit::Seconds => DUCKDB_TYPE::DUCKDB_TYPE_TIMESTAMP_S, - _ => vortex_bail!(InvalidArgument: "Invalid TimeUnit {} for timestamp", unit), + _ => vortex_bail!("Invalid TimeUnit {} for timestamp", unit), }, // TIMESTAMP_TZ's timezone is a display unit, time is stored in UTC // microseconds TemporalMetadata::Timestamp(unit, Some(_)) => { if unit != &TimeUnit::Microseconds { vortex_bail!( - InvalidArgument: "Invalid TimeUnit {} for timestamp_tz, must be Microseconds", + "Invalid TimeUnit {} for timestamp_tz, must be Microseconds", unit ); } @@ -336,12 +336,12 @@ fn temporal_to_duckdb(temporal: TemporalMetadata) -> VortexResult { } TemporalMetadata::Date(unit) => match unit { TimeUnit::Days => DUCKDB_TYPE::DUCKDB_TYPE_DATE, - _ => vortex_bail!(InvalidArgument: "Invalid TimeUnit {} for date", unit), + _ => vortex_bail!("Invalid TimeUnit {} for date", unit), }, TemporalMetadata::Time(unit) => match unit { TimeUnit::Microseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIME, TimeUnit::Nanoseconds => DUCKDB_TYPE::DUCKDB_TYPE_TIME_NS, - _ => vortex_bail!(InvalidArgument: "Invalid TimeUnit {} for time", unit), + _ => vortex_bail!("Invalid TimeUnit {} for time", unit), }, }; @@ -371,11 +371,10 @@ impl TryFrom<&StructFields> for LogicalType { .iter() .map(|field_name| { if name_set.replace(field_name.as_ref()).is_some() { - vortex_bail!(InvalidArgument: "Duplicate field '{field_name}'"); + vortex_bail!("Duplicate field '{field_name}'"); } - CString::new(field_name.as_ref()).map_err( - |e| vortex_err!(InvalidArgument: "Invalid field name '{field_name}': {e}"), - ) + CString::new(field_name.as_ref()) + .map_err(|e| vortex_err!("Invalid field name '{field_name}': {e}")) }) .collect::>()?; @@ -399,7 +398,7 @@ impl TryFrom for LogicalType { F32 => LogicalType::new(DUCKDB_TYPE::DUCKDB_TYPE_FLOAT), F64 => LogicalType::new(DUCKDB_TYPE::DUCKDB_TYPE_DOUBLE), PType::F16 => { - return Err(vortex_err!(InvalidArgument: "F16 type not supported in DuckDB")); + return Err(vortex_err!("F16 type not supported in DuckDB")); } }) } diff --git a/vortex-duckdb/src/convert/expr.rs b/vortex-duckdb/src/convert/expr.rs index 382c1bc2f00..b0ec984b7cc 100644 --- a/vortex-duckdb/src/convert/expr.rs +++ b/vortex-duckdb/src/convert/expr.rs @@ -86,7 +86,7 @@ fn from_bound_str(value: &ExpressionRef) -> VortexResult { match value.as_class().vortex_expect("unknown class") { BoundConstant(constant) => Ok(constant.value.as_string().as_str().to_owned()), _ => { - vortex_bail!(MismatchedTypes: "Expected string expression, got {:?}", value.as_class_id()) + vortex_bail!("Expected string expression, got {:?}", value.as_class_id()) } } } @@ -602,7 +602,7 @@ fn try_from_expression_inner( Ok(Some(match class { BoundRef => { let Some(col) = ctx.col_sub else { - vortex_bail!(InvalidArgument: "BoundRef requested but no column supplied"); + vortex_bail!("BoundRef requested but no column supplied"); }; col.clone() } @@ -721,7 +721,7 @@ fn try_from_expression_inner( or_collect(children).vortex_expect("cannot be empty") } _ => { - vortex_bail!(AssertionFailed: "unexpected operator {:?} in bound conjunction", conj.op) + vortex_bail!("unexpected operator {:?} in bound conjunction", conj.op) } } } @@ -765,7 +765,7 @@ impl TryFrom for Operator { fn try_from(value: DUCKDB_VX_EXPR_TYPE) -> VortexResult { Ok(match value { DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_INVALID => { - vortex_bail!(InvalidArgument: "invalid expression") + vortex_bail!("invalid expression") } DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_EQUAL => Operator::Eq, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_NOTEQUAL => Operator::NotEq, @@ -773,7 +773,7 @@ impl TryFrom for Operator { DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_GREATERTHAN => Operator::Gt, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_LESSTHANOREQUALTO => Operator::Lte, DUCKDB_VX_EXPR_TYPE::DUCKDB_VX_EXPR_TYPE_COMPARE_GREATERTHANOREQUALTO => Operator::Gte, - _ => vortex_bail!(MismatchedTypes: "cannot convert {:?}", value), + _ => vortex_bail!("cannot convert {:?}", value), }) } } diff --git a/vortex-duckdb/src/convert/scalar.rs b/vortex-duckdb/src/convert/scalar.rs index 00361e595c8..0b8b79dc1cb 100644 --- a/vortex-duckdb/src/convert/scalar.rs +++ b/vortex-duckdb/src/convert/scalar.rs @@ -87,12 +87,12 @@ impl ToDuckDBScalar for Scalar { DType::List(..) | DType::FixedSizeList(..) => self.as_list().try_to_duckdb_scalar(), DType::Map(..) => self.as_map().try_to_duckdb_scalar(), DType::Variant(_) => { - vortex_bail!(NotImplemented: "Vortex Variant scalars aren't supported") + vortex_bail!("Vortex Variant scalars aren't supported") } DType::Struct(..) => self.as_struct().try_to_duckdb_scalar(), // TODO(connor): Union DType::Union(..) => { - vortex_bail!(NotImplemented: "Vortex Union scalars aren't supported") + vortex_bail!("Vortex Union scalars aren't supported") } DType::Extension(..) => self.as_extension().try_to_duckdb_scalar(), } @@ -130,7 +130,7 @@ impl ToDuckDBScalar for DecimalScalar<'_> { let decimal_type = self .dtype() .as_decimal_opt() - .ok_or_else(|| vortex_err!(AssertionFailed: "decimal scalar without decimal dtype"))?; + .ok_or_else(|| vortex_err!("decimal scalar without decimal dtype"))?; let Some(decimal_value) = self.decimal_value() else { let lt = LogicalType::try_from(self.dtype())?; @@ -144,7 +144,7 @@ impl ToDuckDBScalar for DecimalScalar<'_> { DecimalValue::I64(v) => v as i128, DecimalValue::I128(v) => v, DecimalValue::I256(_) => { - vortex_bail!(NotImplemented: "cannot handle a i256 decimal in duckdb") + vortex_bail!("cannot handle a i256 decimal in duckdb") } }; @@ -244,9 +244,9 @@ impl ToDuckDBScalar for ExtScalar<'_> { fn try_to_duckdb_scalar(&self) -> VortexResult { if let Some(wkb) = self.ext_dtype().metadata_opt::() { let storage = self.to_storage_scalar(); - let binary = storage.as_binary_opt().ok_or_else( - || vortex_err!(InvalidArgument: "WellKnownBinary storage must be a binary scalar"), - )?; + let binary = storage + .as_binary_opt() + .ok_or_else(|| vortex_err!("WellKnownBinary storage must be a binary scalar"))?; return Ok(match binary.value() { Some(bytes) => Value::new_geometry(bytes.as_slice(), wkb.crs.as_deref())?, None => Value::null(&*ext_logical_type(self)?), @@ -254,14 +254,14 @@ impl ToDuckDBScalar for ExtScalar<'_> { } let Some(temporal) = self.ext_dtype().metadata_opt::() else { - vortex_bail!(MismatchedTypes: "Cannot convert non-temporal extension scalar to duckdb value"); + vortex_bail!("Cannot convert non-temporal extension scalar to duckdb value"); }; let storage = PrimitiveScalar::try_new(self.ext_dtype().storage_dtype(), self.value())?; let value = || { storage .as_::() - .ok_or_else(|| vortex_err!(Overflow: "temporal types must be convertible to i64")) + .ok_or_else(|| vortex_err!("temporal types must be convertible to i64")) }; Ok(match temporal { @@ -280,7 +280,7 @@ impl ToDuckDBScalar for ExtScalar<'_> { TimeUnit::Milliseconds => Value::new_timestamp_ms(value()?), TimeUnit::Seconds => Value::new_timestamp_s(value()?), TimeUnit::Days => { - vortex_bail!(InvalidArgument: "timestamp(d) is cannot be converted to duckdb scalar") + vortex_bail!("timestamp(d) is cannot be converted to duckdb scalar") } } } @@ -290,7 +290,7 @@ impl ToDuckDBScalar for ExtScalar<'_> { None => Value::null(&*ext_logical_type(self)?), }, _ => { - vortex_bail!(InvalidArgument: "cannot have TimeUnit {unit}, so represent a day") + vortex_bail!("cannot have TimeUnit {unit}, so represent a day") } }, TemporalMetadata::Time(unit) => match unit { @@ -299,7 +299,7 @@ impl ToDuckDBScalar for ExtScalar<'_> { TimeUnit::Seconds => Value::new_time(value()? * 1000 * 1000), TimeUnit::Nanoseconds => Value::new_time_ns(value()?), TimeUnit::Days => { - vortex_bail!(MismatchedTypes: "cannot convert timeunit {unit} to a duckdb time") + vortex_bail!("cannot convert timeunit {unit} to a duckdb time") } }, }) @@ -311,14 +311,13 @@ fn ext_logical_type(scalar: &ExtScalar<'_>) -> VortexResult { } fn timestamp_tz_micros(unit: TimeUnit, raw: i64) -> VortexResult { - let overflow = - || vortex_err!(Overflow: "timestamp_tz overflow rescaling {raw}{unit} to micros"); + let overflow = || vortex_err!("timestamp_tz overflow rescaling {raw}{unit} to micros"); match unit { TimeUnit::Seconds => raw.checked_mul(1_000_000).ok_or_else(overflow), TimeUnit::Milliseconds => raw.checked_mul(1_000).ok_or_else(overflow), TimeUnit::Microseconds => Ok(raw), TimeUnit::Nanoseconds => Ok(raw / 1_000), - TimeUnit::Days => vortex_bail!(InvalidArgument: "timestamp_tz cannot have a day time unit"), + TimeUnit::Days => vortex_bail!("timestamp_tz cannot have a day time unit"), } } @@ -352,10 +351,10 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { ExtractedValue::Integer(v) => Ok(Scalar::primitive(v, Nullable)), ExtractedValue::BigInt(v) => Ok(Scalar::primitive(v, Nullable)), ExtractedValue::HugeInt(_) => { - vortex_bail!(NotImplemented: "DuckDB HugeInt is not yet supported in Vortex"); + vortex_bail!("DuckDB HugeInt is not yet supported in Vortex"); } ExtractedValue::UHugeInt(_) => { - vortex_bail!(NotImplemented: "DuckDB UHugeInt is not yet supported in Vortex"); + vortex_bail!("DuckDB UHugeInt is not yet supported in Vortex"); } ExtractedValue::UTinyInt(v) => Ok(Scalar::primitive(v, Nullable)), ExtractedValue::USmallInt(v) => Ok(Scalar::primitive(v, Nullable)), @@ -371,7 +370,7 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { Scalar::binary(b, Nullable), )), DType::Extension(ext) if ext.is::() => { - vortex_ensure_eq!(b.len(), 16, InvalidArgument: "UUID blob must be 16 bytes"); + vortex_ensure_eq!(b.len(), 16, "UUID blob must be 16 bytes"); let children = b .iter() .map(|&byte| Scalar::primitive(byte, NonNullable)) @@ -384,7 +383,7 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { Ok(Scalar::extension_ref(ext.clone(), storage)) } _ => { - vortex_bail!(MismatchedTypes: "Cannot convert DuckDB blob to Vortex scalar of dtype {dtype}") + vortex_bail!("Cannot convert DuckDB blob to Vortex scalar of dtype {dtype}") } }, ExtractedValue::Date(days) => Ok(Scalar::extension::( @@ -485,11 +484,11 @@ impl<'a> TryFrom<&'a ValueRef> for Scalar { .collect::>>()?, )), _ => { - vortex_bail!(MismatchedTypes: "List value must be a list, fixed-size list or struct dtype") + vortex_bail!("List value must be a list, fixed-size list or struct dtype") } }, ExtractedValue::Unsupported(type_id) => { - vortex_bail!(InvalidArgument: "Unsupported DuckDB value type {type_id:?}") + vortex_bail!("Unsupported DuckDB value type {type_id:?}") } } } diff --git a/vortex-duckdb/src/convert/table_filter.rs b/vortex-duckdb/src/convert/table_filter.rs index f331e1a284d..2dce92d3d04 100644 --- a/vortex-duckdb/src/convert/table_filter.rs +++ b/vortex-duckdb/src/convert/table_filter.rs @@ -101,7 +101,7 @@ pub fn try_from_table_filter( } } TableFilterClass::Bloom => { - vortex_bail!(InvalidArgument: "bloom filter table filter is not supported") + vortex_bail!("bloom filter table filter is not supported") } })) } @@ -123,7 +123,7 @@ pub(super) fn dynamic_filter_expr( CompareOperator::Gte } _ => { - vortex_bail!(InvalidArgument: "unsupported dynamic filter operator {:?}", dynamic.operator) + vortex_bail!("unsupported dynamic filter operator {:?}", dynamic.operator) } }; let data = dynamic.data; @@ -145,14 +145,14 @@ pub(super) fn dynamic_filter_expr( fn nonnegative_number_from_value(value: &ValueRef) -> VortexResult { match value.extract() { ExtractedValue::BigInt(i) => { - u64::try_from(i).map_err(|_| vortex_err!(Overflow: "negative value: {i}")) + u64::try_from(i).map_err(|_| vortex_err!("negative value: {i}")) } ExtractedValue::Integer(i) => { - u64::try_from(i).map_err(|_| vortex_err!(Overflow: "negative value: {i}")) + u64::try_from(i).map_err(|_| vortex_err!("negative value: {i}")) } ExtractedValue::UBigInt(u) => Ok(u), ExtractedValue::UInteger(u) => Ok(u64::from(u)), - _ => vortex_bail!(MismatchedTypes: "unexpected value type"), + _ => vortex_bail!("unexpected value type"), } } diff --git a/vortex-duckdb/src/convert/vector.rs b/vortex-duckdb/src/convert/vector.rs index ab8002197a3..f3da09ceeec 100644 --- a/vortex-duckdb/src/convert/vector.rs +++ b/vortex-duckdb/src/convert/vector.rs @@ -332,7 +332,7 @@ pub fn flat_vector_to_vortex(vector: &VectorRef, len: usize) -> VortexResult vortex_bail!(InvalidArgument: "Unsupported decimal precision: {precision}"), + _ => vortex_bail!("Unsupported decimal precision: {precision}"), } .map(|a| a.into_array()) } @@ -407,7 +407,7 @@ pub fn flat_vector_to_vortex(vector: &VectorRef, len: usize) -> VortexResult { - vortex_bail!(InvalidArgument: "{type_id:?} flat Vector to Vortex array not supported") + vortex_bail!("{type_id:?} flat Vector to Vortex array not supported") } } } @@ -1069,14 +1069,14 @@ mod tests { &point!(x: 1.0_f64, y: 2.0_f64), &WriteOptions::default(), ) - .map_err(|e| vortex::error::vortex_err!(Serde: "writing WKB point: {e}"))?; + .map_err(|e| vortex::error::vortex_err!("writing WKB point: {e}"))?; let mut wkb_b: Vec = Vec::new(); write_point( &mut wkb_b, &point!(x: 3.5_f64, y: -4.25_f64), &WriteOptions::default(), ) - .map_err(|e| vortex::error::vortex_err!(Serde: "writing WKB point: {e}"))?; + .map_err(|e| vortex::error::vortex_err!("writing WKB point: {e}"))?; let len = 3; let logical_type = LogicalType::geometry_type(Some("EPSG:4326"))?; diff --git a/vortex-duckdb/src/copy.rs b/vortex-duckdb/src/copy.rs index a4c09b52f7c..6d3dbbbd952 100644 --- a/vortex-duckdb/src/copy.rs +++ b/vortex-duckdb/src/copy.rs @@ -98,7 +98,7 @@ fn push_to_writer(global: &CopyFunctionGlobal, array: ArrayRef) -> VortexResult< let mut sink = global .sink .as_ref() - .ok_or_else(|| vortex_err!(Io: "sink closed early"))? + .ok_or_else(|| vortex_err!("sink closed early"))? .clone(); RUNTIME.block_on(async { // send may error with "receiver is gone" which isn't the real error @@ -110,7 +110,7 @@ fn push_to_writer(global: &CopyFunctionGlobal, array: ArrayRef) -> VortexResult< // we can get the real error (i.e invalid path) from here task.await?; } - vortex_bail!(Io: "Writer stopped before all data was written") + vortex_bail!("Writer stopped before all data was written") }) } @@ -236,11 +236,11 @@ fn column_stats_from_summary( let file_stats = summary .footer() .statistics() - .ok_or_else(|| vortex_err!(AssertionFailed: "written file has no statistics"))?; + .ok_or_else(|| vortex_err!("written file has no statistics"))?; let stats_sets = file_stats.stats_sets(); if column_index >= stats_sets.len() { vortex_bail!( - OutOfBounds: "column index {column_index} out of range for {} statistics sets", + "column index {column_index} out of range for {} statistics sets", stats_sets.len() ); } diff --git a/vortex-duckdb/src/duckdb/connection.rs b/vortex-duckdb/src/duckdb/connection.rs index 7acaee68a96..719cc104e95 100644 --- a/vortex-duckdb/src/duckdb/connection.rs +++ b/vortex-duckdb/src/duckdb/connection.rs @@ -35,8 +35,8 @@ impl ConnectionRef { /// Execute SQL query and return the result. pub fn query(&self, query: &str) -> VortexResult { let mut result: cpp::duckdb_result = unsafe { std::mem::zeroed() }; - let query_cstr = std::ffi::CString::new(query) - .map_err(|_| vortex_err!(InvalidArgument: "Invalid query string"))?; + let query_cstr = + std::ffi::CString::new(query).map_err(|_| vortex_err!("Invalid query string"))?; let status = unsafe { cpp::duckdb_query(self.as_ptr(), query_cstr.as_ptr(), &raw mut result) }; @@ -52,7 +52,7 @@ impl ConnectionRef { }; unsafe { cpp::duckdb_destroy_result(&raw mut result) }; - return Err(vortex_err!(InvalidArgument: "Failed to execute query: {}", error_msg)); + return Err(vortex_err!("Failed to execute query: {}", error_msg)); } Ok(unsafe { QueryResult::new(result) }) diff --git a/vortex-duckdb/src/duckdb/data_chunk.rs b/vortex-duckdb/src/duckdb/data_chunk.rs index 02f228473b3..dce2a5637bf 100644 --- a/vortex-duckdb/src/duckdb/data_chunk.rs +++ b/vortex-duckdb/src/duckdb/data_chunk.rs @@ -82,14 +82,14 @@ impl TryFrom<&DataChunkRef> for String { cpp::duckdb_data_chunk_verify(value.as_ptr(), &raw mut err); if !err.is_null() { vortex_bail!( - InvalidArgument: "{}", + "{}", CStr::from_ptr(cpp::duckdb_vx_error_value(err)).to_string_lossy() ) } }; let debug = unsafe { cpp::duckdb_data_chunk_to_string(value.as_ptr(), &raw mut err) }; if !err.is_null() { - vortex_bail!(InvalidArgument: "{}", unsafe { + vortex_bail!("{}", unsafe { CStr::from_ptr(cpp::duckdb_vx_error_value(err)).to_string_lossy() }) } diff --git a/vortex-duckdb/src/duckdb/database.rs b/vortex-duckdb/src/duckdb/database.rs index 6bde4c143de..53967a89d97 100644 --- a/vortex-duckdb/src/duckdb/database.rs +++ b/vortex-duckdb/src/duckdb/database.rs @@ -36,11 +36,12 @@ impl Database { /// /// Creates a new file in case the path does not exist. pub fn open>(path: P) -> VortexResult { - let path_str = path.as_ref().to_str().ok_or_else( - || vortex_err!(InvalidArgument: "Invalid path: path contains non-UTF8 characters"), - )?; + let path_str = path + .as_ref() + .to_str() + .ok_or_else(|| vortex_err!("Invalid path: path contains non-UTF8 characters"))?; let path_cstr = CString::new(path_str) - .map_err(|_| vortex_err!(InvalidArgument: "Invalid path: path contains null bytes"))?; + .map_err(|_| vortex_err!("Invalid path: path contains null bytes"))?; let mut ptr: duckdb_database = ptr::null_mut(); duckdb_try!( @@ -62,9 +63,8 @@ impl DatabaseRef { } pub fn register_version_function(&self, version: &str) -> VortexResult<()> { - let version = CString::new(version).map_err( - |_| vortex_err!(InvalidArgument: "Invalid version: string contains null bytes"), - )?; + let version = CString::new(version) + .map_err(|_| vortex_err!("Invalid version: string contains null bytes"))?; duckdb_try!( unsafe { cpp::duckdb_vx_register_version_function(self.as_ptr(), version.as_ptr()) }, "Failed to register vortex_version function" diff --git a/vortex-duckdb/src/duckdb/function.rs b/vortex-duckdb/src/duckdb/function.rs index b70ba55fa9a..0441fe43548 100644 --- a/vortex-duckdb/src/duckdb/function.rs +++ b/vortex-duckdb/src/duckdb/function.rs @@ -16,7 +16,7 @@ impl ScalarFunctionRef { let name_ptr = cpp::duckdb_vx_sfunc_name(self.as_ptr()); std::ffi::CStr::from_ptr(name_ptr) .to_str() - .map_err(|e| vortex_err!(InvalidArgument: "invalid utf-8: {e}")) + .map_err(|e| vortex_err!("invalid utf-8: {e}")) .vortex_expect("scalar function name should be valid UTF-8") } } @@ -28,7 +28,7 @@ impl AggregateFunctionRef { let name_ptr = cpp::duckdb_vx_agg_func_name(self.as_ptr()); std::ffi::CStr::from_ptr(name_ptr) .to_str() - .map_err(|e| vortex_err!(InvalidArgument: "invalid utf-8: {e}")) + .map_err(|e| vortex_err!("invalid utf-8: {e}")) .vortex_expect("aggregate function name should be valid UTF-8") } } diff --git a/vortex-duckdb/src/duckdb/logical_type.rs b/vortex-duckdb/src/duckdb/logical_type.rs index 1cb25a7b43f..ea1443db50a 100644 --- a/vortex-duckdb/src/duckdb/logical_type.rs +++ b/vortex-duckdb/src/duckdb/logical_type.rs @@ -89,7 +89,7 @@ impl LogicalType { }; if struct_type_ptr.is_null() { - vortex_bail!(InvalidArgument: "Failed to create struct logical type"); + vortex_bail!("Failed to create struct logical type"); } Ok(unsafe { Self::own(struct_type_ptr) }) @@ -99,13 +99,13 @@ impl LogicalType { pub fn decimal_type(precision: u8, scale: u8) -> VortexResult { vortex_ensure!( precision <= DUCKDB_MAX_DECIMAL_PRECISION, - InvalidArgument: "DuckDB decimal type precision must be <= {DUCKDB_MAX_DECIMAL_PRECISION}. \ + "DuckDB decimal type precision must be <= {DUCKDB_MAX_DECIMAL_PRECISION}. \ precision: {precision}" ); let ptr = unsafe { duckdb_create_decimal_type(precision, scale) }; if ptr.is_null() { - vortex_bail!(InvalidArgument: "Failed to create decimal type"); + vortex_bail!("Failed to create decimal type"); } Ok(unsafe { Self::own(ptr) }) } @@ -115,7 +115,7 @@ impl LogicalType { let ptr = unsafe { duckdb_create_list_type(element_type.as_ptr()) }; if ptr.is_null() { - vortex_bail!(InvalidArgument: "Failed to create list type"); + vortex_bail!("Failed to create list type"); } Ok(unsafe { Self::own(ptr) }) } @@ -128,7 +128,7 @@ impl LogicalType { let ptr = unsafe { duckdb_create_array_type(element_type.as_ptr(), list_size as idx_t) }; if ptr.is_null() { - vortex_bail!(InvalidArgument: "Failed to create fixed-size list (array) type"); + vortex_bail!("Failed to create fixed-size list (array) type"); } // SAFETY: This pointer came directly from DuckDB, and we checked that it was not `NULL`. @@ -140,7 +140,7 @@ impl LogicalType { let ptr = unsafe { duckdb_create_map_type(key_type.as_ptr(), value_type.as_ptr()) }; if ptr.is_null() { - vortex_bail!(InvalidArgument: "Failed to create map type"); + vortex_bail!("Failed to create map type"); } Ok(unsafe { Self::own(ptr) }) } @@ -238,11 +238,11 @@ impl LogicalType { /// Pass `None` for a GEOMETRY with no associated CRS. pub fn geometry_type(crs: Option<&str>) -> VortexResult { let Ok(crs) = CString::new(crs.unwrap_or("")) else { - vortex_bail!(InvalidArgument: "CRS must not contain NUL bytes"); + vortex_bail!("CRS must not contain NUL bytes"); }; let ptr = unsafe { duckdb_vx_create_geometry(crs.as_ptr()) }; if ptr.is_null() { - vortex_bail!(InvalidArgument: "Failed to create GEOMETRY logical type"); + vortex_bail!("Failed to create GEOMETRY logical type"); } Ok(unsafe { Self::own(ptr) }) } @@ -456,7 +456,7 @@ macro_rules! match_each_primitive_type { $body } _ => vortex::error::vortex_panic!( - MismatchedTypes: "Unexpected type for match_each_primitive_type: {:?}", + "Unexpected type for match_each_primitive_type: {:?}", $self.as_type_id() ), } diff --git a/vortex-duckdb/src/duckdb/macro_.rs b/vortex-duckdb/src/duckdb/macro_.rs index 1e454396834..83e79ada5e5 100644 --- a/vortex-duckdb/src/duckdb/macro_.rs +++ b/vortex-duckdb/src/duckdb/macro_.rs @@ -6,21 +6,21 @@ macro_rules! duckdb_try { // Pattern: duckdb_try!(function_call) ($call:expr) => { if $call != $crate::cpp::duckdb_state::DuckDBSuccess { - vortex::error::vortex_bail!(Other: "DuckDB operation failed"); + vortex::error::vortex_bail!("DuckDB operation failed"); } }; // Pattern: duckdb_try!(function_call, "error message") ($call:expr, $msg:literal) => { if $call != $crate::cpp::duckdb_state::DuckDBSuccess { - vortex::error::vortex_bail!(Other: $msg); + vortex::error::vortex_bail!($msg); } }; // Pattern: duckdb_try!(function_call, "error message with {}", args...) ($call:expr, $msg:literal, $($args:expr),+) => { if $call != $crate::cpp::duckdb_state::DuckDBSuccess { - vortex::error::vortex_bail!(Other: $msg, $($args),+); + vortex::error::vortex_bail!($msg, $($args),+); } }; } @@ -66,7 +66,7 @@ macro_rules! lifetime_wrapper { pub unsafe fn own(ptr: $ffi_type) -> Self { if ptr.is_null() { vortex::error::vortex_panic!( - InvalidArgument: "Attempted to create an owned wrapper from a null pointer" + "Attempted to create an owned wrapper from a null pointer" ); } Self(unsafe { std::ptr::NonNull::new_unchecked(ptr.cast()) }) @@ -80,7 +80,7 @@ macro_rules! lifetime_wrapper { pub unsafe fn borrow<'a>(ptr: $ffi_type) -> &'a [<$Name Ref>] { if ptr.is_null() { vortex::error::vortex_panic!( - InvalidArgument: "Attempted to borrow from a null pointer" + "Attempted to borrow from a null pointer" ); } unsafe { &*(ptr as *const [<$Name Ref>]) } @@ -95,7 +95,7 @@ macro_rules! lifetime_wrapper { pub unsafe fn borrow_mut<'a>(ptr: $ffi_type) -> &'a mut [<$Name Ref>] { if ptr.is_null() { vortex::error::vortex_panic!( - InvalidArgument: "Attempted to borrow_mut from a null pointer" + "Attempted to borrow_mut from a null pointer" ); } unsafe { &mut *(ptr as *mut [<$Name Ref>]) } diff --git a/vortex-duckdb/src/duckdb/query_result.rs b/vortex-duckdb/src/duckdb/query_result.rs index 109a9b23439..c32c1debf0d 100644 --- a/vortex-duckdb/src/duckdb/query_result.rs +++ b/vortex-duckdb/src/duckdb/query_result.rs @@ -65,11 +65,11 @@ impl QueryResultRef { let name_ptr = cpp::duckdb_column_name(self.as_ptr(), col_idx as u64); if name_ptr.is_null() { - vortex_bail!(InvalidArgument: "Invalid column index: {}", col_idx); + vortex_bail!("Invalid column index: {}", col_idx); } CStr::from_ptr(name_ptr) .to_str() - .map_err(|_| vortex_err!(InvalidArgument: "Invalid UTF-8 in column name")) + .map_err(|_| vortex_err!("Invalid UTF-8 in column name")) } } diff --git a/vortex-duckdb/src/duckdb/table_filter.rs b/vortex-duckdb/src/duckdb/table_filter.rs index c0facf7bce2..79468315144 100644 --- a/vortex-duckdb/src/duckdb/table_filter.rs +++ b/vortex-duckdb/src/duckdb/table_filter.rs @@ -52,7 +52,7 @@ impl<'a> IntoIterator for &'a TableFilterSetRef { fn into_iter(self) -> Self::IntoIter { Box::new((0..self.len()).map(move |i| { self.get(i) - .unwrap_or_else(|| vortex_panic!(AssertionFailed: "inside filter set bounds {i}")) + .unwrap_or_else(|| vortex_panic!("inside filter set bounds {i}")) })) } } diff --git a/vortex-duckdb/src/duckdb/value.rs b/vortex-duckdb/src/duckdb/value.rs index fb980f7f9bd..bd14635f18a 100644 --- a/vortex-duckdb/src/duckdb/value.rs +++ b/vortex-duckdb/src/duckdb/value.rs @@ -36,7 +36,7 @@ impl ValueRef { pub fn as_string(&self) -> BufferString { let ExtractedValue::Varchar(string) = self.extract() else { - vortex_panic!(MismatchedTypes: "ValueRef is not a string"); + vortex_panic!("ValueRef is not a string"); }; string } @@ -48,7 +48,7 @@ impl ValueRef { } match self.logical_type().as_type_id() { DUCKDB_TYPE::DUCKDB_TYPE_INVALID => { - vortex_panic!(MismatchedTypes: "Invalid type for DuckDB value") + vortex_panic!("Invalid type for DuckDB value") } DUCKDB_TYPE::DUCKDB_TYPE_SQLNULL => ExtractedValue::Null, DUCKDB_TYPE::DUCKDB_TYPE_BOOLEAN => { @@ -97,7 +97,7 @@ impl ValueRef { let cstr = unsafe { CStr::from_ptr(ptr) }; let string = BufferString::from( cstr.to_str() - .map_err(|e| vortex_err!(InvalidArgument: "Invalid UTF-8 string from DuckDB: {e}")) + .map_err(|e| vortex_err!("Invalid UTF-8 string from DuckDB: {e}")) .vortex_expect("Invalid UTF-8 string from DuckDB"), ); unsafe { cpp::duckdb_free(ptr.cast()) }; @@ -298,7 +298,7 @@ impl Value { let crs_c = crs .map(CString::new) .transpose() - .map_err(|_| vortex_err!(InvalidArgument: "CRS must not contain NUL bytes"))?; + .map_err(|_| vortex_err!("CRS must not contain NUL bytes"))?; let crs_ptr = crs_c.as_ref().map_or(ptr::null(), |c| c.as_ptr()); Ok(unsafe { Self::own(cpp::duckdb_vx_value_create_geometry( @@ -341,7 +341,7 @@ impl Value { vortex_ensure_eq!( fields.len(), struct_type.struct_type_child_count(), - InvalidArgument: "struct value field count must match its logical type" + "struct value field count must match its logical type" ); let mut ptrs = value_ptrs(fields); let ptr = @@ -358,7 +358,7 @@ impl Value { vortex_ensure_eq!( keys.len(), values.len(), - InvalidArgument: "map value must have as many keys as values" + "map value must have as many keys as values" ); let mut key_ptrs = value_ptrs(keys); let mut val_ptrs = value_ptrs(values); @@ -377,7 +377,7 @@ impl Value { /// invalid input. fn try_own(ptr: cpp::duckdb_value, kind: &str) -> VortexResult { if ptr.is_null() { - vortex_bail!(InvalidArgument: "Failed to create DuckDB {kind} value"); + vortex_bail!("Failed to create DuckDB {kind} value"); } Ok(unsafe { Self::own(ptr) }) } diff --git a/vortex-duckdb/src/duckdb/vector.rs b/vortex-duckdb/src/duckdb/vector.rs index 3a7ce09a5cd..1d37ff9d6ef 100644 --- a/vortex-duckdb/src/duckdb/vector.rs +++ b/vortex-duckdb/src/duckdb/vector.rs @@ -285,7 +285,7 @@ impl VectorRef { let state = unsafe { cpp::duckdb_list_vector_reserve(self.as_ptr(), required_capacity) }; match state { cpp::duckdb_state::DuckDBSuccess => Ok(()), - cpp::duckdb_state::DuckDBError => vortex_bail!(InvalidArgument: "vector was nullptr!"), + cpp::duckdb_state::DuckDBError => vortex_bail!("vector was nullptr!"), } } @@ -313,7 +313,7 @@ impl VectorRef { let state = unsafe { cpp::duckdb_list_vector_set_size(self.as_ptr(), size) }; match state { cpp::duckdb_state::DuckDBSuccess => Ok(()), - cpp::duckdb_state::DuckDBError => vortex_bail!(InvalidArgument: "vector was nullptr!"), + cpp::duckdb_state::DuckDBError => vortex_bail!("vector was nullptr!"), } } diff --git a/vortex-duckdb/src/exporter/canonical.rs b/vortex-duckdb/src/exporter/canonical.rs index 01a9b0122ea..e7374298c26 100644 --- a/vortex-duckdb/src/exporter/canonical.rs +++ b/vortex-duckdb/src/exporter/canonical.rs @@ -30,15 +30,15 @@ pub(crate) fn new_exporter( Canonical::Decimal(array) => decimal::new_exporter(array, ctx), Canonical::VarBinView(array) => varbinview::new_exporter(array, ctx), Canonical::List(array) => list_view::new_exporter(array, cache, ctx), - Canonical::Map(_) => vortex_bail!(NotImplemented: "Map arrays can't be exported to DuckDB"), + Canonical::Map(_) => vortex_bail!("Map arrays can't be exported to DuckDB"), Canonical::FixedSizeList(array) => fixed_size_list::new_exporter(array, cache, ctx), Canonical::Struct(array) => struct_::new_exporter(array, cache, ctx), Canonical::Union(_) => { - vortex_bail!(NotImplemented: "TODO(connor)[Union]: implement DuckDB export for Union arrays") + vortex_bail!("TODO(connor)[Union]: implement DuckDB export for Union arrays") } Canonical::Extension(ext) => extension::new_exporter(ext, ctx), Canonical::Variant(_) => { - vortex_bail!(NotImplemented: "Variant arrays can't be exported to DuckDB") + vortex_bail!("Variant arrays can't be exported to DuckDB") } } } diff --git a/vortex-duckdb/src/exporter/chunked.rs b/vortex-duckdb/src/exporter/chunked.rs index 2c8deee72a2..78a4e0dfee3 100644 --- a/vortex-duckdb/src/exporter/chunked.rs +++ b/vortex-duckdb/src/exporter/chunked.rs @@ -80,7 +80,7 @@ impl ColumnExporter for ChunkedExporter { let offset_in_chunk = offset - chunk_start; vortex_ensure!( offset + len <= chunk_end, - InvalidArgument: "chunked DuckDB export range {offset}..{} crosses chunk boundary at {chunk_end}", + "chunked DuckDB export range {offset}..{} crosses chunk boundary at {chunk_end}", offset + len ); diff --git a/vortex-duckdb/src/exporter/decimal.rs b/vortex-duckdb/src/exporter/decimal.rs index 7cf561892a3..2330bc6a2b6 100644 --- a/vortex-duckdb/src/exporter/decimal.rs +++ b/vortex-duckdb/src/exporter/decimal.rs @@ -124,7 +124,7 @@ pub fn precision_to_duckdb_storage_size(decimal_dtype: &DecimalDType) -> VortexR 10..=18 => DecimalType::I64, 19..=38 => DecimalType::I128, decimal_dtype => { - vortex_bail!(NotImplemented: "cannot represent decimal in ducdkb {decimal_dtype}") + vortex_bail!("cannot represent decimal in ducdkb {decimal_dtype}") } }) } diff --git a/vortex-duckdb/src/exporter/extension.rs b/vortex-duckdb/src/exporter/extension.rs index 5ac31b81ef1..ebebefd177c 100644 --- a/vortex-duckdb/src/exporter/extension.rs +++ b/vortex-duckdb/src/exporter/extension.rs @@ -69,5 +69,5 @@ pub(crate) fn new_exporter( return spatial::new_multipolygon_exporter(MultiPolygonData::try_from(ext)?, ctx); } - vortex_bail!(NotImplemented: "no non-temporal extension exporter") + vortex_bail!("no non-temporal extension exporter") } diff --git a/vortex-duckdb/src/exporter/mod.rs b/vortex-duckdb/src/exporter/mod.rs index f8743af8fc2..539a6d994a2 100644 --- a/vortex-duckdb/src/exporter/mod.rs +++ b/vortex-duckdb/src/exporter/mod.rs @@ -103,7 +103,7 @@ impl ArrayExporter { let expected_cols = self.fields.len(); let chunk_cols = chunk.column_count(); if !zero_projection && chunk_cols != expected_cols { - vortex_bail!(MismatchedTypes: "Expected {expected_cols} columns in output chunk, got {chunk_cols}"); + vortex_bail!("Expected {expected_cols} columns in output chunk, got {chunk_cols}"); } let position = self.array_len - self.remaining; @@ -115,7 +115,7 @@ impl ArrayExporter { } vortex_ensure!( chunk_len > 0, - AssertionFailed: "column exporter returned zero rows for non-empty export" + "column exporter returned zero rows for non-empty export" ); self.remaining -= chunk_len; diff --git a/vortex-duckdb/src/exporter/uuid.rs b/vortex-duckdb/src/exporter/uuid.rs index a5cb990a935..73a221033bc 100644 --- a/vortex-duckdb/src/exporter/uuid.rs +++ b/vortex-duckdb/src/exporter/uuid.rs @@ -44,7 +44,7 @@ pub(crate) fn new_exporter( vortex_ensure_eq!( bytes.len(), len * UUID_BYTE_LEN, - InvalidArgument: "UUID storage byte length mismatch" + "UUID storage byte length mismatch" ); let exporter = Box::new(UuidExporter { bytes }); diff --git a/vortex-duckdb/src/ffi.rs b/vortex-duckdb/src/ffi.rs index ea0323893ab..01e6cf5a7e2 100644 --- a/vortex-duckdb/src/ffi.rs +++ b/vortex-duckdb/src/ffi.rs @@ -191,8 +191,7 @@ pub unsafe extern "C-unwind" fn duckdb_reader_open( let path = unsafe { std::slice::from_raw_parts(file_path.cast::(), file_path_len) }; try_or_null(error, || { - let path = - str::from_utf8(path).map_err(|_| vortex_err!(InvalidArgument: "invalid utf-8"))?; + let path = str::from_utf8(path).map_err(|_| vortex_err!("invalid utf-8"))?; let file = reader_open(path)?; Ok(Data::from(Box::new(file)).as_ptr()) }) @@ -243,8 +242,7 @@ pub unsafe extern "C-unwind" fn duckdb_footer_get_cached( let bind = unsafe { bind.cast::().as_mut() }.vortex_expect("null pointer"); let path = unsafe { std::slice::from_raw_parts(path.cast::(), len) }; try_or_null(error, || { - let path = - str::from_utf8(path).map_err(|_| vortex_err!(InvalidArgument: "invalid utf-8"))?; + let path = str::from_utf8(path).map_err(|_| vortex_err!("invalid utf-8"))?; Ok(match footer_get_cached(bind, path)? { Some(footer) => { unsafe { *row_count_out = footer.row_count() }; diff --git a/vortex-duckdb/src/projection.rs b/vortex-duckdb/src/projection.rs index b3bca3db2cc..beec2cc74db 100644 --- a/vortex-duckdb/src/projection.rs +++ b/vortex-duckdb/src/projection.rs @@ -267,9 +267,9 @@ impl Filter { } pub fn extract_schema_from_dtype(dtype: &DType) -> VortexResult> { - let struct_dtype = dtype.as_struct_fields_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "Vortex file must contain a struct array at the top level"), - )?; + let struct_dtype = dtype + .as_struct_fields_opt() + .ok_or_else(|| vortex_err!("Vortex file must contain a struct array at the top level"))?; let len = struct_dtype.names().len(); let mut fields = Vec::with_capacity(len); diff --git a/vortex-duckdb/src/table_function.rs b/vortex-duckdb/src/table_function.rs index 8bbd3758afa..7c7d172b38c 100644 --- a/vortex-duckdb/src/table_function.rs +++ b/vortex-duckdb/src/table_function.rs @@ -395,7 +395,7 @@ fn aggregate_output_value(scalar: Scalar, expected: &LogicalTypeRef) -> VortexRe PType::I64 => primitive.typed_value::().map(i128::from), PType::U64 => primitive.typed_value::().map(i128::from), other => { - vortex_bail!(MismatchedTypes: "expected {expected:?} output type, got {other}") + vortex_bail!("expected {expected:?} output type, got {other}") } }) }; diff --git a/vortex-edition/src/lib.rs b/vortex-edition/src/lib.rs index f1b787c4e0a..ede2646bb17 100644 --- a/vortex-edition/src/lib.rs +++ b/vortex-edition/src/lib.rs @@ -95,13 +95,13 @@ impl EditionId { /// [`test_harness::validate_edition`]. pub fn validate(&self) -> VortexResult<()> { if self.family.is_empty() || !self.family.chars().all(|c| c.is_ascii_lowercase()) { - vortex_bail!(InvalidArgument: "edition {self} must have a non-empty lowercase family, e.g. `core`"); + vortex_bail!("edition {self} must have a non-empty lowercase family, e.g. `core`"); } if !(1000..=9999).contains(&self.year) { - vortex_bail!(InvalidArgument: "edition {self} must have a four-digit year"); + vortex_bail!("edition {self} must have a four-digit year"); } if !(1..=12).contains(&self.month) { - vortex_bail!(InvalidArgument: "edition {self} must have a month in 01-12"); + vortex_bail!("edition {self} must have a month in 01-12"); } Ok(()) } @@ -141,18 +141,18 @@ impl EditionFamily { pub fn validate(&self) -> VortexResult<()> { if self.name.is_empty() || !self.name.chars().all(|c| c.is_ascii_lowercase()) { vortex_bail!( - InvalidArgument: "edition family {:?} must have a non-empty lowercase name, e.g. `core`", + "edition family {:?} must have a non-empty lowercase name, e.g. `core`", self.name ); } if self.origin.trim().is_empty() { vortex_bail!( - InvalidArgument: "edition family {} must name its origin library or project", + "edition family {} must name its origin library or project", self.name ); } if self.doc.trim().is_empty() { - vortex_bail!(InvalidArgument: "edition family {} must document what it is for", self.name); + vortex_bail!("edition family {} must document what it is for", self.name); } Ok(()) } @@ -369,7 +369,7 @@ impl EditionInclusion { .all(|c| c.is_ascii_lowercase() || c.is_ascii_digit() || "._-".contains(c)); if !well_formed { vortex_bail!( - InvalidArgument: "invalid {} id {id:?}: expected lowercase `namespace.name`, e.g. `vortex.alp`", + "invalid {} id {id:?}: expected lowercase `namespace.name`, e.g. `vortex.alp`", self.kind ); } @@ -377,7 +377,7 @@ impl EditionInclusion { && parse_release(release).is_none() { vortex_bail!( - Serde: "{} {id} declares malformed required_vortex_release {release:?}", + "{} {id} declares malformed required_vortex_release {release:?}", self.kind ); } diff --git a/vortex-edition/src/session.rs b/vortex-edition/src/session.rs index 089c6e4ca40..4b192e3d7d9 100644 --- a/vortex-edition/src/session.rs +++ b/vortex-edition/src/session.rs @@ -106,7 +106,7 @@ impl EditionSession { pub fn declare_family(&self, family: &EditionFamily) -> VortexResult<()> { let mut inner = self.inner.write(); if inner.families.contains_key(family.name) { - vortex_bail!(InvalidArgument: "duplicate edition family {}", family.name); + vortex_bail!("duplicate edition family {}", family.name); } inner.families.insert(family.name.to_string(), *family); Ok(()) @@ -127,7 +127,7 @@ impl EditionSession { let mut inner = self.inner.write(); let key = edition.id.to_string(); if inner.editions.contains_key(&key) { - vortex_bail!(InvalidArgument: "duplicate edition {key}"); + vortex_bail!("duplicate edition {key}"); } inner.editions.insert(key, edition); Ok(()) @@ -153,7 +153,7 @@ impl EditionSession { if let Some(previous) = previous { vortex_bail!( - InvalidArgument: "{} {} already joined family {} in edition {}", + "{} {} already joined family {} in edition {}", inclusion.kind, inclusion.component_id, inclusion.since.family, @@ -234,7 +234,7 @@ impl EditionSession { edition.id.validate()?; if self.find_family(edition.id.family).is_none() { vortex_bail!( - NotFound: "edition {} belongs to undeclared family {}; declare the family before \ + "edition {} belongs to undeclared family {}; declare the family before \ its editions", edition.id, edition.id.family, @@ -244,7 +244,7 @@ impl EditionSession { && parse_release(version).is_none() { vortex_bail!( - Serde: "edition {} declares malformed min_library_version {version:?}", + "edition {} declares malformed min_library_version {version:?}", edition.id ); } @@ -256,7 +256,7 @@ impl EditionSession { let (prev, next) = (&pair[0], &pair[1]); if prev.id.family == next.id.family && prev.is_draft() && !next.is_draft() { vortex_bail!( - InvalidArgument: "frozen edition {} follows draft {}; drafts must be newest in a family", + "frozen edition {} follows draft {}; drafts must be newest in a family", next.id, prev.id, ); @@ -274,7 +274,7 @@ impl EditionSession { let Some(edition) = inner.editions.get(&inclusion.since.to_string()) else { vortex_bail!( - NotFound: "{} {} is included in undeclared edition {}", + "{} {} is included in undeclared edition {}", inclusion.kind, inclusion.component_id, inclusion.since @@ -286,7 +286,7 @@ impl EditionSession { && required > declared { vortex_bail!( - InvalidArgument: "{} {} requires release {}, newer than edition {}'s declared \ + "{} {} requires release {}, newer than edition {}'s declared \ min_library_version", inclusion.kind, inclusion.component_id, @@ -347,7 +347,7 @@ pub trait EditionSessionExt: SessionExt { /// silently produce an empty writable set. fn enable_edition(&self, edition: EditionId) -> VortexResult<()> { if self.editions().find(&edition).is_none() { - vortex_bail!(NotFound: "cannot enable unregistered edition {edition}"); + vortex_bail!("cannot enable unregistered edition {edition}"); } self.enabled_editions().enable(edition); Ok(()) diff --git a/vortex-edition/src/test_harness.rs b/vortex-edition/src/test_harness.rs index 105ba91bb76..0594ccf9756 100644 --- a/vortex-edition/src/test_harness.rs +++ b/vortex-edition/src/test_harness.rs @@ -28,7 +28,7 @@ use crate::EditionSession; pub fn validate_edition(editions: &EditionSession, edition: &EditionId) -> VortexResult<()> { edition.validate()?; if editions.find(edition).is_none() { - vortex_bail!(NotFound: "{edition} is not declared in the session"); + vortex_bail!("{edition} is not declared in the session"); } editions.validate() } diff --git a/vortex-edition/src/tests.rs b/vortex-edition/src/tests.rs index 786e46b9087..7394414499d 100644 --- a/vortex-edition/src/tests.rs +++ b/vortex-edition/src/tests.rs @@ -97,17 +97,17 @@ fn membership_is_transitive() -> VortexResult<()> { let alpha = second .iter() .find(|i| i.component_id.as_str() == "test.alpha") - .ok_or_else(|| vortex_err!(AssertionFailed: "test.alpha is a member"))?; + .ok_or_else(|| vortex_err!("test.alpha is a member"))?; assert_eq!(alpha.since, FIRST); let alpha_v2 = second .iter() .find(|i| i.component_id.as_str() == "test.alpha_v2") - .ok_or_else(|| vortex_err!(AssertionFailed: "test.alpha_v2 is a member"))?; + .ok_or_else(|| vortex_err!("test.alpha_v2 is a member"))?; assert_eq!(alpha_v2.since, SECOND); let beta = second .iter() .find(|i| i.component_id.as_str() == "test.beta") - .ok_or_else(|| vortex_err!(AssertionFailed: "test.beta is a member"))?; + .ok_or_else(|| vortex_err!("test.beta is a member"))?; assert_eq!(beta.since, FIRST); // The second edition's delta is exactly the members declared at it. diff --git a/vortex-error/src/lib.rs b/vortex-error/src/lib.rs index 7b087c8d277..0d90340ebe2 100644 --- a/vortex-error/src/lib.rs +++ b/vortex-error/src/lib.rs @@ -6,10 +6,9 @@ //! This crate defines error & result types for Vortex. //! It also contains a variety of useful macros for error handling. //! -//! Vortex models errors the way Python models exceptions: a small, stable set of classes -//! ([`VortexErrorKind`]) carrying a human-readable message, rather than one enum variant per -//! library that Vortex happens to depend on. An error from a dependency is attached as the -//! [`Error::source`] of a [`VortexError`] and is recovered by downcasting that source. +//! A [`VortexError`] is a human-readable message, not one enum variant per library that Vortex +//! happens to depend on. An error from a dependency is attached as the [`Error::source`] of a +//! [`VortexError`] and is recovered by downcasting that source. use std::backtrace::Backtrace; use std::backtrace::BacktraceStatus; @@ -78,60 +77,10 @@ impl Display for ErrString { } } -/// The classification of a [`VortexError`], analogous to a Python exception class. -/// -/// The set is deliberately small and is mirrored by the `vx_error_code` enum in the C API, so a -/// kind only earns its place if a caller would branch on it. Failures originating in a dependency -/// are classified by what they mean to Vortex, not by which crate produced them. -#[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)] -#[non_exhaustive] -pub enum VortexErrorKind { - /// An otherwise unclassified error. The analogue of Python's `RuntimeError`. - Other, - /// An index is out of bounds. The analogue of Python's `IndexError`. - OutOfBounds, - /// A name was looked up and nothing was bound to it. The analogue of Python's `KeyError`. - NotFound, - /// A numeric value does not fit its target type. The analogue of Python's `OverflowError`. - Overflow, - /// An invalid argument was provided. The analogue of Python's `ValueError`. - InvalidArgument, - /// An error occurred while serializing or deserializing. Closest to Python's `ValueError`, - /// as raised by `json.JSONDecodeError`. - Serde, - /// An unimplemented function was called. The analogue of Python's `NotImplementedError`. - NotImplemented, - /// A value did not have the expected type. The analogue of Python's `TypeError`. - MismatchedTypes, - /// An internal invariant was violated. The analogue of Python's `AssertionError`. - AssertionFailed, - /// An IO operation, or a call into the operating system or a device driver, failed. The - /// analogue of Python's `OSError`, which covers any system function that reports an error. - Io, -} - -impl VortexErrorKind { - /// The human-readable prefix used when displaying an error of this kind. - const fn prefix(self) -> &'static str { - match self { - Self::Other => "Other error: ", - Self::OutOfBounds => "Out of bounds error: ", - Self::NotFound => "Not found error: ", - Self::Overflow => "Overflow error: ", - Self::InvalidArgument => "Invalid argument error: ", - Self::Serde => "Serde error: ", - Self::NotImplemented => "Not implemented error: ", - Self::MismatchedTypes => "Mismatched types error: ", - Self::AssertionFailed => "Assertion failed error: ", - Self::Io => "IO error: ", - } - } -} - /// The top-level error type for Vortex. /// -/// An error is a [`VortexErrorKind`], a message, an optional underlying error, and a backtrace -/// captured at construction. Cloning is cheap: the payload is shared, never copied. +/// An error is a message, an optional underlying error, and a backtrace captured at +/// construction. Cloning is cheap: the payload is shared, never copied. /// /// The payload sits behind one pointer, so a `VortexResult` costs the same as `T` plus at /// most a word on the success path. Most results fit in two registers and are returned in them, @@ -144,7 +93,6 @@ const _: () = assert!(size_of::() == size_of::()); const _: () = assert!(size_of::>() == size_of::()); struct ErrorInner { - kind: VortexErrorKind, /// `None` defers the message to the source, keeping the `?` conversion path allocation-free. message: Option, origin: Origin, @@ -165,37 +113,27 @@ enum Origin { } impl VortexError { - /// Creates an error of the given kind carrying `message`. - pub fn new>(kind: VortexErrorKind, message: T) -> Self { - Self::from_parts(kind, Some(message.into()), None) + /// Creates an error carrying `message`. + pub fn new>(message: T) -> Self { + Self::from_parts(Some(message.into()), None) } - /// Wraps an underlying error as a Vortex error of the given kind. + /// Wraps an underlying error as a Vortex error. /// /// The wrapped error is preserved as the [`Error::source`], so callers that care about the /// concrete type can recover it with [`Error::source`] and `downcast_ref`. - pub fn wrap(kind: VortexErrorKind, source: E) -> Self - where - E: Into>, - { - Self::from_parts(kind, None, Some(source.into())) - } - - /// Wraps an underlying error that does not fit any more specific [`VortexErrorKind`]. pub fn external(source: E) -> Self where E: Into>, { - Self::wrap(VortexErrorKind::Other, source) + Self::from_parts(None, Some(source.into())) } fn from_parts( - kind: VortexErrorKind, message: Option, source: Option>, ) -> Self { Self(Arc::new(ErrorInner { - kind, message, origin: Origin::Own { source, @@ -204,12 +142,7 @@ impl VortexError { })) } - /// The classification of this error. - pub fn kind(&self) -> VortexErrorKind { - self.0.kind - } - - /// Adds additional context to an error, preserving its kind, source and backtrace. + /// Adds additional context to an error, preserving its source and backtrace. pub fn with_context>(mut self, msg: T) -> Self { let msg: ErrString = msg.into(); // Build the combined string directly: `msg` has already been through the @@ -220,7 +153,6 @@ impl VortexError { return self; } Self(Arc::new(ErrorInner { - kind: self.kind(), message: Some(message), origin: Origin::Context(self), })) @@ -252,7 +184,6 @@ impl VortexError { impl Display for VortexError { fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result { - f.write_str(self.kind().prefix())?; match (&self.0.message, self.source_ref()) { (Some(message), _) => Display::fmt(message, f)?, (None, Some(source)) => Display::fmt(source, f)?, @@ -344,22 +275,11 @@ impl VortexExpect for Option { /// A convenient macro for creating a VortexError. /// -/// The leading `Kind:` names the [`VortexErrorKind`] and is required: pick the kind that says -/// what went wrong, and `Other` only when none does. Every kind takes the same -/// `Kind: "format", args..` shape, so no kind gets a bespoke argument grammar that a format string -/// could be mistaken for. -/// -/// ``` -/// use vortex_error::{VortexErrorKind, vortex_err}; -/// -/// let err = vortex_err!(InvalidArgument: "negative length {}", -1); -/// assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); /// ``` +/// use vortex_error::vortex_err; /// -/// A message without a kind does not compile: -/// -/// ```compile_fail -/// let err = vortex_error::vortex_err!("negative length {}", -1); +/// let err = vortex_err!("negative length {}", -1); +/// assert!(err.to_string().starts_with("negative length -1")); /// ``` #[macro_export] macro_rules! vortex_err { @@ -369,18 +289,11 @@ macro_rules! vortex_err { (External: $err:expr $(,)?) => { $crate::__private::external($err) }; - ($kind:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { - $crate::__private::fmt_err($crate::VortexErrorKind::$kind, &format_args!($fmt $(, $arg)*)) - }; - ($kind:ident: $err:expr $(,)?) => { - $crate::__private::fmt_err($crate::VortexErrorKind::$kind, &format_args!("{}", $err)) + ($fmt:literal $(, $arg:expr)* $(,)?) => { + $crate::__private::fmt_err(&format_args!($fmt $(, $arg)*)) }; - ($fmt:literal $($rest:tt)*) => { - ::core::compile_error!(::core::concat!( - "vortex_err! needs a kind before its message, e.g. `vortex_err!(InvalidArgument: ", - ::core::stringify!($fmt), - ")`" - )) + ($err:expr $(,)?) => { + $crate::__private::fmt_err(&format_args!("{}", $err)) }; } @@ -395,19 +308,11 @@ macro_rules! vortex_bail { /// A macro that mirrors `assert!` but instead of panicking on a failed condition, /// it will immediately return an erroneous `VortexResult` to the calling context. /// -/// Without a message the error is an [`VortexErrorKind::AssertionFailed`] naming the condition. A -/// message needs a leading `Kind:`, as in [`vortex_err!`]: -/// -/// ```compile_fail -/// fn check(len: usize) -> vortex_error::VortexResult<()> { -/// vortex_error::vortex_ensure!(len > 0, "length must be positive"); -/// Ok(()) -/// } -/// ``` +/// Without a message the error names the condition. #[macro_export] macro_rules! vortex_ensure { ($cond:expr) => { - $crate::vortex_ensure!($cond, AssertionFailed: "{}", stringify!($cond)); + $crate::vortex_ensure!($cond, "{}", stringify!($cond)); }; ($cond:expr, $($tt:tt)*) => { if !$cond { @@ -422,8 +327,8 @@ macro_rules! vortex_ensure { /// Both values must implement [`PartialEq`] and [`Display`], and each is /// evaluated exactly once. Use [`vortex_ensure!`] for values that do not implement `Display`. /// -/// By default this returns an [`AssertionFailed`](VortexErrorKind::AssertionFailed) error that -/// shows both expressions and their values, so most callers do not need a message: +/// By default the error shows both expressions and their values, so most callers do not need a +/// message: /// /// ``` /// # use vortex_error::{VortexResult, vortex_ensure_eq}; @@ -433,22 +338,7 @@ macro_rules! vortex_ensure { /// } /// /// let err = check(3).unwrap_err().to_string(); -/// assert!(err.starts_with("Assertion failed error: `len == 2`\n left: 3\n right: 2")); -/// ``` -/// -/// A check on the caller's input, rather than on an internal invariant, names its kind, either -/// alone or before a message: -/// -/// ``` -/// # use vortex_error::{VortexErrorKind, VortexResult, vortex_ensure_eq}; -/// fn check(len: usize) -> VortexResult<()> { -/// vortex_ensure_eq!(len, 2, InvalidArgument); -/// Ok(()) -/// } -/// -/// let err = check(3).unwrap_err(); -/// assert_eq!(err.kind(), VortexErrorKind::InvalidArgument); -/// assert!(err.to_string().starts_with("Invalid argument error: `len == 2`\n left: 3\n right: 2")); +/// assert!(err.starts_with("`len == 2`\n left: 3\n right: 2")); /// ``` /// /// A message replaces the expressions. The values are still appended, so the message does not @@ -457,36 +347,23 @@ macro_rules! vortex_ensure { /// ``` /// # use vortex_error::{VortexResult, vortex_ensure_eq}; /// fn check(len: usize) -> VortexResult<()> { -/// vortex_ensure_eq!(len, 2, InvalidArgument: "map entries must have {} fields", 2); +/// vortex_ensure_eq!(len, 2, "map entries must have {} fields", 2); /// Ok(()) /// } /// /// let err = check(3).unwrap_err().to_string(); -/// assert!(err.starts_with( -/// "Invalid argument error: map entries must have 2 fields\n left: 3\n right: 2" -/// )); -/// ``` -/// -/// Like [`vortex_err!`], a message without a kind does not compile: -/// -/// ```compile_fail -/// fn check(len: usize) -> vortex_error::VortexResult<()> { -/// vortex_error::vortex_ensure_eq!(len, 2, "map entries must have 2 fields"); -/// Ok(()) -/// } +/// assert!(err.starts_with("map entries must have 2 fields\n left: 3\n right: 2")); /// ``` #[macro_export] macro_rules! vortex_ensure_eq { ($left:expr, $right:expr $(,)?) => { - $crate::vortex_ensure_eq!($left, $right, AssertionFailed) - }; - ($left:expr, $right:expr, $kind:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { match (&$left, &$right) { (left_val, right_val) => { if *left_val != *right_val { $crate::vortex_bail!( - $kind: "{}\n left: {}\n right: {}", - format_args!($fmt $(, $arg)*), + "`{} == {}`\n left: {}\n right: {}", + stringify!($left), + stringify!($right), left_val, right_val ); @@ -494,14 +371,13 @@ macro_rules! vortex_ensure_eq { } } }; - ($left:expr, $right:expr, $kind:ident $(,)?) => { + ($left:expr, $right:expr, $fmt:literal $(, $arg:expr)* $(,)?) => { match (&$left, &$right) { (left_val, right_val) => { if *left_val != *right_val { $crate::vortex_bail!( - $kind: "`{} == {}`\n left: {}\n right: {}", - stringify!($left), - stringify!($right), + "{}\n left: {}\n right: {}", + format_args!($fmt $(, $arg)*), left_val, right_val ); @@ -509,39 +385,21 @@ macro_rules! vortex_ensure_eq { } } }; - ($left:expr, $right:expr, $fmt:literal $($rest:tt)*) => { - ::core::compile_error!(::core::concat!( - "vortex_ensure_eq! needs a kind before its message, e.g. `vortex_ensure_eq!(a, b, ", - "InvalidArgument: ", - ::core::stringify!($fmt), - ")`" - )) - }; } /// A convenient macro for panicking with a VortexError in the presence of a programmer error /// (e.g., an invariant has been violated). /// -/// Like [`vortex_err!`], a message needs a leading `Kind:`; an existing error can be passed as is. -/// -/// ```compile_fail -/// vortex_error::vortex_panic!("unreachable state {}", 3); -/// ``` +/// It takes a message like [`vortex_err!`], or an existing error with an optional message to add +/// as context. #[macro_export] macro_rules! vortex_panic { (Context: $msg:literal, $err:expr) => {{ $crate::vortex_panic!($crate::vortex_err!(Context: $msg, $err)) }}; - ($kind:ident: $fmt:literal $(, $arg:expr)* $(,)?) => { - $crate::vortex_panic!($crate::vortex_err!($kind: $fmt, $($arg),*)) - }; // Before the `$err:expr` arms, which a bare message would otherwise match. - ($fmt:literal $($rest:tt)*) => { - ::core::compile_error!(::core::concat!( - "vortex_panic! needs a kind before its message, e.g. `vortex_panic!(AssertionFailed: ", - ::core::stringify!($fmt), - ")`" - )) + ($fmt:literal $(, $arg:expr)* $(,)?) => { + $crate::vortex_panic!($crate::vortex_err!($fmt $(, $arg)*)) }; ($err:expr, $fmt:literal $(, $arg:expr)* $(,)?) => { $crate::__private::panic_err_ctx($err, &format_args!($fmt $(, $arg)*)) @@ -559,60 +417,33 @@ impl From for VortexError { impl From for VortexError { fn from(value: arrow_schema::ArrowError) -> Self { - use arrow_schema::ArrowError::*; - let kind = match &value { - NotYetImplemented(_) => VortexErrorKind::NotImplemented, - // A cast or parse Arrow rejects is a value it cannot represent, not a type it - // cannot handle, which is why `int("x")` is a ValueError. - CastError(_) | ParseError(_) | DivideByZero | InvalidArgumentError(_) => { - VortexErrorKind::InvalidArgument - } - SchemaError(_) => VortexErrorKind::MismatchedTypes, - ArithmeticOverflow(_) - | DictionaryKeyOverflowError - | RunEndIndexOverflowError - | OffsetOverflowError(_) => VortexErrorKind::Overflow, - CsvError(_) | JsonError(_) | IpcError(_) | ParquetError(_) | CDataInterface(_) => { - VortexErrorKind::Serde - } - IoError(..) => VortexErrorKind::Io, - AvroError(_) => VortexErrorKind::Serde, - ExternalError(_) | MemoryError(_) | ComputeError(_) => VortexErrorKind::Other, - }; - VortexError::wrap(kind, value) + VortexError::external(value) } } #[cfg(feature = "flatbuffers")] impl From for VortexError { fn from(value: flatbuffers::InvalidFlatbuffer) -> Self { - VortexError::wrap(VortexErrorKind::Serde, value) + VortexError::external(value) } } impl From for VortexError { fn from(value: io::Error) -> Self { - VortexError::wrap(VortexErrorKind::Io, value) + VortexError::external(value) } } #[cfg(feature = "object_store")] impl From for VortexError { fn from(value: object_store::Error) -> Self { - VortexError::wrap(VortexErrorKind::Io, value) + VortexError::external(value) } } impl From for VortexError { fn from(value: jiff::Error) -> Self { - // A date that does not exist and a unit that makes no sense for the call are both what - // Python's datetime raises ValueError for; jiff reports anything else only as text. - let kind = if value.is_range() || value.is_invalid_parameter() { - VortexErrorKind::InvalidArgument - } else { - VortexErrorKind::Other - }; - VortexError::wrap(kind, value) + VortexError::external(value) } } @@ -629,25 +460,25 @@ impl From for VortexError { impl From for VortexError { fn from(value: TryFromIntError) -> Self { - VortexError::wrap(VortexErrorKind::Overflow, value) + VortexError::external(value) } } impl From for VortexError { fn from(value: prost::EncodeError) -> Self { - VortexError::wrap(VortexErrorKind::Serde, value) + VortexError::external(value) } } impl From for VortexError { fn from(value: prost::DecodeError) -> Self { - VortexError::wrap(VortexErrorKind::Serde, value) + VortexError::external(value) } } impl From for VortexError { fn from(value: prost::UnknownEnumValue) -> Self { - VortexError::wrap(VortexErrorKind::Serde, value) + VortexError::external(value) } } @@ -668,7 +499,6 @@ pub mod __private { use std::fmt::Arguments; use crate::VortexError; - use crate::VortexErrorKind; #[doc(hidden)] #[inline] @@ -682,8 +512,8 @@ pub mod __private { #[cold] #[inline(never)] #[must_use] - pub fn fmt_err(kind: VortexErrorKind, args: &Arguments<'_>) -> VortexError { - VortexError::new(kind, args.to_string()) + pub fn fmt_err(args: &Arguments<'_>) -> VortexError { + VortexError::new(args.to_string()) } #[doc(hidden)] @@ -727,9 +557,6 @@ pub mod __private { #[cold] #[inline(never)] pub fn option_expect_failed(msg: &'static str) -> ! { - panic!( - "{}", - VortexError::new(VortexErrorKind::AssertionFailed, msg) - ) + panic!("{}", VortexError::new(msg)) } } diff --git a/vortex-error/tests/ensure.rs b/vortex-error/tests/ensure.rs index 3fd9369b07c..ba0f046670b 100644 --- a/vortex-error/tests/ensure.rs +++ b/vortex-error/tests/ensure.rs @@ -8,18 +8,13 @@ mod tests { use std::cell::Cell; use vortex_error::VortexError; - use vortex_error::VortexErrorKind; use vortex_error::VortexResult; - /// Asserts the error's kind and the message shown after its kind prefix. - fn assert_error(error: &VortexError, kind: VortexErrorKind, message: &str) { - assert_eq!(error.kind(), kind, "{error}"); + /// Asserts the message shown, ignoring a captured backtrace. + fn assert_error(error: &VortexError, message: &str) { let shown = error.to_string(); - let body = shown - .split_once(": ") - .map_or(shown.as_str(), |(_, body)| body); assert!( - body == message || body.starts_with(&format!("{message}\nBacktrace:")), + shown == message || shown.starts_with(&format!("{message}\nBacktrace:")), "{shown:?}" ); } @@ -55,7 +50,6 @@ mod tests { assert_eq!(right.get(), 3); assert_error( &error, - VortexErrorKind::AssertionFailed, "`left.replace(left.get() + 1) == right.replace(right.get() + 1)`\n left: 1\n right: 2", ); } @@ -70,7 +64,7 @@ mod tests { vortex_error::vortex_ensure_eq!( &left, right, - InvalidArgument: "{context} mismatch {}", + "{context} mismatch {}", message_calls.replace(message_calls.get() + 1), ); Ok(()) @@ -82,46 +76,22 @@ mod tests { let error = check(&right).unwrap_err(); assert_eq!(message_calls.get(), 1); - assert_error( - &error, - VortexErrorKind::InvalidArgument, - "field mismatch 0\n left: left\n right: right", - ); + assert_error(&error, "field mismatch 0\n left: left\n right: right"); assert_eq!(left, "left"); assert_eq!(right, "right"); Ok(()) } #[test] - fn explicit_variant_keeps_context_and_values() { - let check = || -> VortexResult<()> { - vortex_error::vortex_ensure_eq!(1, 2, InvalidArgument: "expected {} fields", 2,); - Ok(()) - }; - - let error = check().unwrap_err(); - - assert_error( - &error, - VortexErrorKind::InvalidArgument, - "expected 2 fields\n left: 1\n right: 2", - ); - } - - #[test] - fn kind_without_message_reports_the_values_compared() { + fn message_keeps_context_and_values() { let check = || -> VortexResult<()> { - vortex_error::vortex_ensure_eq!(1 + 1, 3, OutOfBounds); + vortex_error::vortex_ensure_eq!(1, 2, "expected {} fields", 2,); Ok(()) }; let error = check().unwrap_err(); - assert_error( - &error, - VortexErrorKind::OutOfBounds, - "`1 + 1 == 3`\n left: 2\n right: 3", - ); + assert_error(&error, "expected 2 fields\n left: 1\n right: 2"); } #[test] @@ -133,6 +103,6 @@ mod tests { let error = check().unwrap_err(); - assert_error(&error, VortexErrorKind::AssertionFailed, "false"); + assert_error(&error, "false"); } } diff --git a/vortex-error/tests/error.rs b/vortex-error/tests/error.rs new file mode 100644 index 00000000000..3592bb87ff4 --- /dev/null +++ b/vortex-error/tests/error.rs @@ -0,0 +1,117 @@ +// SPDX-License-Identifier: Apache-2.0 +// SPDX-FileCopyrightText: Copyright the Vortex contributors + +// This seems to be a bug in the lint - https://github.com/rust-lang/rust-clippy/issues/11024 +#![expect(clippy::tests_outside_test_module)] + +use std::error::Error; +use std::io; +use std::sync::Arc; + +use vortex_error::VortexError; +use vortex_error::vortex_err; + +#[test] +fn test_message_is_displayed_as_written() { + assert!( + vortex_err!("index {} past {}", 5, 3) + .to_string() + .starts_with("index 5 past 3") + ); +} + +#[test] +fn test_with_context_preserves_source() { + let err = VortexError::from(io::Error::other("disk on fire")).with_context("while reading"); + + assert!( + err.source() + .and_then(|source| source.downcast_ref::()) + .is_some(), + "context must not hide the underlying error" + ); + + let display = err.to_string(); + assert!( + display.starts_with("while reading:\n disk on fire"), + "{display}" + ); +} + +#[test] +fn test_nested_context() { + let err = vortex_err!("bad footer") + .with_context("reading layout") + .with_context("opening file"); + + let display = err.to_string(); + assert!( + display.starts_with("opening file:\n reading layout:\n bad footer"), + "{display}" + ); +} + +#[test] +fn test_external_preserves_concrete_source() { + let err = vortex_err!(External: io::Error::from(io::ErrorKind::NotFound)); + + assert_eq!( + err.source() + .and_then(|source| source.downcast_ref::()) + .map(io::Error::kind), + Some(io::ErrorKind::NotFound) + ); +} + +#[test] +fn test_clone_and_shared_round_trip() { + let err = vortex_err!("device disappeared"); + let clone = err.clone(); + + assert_eq!(clone.to_string(), err.to_string()); + + // An `Arc` is unwrapped when uniquely held and cloned otherwise; both keep the message. + let shared = Arc::new(err); + let borrowed = VortexError::from(&shared); + let owned = VortexError::from(shared); + + assert_eq!(borrowed.to_string(), owned.to_string()); +} + +#[test] +fn test_context_on_a_clone_leaves_the_other_clone_alone() { + let err = VortexError::from(io::Error::other("disk on fire")); + let clone = err.clone(); + + // The payload is shared, so this context cannot be written into it in place. + let with_context = clone.with_context("while reading"); + + let original = err.to_string(); + assert!( + original.starts_with("disk on fire") && !original.contains("while reading"), + "{original}" + ); + let display = with_context.to_string(); + assert!( + display.starts_with("while reading:\n disk on fire"), + "{display}" + ); + assert!( + with_context + .source() + .and_then(|source| source.downcast_ref::()) + .is_some(), + "context on a shared error must still expose the underlying error" + ); +} + +#[test] +fn test_arrow_error_is_kept_as_the_source() { + let err = VortexError::from(arrow_schema::ArrowError::ComputeError("x".into())); + assert!( + err.source() + .and_then(|source| source.downcast_ref::()) + .is_some(), + "the Arrow error is kept as the source" + ); +} diff --git a/vortex-error/tests/fmt.rs b/vortex-error/tests/fmt.rs index 993ad964bc9..c09458493aa 100644 --- a/vortex-error/tests/fmt.rs +++ b/vortex-error/tests/fmt.rs @@ -13,11 +13,11 @@ use vortex_error::vortex_err; #[inline(never)] fn test_basic_display() { temp_env::with_var("RUST_BACKTRACE", Some("1"), || { - let err = vortex_err!(Other: "this is bad"); + let err = vortex_err!("this is bad"); let display = err.to_string(); assert!( - display.contains("Other error: this is bad"), + display.contains("this is bad"), "should contain error message" ); assert!( @@ -45,9 +45,7 @@ fn test_from_arrow_with_backtrace() { let display = vx_error.to_string(); assert!( - display.contains( - "Not implemented error: Not yet implemented: This feature isn't implemented yet" - ), + display.contains("Not yet implemented: This feature isn't implemented yet"), "should contain arrow error message" ); assert!( @@ -72,9 +70,7 @@ fn test_from_arrow_no_backtrace() { let display = vx_error.to_string(); assert!( - display.contains( - "Not implemented error: Not yet implemented: This feature isn't implemented yet" - ), + display.contains("Not yet implemented: This feature isn't implemented yet"), "should contain arrow error message" ); assert!( diff --git a/vortex-error/tests/kind.rs b/vortex-error/tests/kind.rs deleted file mode 100644 index 99f17776191..00000000000 --- a/vortex-error/tests/kind.rs +++ /dev/null @@ -1,217 +0,0 @@ -// SPDX-License-Identifier: Apache-2.0 -// SPDX-FileCopyrightText: Copyright the Vortex contributors - -// This seems to be a bug in the lint - https://github.com/rust-lang/rust-clippy/issues/11024 -#![expect(clippy::tests_outside_test_module)] - -use std::error::Error; -use std::io; -use std::sync::Arc; - -use vortex_error::VortexError; -use vortex_error::VortexErrorKind; -use vortex_error::vortex_err; - -#[test] -fn test_other_err_is_other() { - assert_eq!(vortex_err!(Other: "boom").kind(), VortexErrorKind::Other); -} - -#[test] -fn test_tagged_err_carries_kind() { - // Every kind takes the same `Kind: "format", args..` shape. - let cases: [(VortexError, VortexErrorKind); 8] = [ - ( - vortex_err!(InvalidArgument: "bad {}", 1), - VortexErrorKind::InvalidArgument, - ), - ( - vortex_err!(OutOfBounds: "index {} past {}", 5, 3), - VortexErrorKind::OutOfBounds, - ), - ( - vortex_err!(MismatchedTypes: "want i32, got {}", "u8"), - VortexErrorKind::MismatchedTypes, - ), - ( - vortex_err!(NotImplemented: "take on {}", "Sparse"), - VortexErrorKind::NotImplemented, - ), - ( - vortex_err!(NotFound: "no field {}", "a"), - VortexErrorKind::NotFound, - ), - ( - vortex_err!(Overflow: "{} exceeds u32", 1u64 << 40), - VortexErrorKind::Overflow, - ), - (vortex_err!(Serde: "corrupt footer"), VortexErrorKind::Serde), - ( - vortex_err!(AssertionFailed: "invariant broken"), - VortexErrorKind::AssertionFailed, - ), - ]; - for (err, kind) in cases { - assert_eq!(err.kind(), kind, "{err}"); - } -} - -#[test] -fn test_kind_prefixes_the_display() { - assert!( - vortex_err!(NotFound: "no field a") - .to_string() - .starts_with("Not found error: no field a") - ); - assert!( - vortex_err!(Overflow: "too big") - .to_string() - .starts_with("Overflow error: too big") - ); -} - -#[test] -fn test_int_conversion_is_overflow() { - // `?` on a fallible integer cast must land in Overflow, not Other. - let err = VortexError::from(u8::try_from(300u32).unwrap_err()); - assert_eq!(err.kind(), VortexErrorKind::Overflow); -} - -#[test] -fn test_with_context_preserves_kind_and_source() { - let err = VortexError::from(io::Error::other("disk on fire")).with_context("while reading"); - - assert_eq!(err.kind(), VortexErrorKind::Io); - assert!( - err.source() - .and_then(|source| source.downcast_ref::()) - .is_some(), - "context must not hide the underlying error" - ); - - let display = err.to_string(); - assert!( - display.starts_with("IO error: while reading:\n disk on fire"), - "{display}" - ); -} - -#[test] -fn test_nested_context() { - let err = vortex_err!(Serde: "bad footer") - .with_context("reading layout") - .with_context("opening file"); - - assert_eq!(err.kind(), VortexErrorKind::Serde); - let display = err.to_string(); - assert!( - display.starts_with("Serde error: opening file:\n reading layout:\n bad footer"), - "{display}" - ); -} - -#[test] -fn test_external_preserves_concrete_source() { - let err = vortex_err!(External: io::Error::from(io::ErrorKind::NotFound)); - - assert_eq!(err.kind(), VortexErrorKind::Other); - assert_eq!( - err.source() - .and_then(|source| source.downcast_ref::()) - .map(io::Error::kind), - Some(io::ErrorKind::NotFound) - ); -} - -#[test] -fn test_clone_and_shared_round_trip() { - let err = vortex_err!(Io: "device disappeared"); - let clone = err.clone(); - - assert_eq!(clone.kind(), err.kind()); - assert_eq!(clone.to_string(), err.to_string()); - - // An `Arc` is unwrapped when uniquely held and cloned otherwise; both keep the classification. - let shared = Arc::new(err); - let borrowed = VortexError::from(&shared); - let owned = VortexError::from(shared); - - assert_eq!(borrowed.kind(), VortexErrorKind::Io); - assert_eq!(owned.kind(), VortexErrorKind::Io); - assert_eq!(borrowed.to_string(), owned.to_string()); -} - -#[test] -fn test_context_on_a_clone_leaves_the_other_clone_alone() { - let err = VortexError::from(io::Error::other("disk on fire")); - let clone = err.clone(); - - // The payload is shared, so this context cannot be written into it in place. - let with_context = clone.with_context("while reading"); - - let original = err.to_string(); - assert!( - original.starts_with("IO error: disk on fire") && !original.contains("while reading"), - "{original}" - ); - let display = with_context.to_string(); - assert!( - display.starts_with("IO error: while reading:\n disk on fire"), - "{display}" - ); - assert_eq!(with_context.kind(), VortexErrorKind::Io); - assert!( - with_context - .source() - .and_then(|source| source.downcast_ref::()) - .is_some(), - "context on a shared error must still expose the underlying error" - ); -} - -#[test] -fn test_arrow_error_is_classified_by_variant() { - use arrow_schema::ArrowError; - - let cases = [ - ( - ArrowError::NotYetImplemented("x".into()), - VortexErrorKind::NotImplemented, - ), - ( - ArrowError::ArithmeticOverflow("x".into()), - VortexErrorKind::Overflow, - ), - ( - ArrowError::SchemaError("x".into()), - VortexErrorKind::MismatchedTypes, - ), - ( - ArrowError::IoError("x".into(), io::Error::other("x")), - VortexErrorKind::Io, - ), - (ArrowError::IpcError("x".into()), VortexErrorKind::Serde), - ( - ArrowError::InvalidArgumentError("x".into()), - VortexErrorKind::InvalidArgument, - ), - (ArrowError::ComputeError("x".into()), VortexErrorKind::Other), - ]; - for (arrow, kind) in cases { - let err = VortexError::from(arrow); - assert_eq!(err.kind(), kind, "{err}"); - assert!( - err.source().is_some(), - "the Arrow error is kept as the source" - ); - } -} - -#[test] -fn test_jiff_error_is_classified() { - let no_such_date = jiff::civil::Date::new(2025, 2, 29).unwrap_err(); - assert_eq!( - VortexError::from(no_such_date).kind(), - VortexErrorKind::InvalidArgument - ); -} diff --git a/vortex-expr/src/analysis/referenced_field_paths.rs b/vortex-expr/src/analysis/referenced_field_paths.rs index 185f2455ffe..55cec7afc5e 100644 --- a/vortex-expr/src/analysis/referenced_field_paths.rs +++ b/vortex-expr/src/analysis/referenced_field_paths.rs @@ -84,7 +84,7 @@ impl NodeFolderContext for ReferencedFieldPaths { let child_fields = node.children()[0] .dtype() .as_struct_fields_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Select child is not a struct"))?; + .ok_or_else(|| vortex_err!("Select child is not a struct"))?; let included_fields = selection.normalize_to_included_fields(child_fields.names())?; let mut narrowed = Vec::with_capacity(requested.len()); diff --git a/vortex-expr/src/stats/rewrite.rs b/vortex-expr/src/stats/rewrite.rs index 3a770bbc753..968fbfad9ba 100644 --- a/vortex-expr/src/stats/rewrite.rs +++ b/vortex-expr/src/stats/rewrite.rs @@ -91,7 +91,7 @@ fn ensure_predicate(expr: &BoundExpression) -> VortexResult<()> { let dtype = expr.dtype(); vortex_ensure!( matches!(dtype, DType::Bool(_)), - MismatchedTypes: "Stats rewrites require a boolean predicate, got {dtype}", + "Stats rewrites require a boolean predicate, got {dtype}", ); Ok(()) } diff --git a/vortex-expr/src/transform/bound_partition.rs b/vortex-expr/src/transform/bound_partition.rs index d6093c43626..88ef5287062 100644 --- a/vortex-expr/src/transform/bound_partition.rs +++ b/vortex-expr/src/transform/bound_partition.rs @@ -138,11 +138,7 @@ where /// Replace the partition expressions and update every root dtype in the recombination tree. pub fn replace_partitions(&mut self, partitions: Box<[BoundExpression]>) -> VortexResult<()> { - vortex_ensure_eq!( - partitions.len(), - self.partition_names.len(), - InvalidArgument - ); + vortex_ensure_eq!(partitions.len(), self.partition_names.len()); let root_dtype = partition_root_dtype(&self.partition_names, &partitions); let root = replace_root_dtype(self.root.clone(), root_dtype)?; diff --git a/vortex-ffi/cinclude/vortex.h b/vortex-ffi/cinclude/vortex.h index f233647fdd2..da574f03b4f 100644 --- a/vortex-ffi/cinclude/vortex.h +++ b/vortex-ffi/cinclude/vortex.h @@ -211,49 +211,13 @@ typedef enum { */ typedef enum { /** - * All other errors + * An error returned by Vortex */ VX_ERROR_CODE_OTHER = 0, - /** - * Index out of bounds - */ - VX_ERROR_CODE_OUT_OF_BOUNDS = 1, - /** - * An invalid argument was provided. - */ - VX_ERROR_CODE_INVALID_ARGUMENT = 3, - /** - * Serialization/deserialization error - */ - VX_ERROR_CODE_SERIALIZATION = 4, - /** - * Unimplemented function - */ - VX_ERROR_CODE_NOT_IMPLEMENTED = 5, - /** - * Type mismatch - */ - VX_ERROR_CODE_MISMATCHED_TYPES = 6, - /** - * Assertion failed - */ - VX_ERROR_CODE_ASSERTION_FAILED = 7, - /** - * An IO operation, or a call into the operating system or a device driver, failed - */ - VX_ERROR_CODE_IO = 8, /** * Panic inside FFI */ VX_ERROR_CODE_PANIC = 9, - /** - * A name was looked up and nothing was bound to it - */ - VX_ERROR_CODE_NOT_FOUND = 10, - /** - * A numeric value does not fit its target type - */ - VX_ERROR_CODE_OVERFLOW = 11, } vx_error_code; /** diff --git a/vortex-ffi/examples/hello_vortex.rs b/vortex-ffi/examples/hello_vortex.rs index 5b44abfbef7..93ed17772f1 100644 --- a/vortex-ffi/examples/hello_vortex.rs +++ b/vortex-ffi/examples/hello_vortex.rs @@ -79,7 +79,7 @@ pub fn main() -> VortexResult<()> { println!("C compilation failed:"); println!("Stdout: {}", String::from_utf8_lossy(&output.stdout)); println!("Stderr: {}", String::from_utf8_lossy(&output.stderr)); - return Err(vortex_err!(Other: "C compilation failed")); + return Err(vortex_err!("C compilation failed")); } // Use a fixed path in the working directory instead of temp file @@ -129,7 +129,7 @@ pub fn main() -> VortexResult<()> { println!("✅ FFI example ran successfully! (Exit code issues during cleanup are known)"); } else if !output.status.success() { println!("Command failed with exit code: {:?}", output.status.code()); - return Err(vortex_err!(Other: "C binary execution failed")); + return Err(vortex_err!("C binary execution failed")); } else { println!("✅ Success!"); } diff --git a/vortex-ffi/src/array.rs b/vortex-ffi/src/array.rs index c29bd27df21..e339215c2e0 100644 --- a/vortex-ffi/src/array.rs +++ b/vortex-ffi/src/array.rs @@ -119,7 +119,7 @@ impl vx_bool_view { /// `array` must be null or a valid `vx_array` pointer created by this crate, and must stay valid /// for the returned reference. pub unsafe fn vx_array_ref<'a>(array: *const vx_array) -> VortexResult<&'a ArrayRef> { - vortex_ensure!(!array.is_null(), InvalidArgument: "null vx_array"); + vortex_ensure!(!array.is_null(), "null vx_array"); Ok(vx_array::as_ref(array)) } @@ -275,14 +275,14 @@ pub unsafe extern "C-unwind" fn vx_array_get_field( let array = vx_array::as_ref(array); let struct_array = array.as_opt::().ok_or_else(|| { vortex_err!( - MismatchedTypes: "vx_array_get_field requires a canonical Struct array, got {}", + "vx_array_get_field requires a canonical Struct array, got {}", array.encoding_id() ) })?; let field_array = struct_array .unmasked_field_opt(index) - .ok_or_else(|| vortex_err!(OutOfBounds: "Field index out of bounds"))? + .ok_or_else(|| vortex_err!("Field index out of bounds"))? .clone(); Ok(vx_array::new(field_array)) @@ -454,11 +454,11 @@ pub extern "C-unwind" fn vx_array_new_bool( vortex_ensure!(!validity.is_null()); let bits = unsafe { &*view }; let validity = unsafe { &*validity }; - vortex_ensure!(bits.bit_offset < 8, InvalidArgument: "bit_offset must be in [0; 8)"); + vortex_ensure!(bits.bit_offset < 8, "bit_offset must be in [0; 8)"); let byte_len = bits.len(); let slice = if bits.ptr.is_null() { - vortex_ensure_eq!(byte_len, 0, InvalidArgument: "nonzero length but null pointer for view"); + vortex_ensure_eq!(byte_len, 0, "nonzero length but null pointer for view"); &[] } else { unsafe { std::slice::from_raw_parts(bits.ptr, byte_len) } @@ -498,8 +498,8 @@ pub unsafe extern "C-unwind" fn vx_array_from_arrow( error_out: *mut *mut vx_error, ) -> *const vx_array { try_or_default(error_out, || { - vortex_ensure!(!array.is_null(), InvalidArgument: "null arrow array"); - vortex_ensure!(!schema.is_null(), InvalidArgument: "null arrow schema"); + vortex_ensure!(!array.is_null(), "null arrow array"); + vortex_ensure!(!schema.is_null(), "null arrow schema"); let session = vx_session::as_ref(session); let ffi_array = unsafe { ptr::replace(array, FFI_ArrowArray::empty()) }; let ffi_schema = unsafe { ptr::replace(schema, FFI_ArrowSchema::empty()) }; @@ -521,7 +521,7 @@ unsafe fn varbinview_at( ) -> vx_view { try_or(error_out, vx_view::null(), || { let array = unsafe { vx_array_ref(array) }?; - vortex_ensure!(index < array.len(), OutOfBounds: "index {index} out of bounds"); + vortex_ensure!(index < array.len(), "index {index} out of bounds"); let dtype_matches = if want_utf8 { matches!(array.dtype(), DType::Utf8(_)) } else { @@ -529,12 +529,12 @@ unsafe fn varbinview_at( }; vortex_ensure!( dtype_matches, - MismatchedTypes: "expected a {} array, got {}", + "expected a {} array, got {}", if want_utf8 { "Utf8" } else { "Binary" }, array.dtype() ); let Some(views) = array.as_opt::() else { - vortex_bail!(MismatchedTypes: "expected a canonical array, got {}", array.encoding_id()); + vortex_bail!("expected a canonical array, got {}", array.encoding_id()); }; Ok(vx_view::from_bytes(views.bytes_at(index).as_slice())) }) @@ -586,7 +586,7 @@ pub unsafe extern "C-unwind" fn vx_array_get_bool(array: *const vx_array, index: let bits = bool_array.to_bit_buffer(); if index >= bits.len() { vortex_panic!( - OutOfBounds: "index {index} out of bounds for array of length {}", + "index {index} out of bounds for array of length {}", bits.len() ); } @@ -648,14 +648,14 @@ pub unsafe extern "C-unwind" fn vx_array_data_ptr_primitive( let array = vx_array::as_ref(array); let primitive = array.as_opt::().ok_or_else(|| { vortex_err!( - InvalidArgument: "vx_array_data_ptr_primitive requires a canonical Primitive array, got {}", + "vx_array_data_ptr_primitive requires a canonical Primitive array, got {}", array.encoding_id() ) })?; let bytes = primitive .buffer_handle() .as_host_opt() - .ok_or_else(|| vortex_err!(InvalidArgument: "array buffer is not in host memory"))?; + .ok_or_else(|| vortex_err!("array buffer is not in host memory"))?; Ok(bytes.as_ptr().cast()) }) } @@ -686,7 +686,7 @@ pub unsafe extern "C-unwind" fn vx_array_data_ptr_bool( let array = unsafe { vx_array_ref(array) }?; let array = array.as_opt::().ok_or_else(|| { let id = array.encoding_id(); - vortex_err!(InvalidArgument: "vx_array_data_ptr_bool requires a canonical Bool array, got {id}") + vortex_err!("vx_array_data_ptr_bool requires a canonical Bool array, got {id}") })?; let bits = array.to_bit_buffer(); let ptr = bits.inner().as_ptr().cast(); diff --git a/vortex-ffi/src/data_source.rs b/vortex-ffi/src/data_source.rs index cc66df2470e..a881b3ac085 100644 --- a/vortex-ffi/src/data_source.rs +++ b/vortex-ffi/src/data_source.rs @@ -110,7 +110,7 @@ unsafe fn data_source_new( let opts = unsafe { &*opts }; vortex_ensure!(!opts.paths.is_null()); - vortex_ensure!(opts.paths_len > 0, InvalidArgument: "empty paths"); + vortex_ensure!(opts.paths_len > 0, "empty paths"); let paths = unsafe { slice::from_raw_parts(opts.paths, opts.paths_len) }; let mut data_source = MultiFileDataSource::new(session.clone()); diff --git a/vortex-ffi/src/dtype.rs b/vortex-ffi/src/dtype.rs index 4875a0e7bf8..316b7e35c70 100644 --- a/vortex-ffi/src/dtype.rs +++ b/vortex-ffi/src/dtype.rs @@ -74,10 +74,10 @@ impl From<&DType> for vx_dtype_variant { DType::List(..) => vx_dtype_variant::DTYPE_LIST, DType::FixedSizeList(..) => vx_dtype_variant::DTYPE_FIXED_SIZE_LIST, DType::Struct(..) => vx_dtype_variant::DTYPE_STRUCT, - DType::Map(..) => vortex_panic!(NotImplemented: "Map is not supported in FFI yet"), - DType::Union(..) => vortex_panic!(NotImplemented: "Union is not supported in FFI yet"), + DType::Map(..) => vortex_panic!("Map is not supported in FFI yet"), + DType::Union(..) => vortex_panic!("Union is not supported in FFI yet"), DType::Variant(_) => { - vortex_panic!(NotImplemented: "Variant is not supported in FFI yet") + vortex_panic!("Variant is not supported in FFI yet") } DType::Extension(_) => vx_dtype_variant::DTYPE_EXTENSION, } @@ -255,7 +255,7 @@ pub unsafe extern "C-unwind" fn vx_dtype_fixed_size_list_size(dtype: *const vx_d let dtype_ref = vx_dtype::as_ref(dtype); match dtype_ref { DType::FixedSizeList(_, size, _) => *size, - _ => vortex_panic!(MismatchedTypes: "not a fixed-size list dtype"), + _ => vortex_panic!("not a fixed-size list dtype"), } } @@ -296,7 +296,7 @@ pub unsafe extern "C-unwind" fn vx_dtype_from_arrow_schema( err: *mut *mut vx_error, ) -> *const vx_dtype { try_or_default(err, || { - vortex_ensure!(!schema.is_null(), InvalidArgument: "null arrow schema"); + vortex_ensure!(!schema.is_null(), "null arrow schema"); let session = vx_session::as_ref(session); let ffi_schema = unsafe { ptr::replace(schema, FFI_ArrowSchema::empty()) }; let arrow_schema = Schema::try_from(&ffi_schema)?; diff --git a/vortex-ffi/src/error.rs b/vortex-ffi/src/error.rs index f63a73bf932..2b2956cf385 100644 --- a/vortex-ffi/src/error.rs +++ b/vortex-ffi/src/error.rs @@ -7,8 +7,6 @@ use std::panic::catch_unwind; use std::ptr; use std::sync::Arc; -use vortex::error::VortexError; -use vortex::error::VortexErrorKind; use vortex::error::VortexResult; use crate::box_wrapper; @@ -18,45 +16,12 @@ use crate::string::vx_view; #[repr(C)] #[derive(Clone, Copy, PartialEq, Eq, Debug)] pub enum vx_error_code { - /// All other errors + /// An error returned by Vortex VX_ERROR_CODE_OTHER = 0, - /// Index out of bounds - VX_ERROR_CODE_OUT_OF_BOUNDS = 1, - // 2 is retired. It was VX_ERROR_CODE_COMPUTE, which classified an error by the code it came - // from rather than by what went wrong. Leaving the value unused keeps every code below stable. - /// An invalid argument was provided. - VX_ERROR_CODE_INVALID_ARGUMENT = 3, - /// Serialization/deserialization error - VX_ERROR_CODE_SERIALIZATION = 4, - /// Unimplemented function - VX_ERROR_CODE_NOT_IMPLEMENTED = 5, - /// Type mismatch - VX_ERROR_CODE_MISMATCHED_TYPES = 6, - /// Assertion failed - VX_ERROR_CODE_ASSERTION_FAILED = 7, - /// An IO operation, or a call into the operating system or a device driver, failed - VX_ERROR_CODE_IO = 8, + // 1 to 8, 10 and 11 are retired. They classified Vortex errors, which no longer carry a + // classification. Leaving them unused keeps VX_ERROR_CODE_PANIC stable. /// Panic inside FFI VX_ERROR_CODE_PANIC = 9, - /// A name was looked up and nothing was bound to it - VX_ERROR_CODE_NOT_FOUND = 10, - /// A numeric value does not fit its target type - VX_ERROR_CODE_OVERFLOW = 11, -} - -fn error_code(error: &VortexError) -> vx_error_code { - match error.kind() { - VortexErrorKind::OutOfBounds => vx_error_code::VX_ERROR_CODE_OUT_OF_BOUNDS, - VortexErrorKind::NotFound => vx_error_code::VX_ERROR_CODE_NOT_FOUND, - VortexErrorKind::Overflow => vx_error_code::VX_ERROR_CODE_OVERFLOW, - VortexErrorKind::InvalidArgument => vx_error_code::VX_ERROR_CODE_INVALID_ARGUMENT, - VortexErrorKind::Serde => vx_error_code::VX_ERROR_CODE_SERIALIZATION, - VortexErrorKind::NotImplemented => vx_error_code::VX_ERROR_CODE_NOT_IMPLEMENTED, - VortexErrorKind::MismatchedTypes => vx_error_code::VX_ERROR_CODE_MISMATCHED_TYPES, - VortexErrorKind::AssertionFailed => vx_error_code::VX_ERROR_CODE_ASSERTION_FAILED, - VortexErrorKind::Io => vx_error_code::VX_ERROR_CODE_IO, - _ => vx_error_code::VX_ERROR_CODE_OTHER, - } } pub(crate) struct VortexFFIError { @@ -120,7 +85,7 @@ pub fn try_or_default( value } Ok(Err(err)) => { - write_error_with_code(error_out, &err.to_string(), error_code(&err)); + write_error(error_out, &err.to_string()); T::default() } Err(payload) => { @@ -149,7 +114,7 @@ pub fn try_or( value } Ok(Err(err)) => { - write_error_with_code(error_out, &err.to_string(), error_code(&err)); + write_error(error_out, &err.to_string()); error_value } Err(payload) => { @@ -192,17 +157,14 @@ mod tests { fn test_try_or_null_error_out() { // A null error_out must be tolerated on both the success and failure paths. assert_eq!(try_or(ptr::null_mut(), -1, || Ok(42)), 42); - assert_eq!( - try_or(ptr::null_mut(), -1, || Err(vortex_err!(Other: "boom"))), - -1 - ); + assert_eq!(try_or(ptr::null_mut(), -1, || Err(vortex_err!("boom"))), -1); } #[test] fn test_try_or_default_null_error_out() { assert_eq!(try_or_default(ptr::null_mut(), || Ok(42)), 42); assert_eq!( - try_or_default::(ptr::null_mut(), || Err(vortex_err!(Other: "boom"))), + try_or_default::(ptr::null_mut(), || Err(vortex_err!("boom"))), 0 ); } @@ -211,10 +173,7 @@ mod tests { fn test_try_or_writes_and_clears_error_out() { let mut error: *mut vx_error = ptr::null_mut(); - assert_eq!( - try_or(&raw mut error, -1, || Err(vortex_err!(Other: "boom"))), - -1 - ); + assert_eq!(try_or(&raw mut error, -1, || Err(vortex_err!("boom"))), -1); assert!(!error.is_null()); unsafe { vx_error_free(error) }; @@ -242,12 +201,16 @@ mod tests { assert_eq!( try_or(&raw mut error, -1, || Err::(vortex_err!( - OutOfBounds: "index {} out of bounds from {} to {}", 5, 0, 3))), + "index {} out of bounds from {} to {}", + 5, + 0, + 3 + ))), -1 ); assert_eq!( unsafe { vx_error_get_code(error) }, - vx_error_code::VX_ERROR_CODE_OUT_OF_BOUNDS + vx_error_code::VX_ERROR_CODE_OTHER ); unsafe { vx_error_free(error) }; diff --git a/vortex-ffi/src/lib.rs b/vortex-ffi/src/lib.rs index bc9cf136cd4..b0168851911 100644 --- a/vortex-ffi/src/lib.rs +++ b/vortex-ffi/src/lib.rs @@ -108,7 +108,7 @@ macro_rules! box_wrapper { /// Extract an owned reference. pub(crate) fn into_box(ptr: *mut $ffi_ident) -> Box<$T>{ if ptr.is_null() { - vortex::error::vortex_panic!(InvalidArgument: "null pointer"); + vortex::error::vortex_panic!("null pointer"); } unsafe { Box::from_raw(ptr.cast::<$T>()) } } @@ -173,7 +173,7 @@ pub(crate) unsafe fn to_field_names( names: *const vx_view, len: usize, ) -> VortexResult> { - vortex_ensure!(!names.is_null() || len == 0, InvalidArgument: "null names pointer"); + vortex_ensure!(!names.is_null() || len == 0, "null names pointer"); (0..len) .map(|i| unsafe { to_field_name(*names.add(i)) }) .collect() diff --git a/vortex-ffi/src/scalar.rs b/vortex-ffi/src/scalar.rs index d5ae5833a85..d9c22083667 100644 --- a/vortex-ffi/src/scalar.rs +++ b/vortex-ffi/src/scalar.rs @@ -245,13 +245,13 @@ pub unsafe extern "C-unwind" fn vx_scalar_new_extension( let storage = vx_scalar::as_ref(storage); let DType::Extension(ext) = dtype else { vortex_bail!( - MismatchedTypes: "vx_scalar_new_extension: dtype {} is not an extension type", + "vx_scalar_new_extension: dtype {} is not an extension type", dtype ); }; vortex_ensure!( storage.dtype().eq_ignore_nullability(ext.storage_dtype()), - MismatchedTypes: "vx_scalar_new_extension: storage scalar dtype {} does not match extension storage dtype {}", + "vx_scalar_new_extension: storage scalar dtype {} does not match extension storage dtype {}", storage.dtype(), ext.storage_dtype() ); @@ -422,7 +422,7 @@ pub unsafe extern "C-unwind" fn vx_scalar_new_struct( err: *mut *mut vx_error, ) -> *mut vx_scalar { try_or(err, ptr::null_mut(), || { - vortex_ensure!(!struct_dtype.is_null(), InvalidArgument: "struct dtype is null"); + vortex_ensure!(!struct_dtype.is_null(), "struct dtype is null"); let values = scalar_values_from_raw(fields, len)?; Ok(vx_scalar::new(Scalar::try_new( vx_dtype::as_ref(struct_dtype).clone(), @@ -451,14 +451,14 @@ fn scalar_values_from_raw( if len == 0 { return Ok(Vec::new()); } - vortex_ensure!(!values.is_null(), InvalidArgument: "scalar pointer array is null"); + vortex_ensure!(!values.is_null(), "scalar pointer array is null"); unsafe { slice::from_raw_parts(values, len) } .iter() .enumerate() .map(|(idx, value)| { if value.is_null() { - vortex_bail!(InvalidArgument: "scalar pointer at index {idx} is null"); + vortex_bail!("scalar pointer at index {idx} is null"); } Ok(vx_scalar::as_ref(*value).clone().into_value()) }) @@ -469,12 +469,12 @@ fn bytes_from_raw<'a>(ptr: *const u8, len: usize, label: &str) -> VortexResult<& if len == 0 { return Ok(&[]); } - vortex_ensure!(!ptr.is_null(), InvalidArgument: "{label} data pointer is null"); + vortex_ensure!(!ptr.is_null(), "{label} data pointer is null"); Ok(unsafe { slice::from_raw_parts(ptr, len) }) } fn fixed_bytes_from_raw(ptr: *const u8, label: &str) -> VortexResult<[u8; N]> { - vortex_ensure!(!ptr.is_null(), InvalidArgument: "{label} data pointer is null"); + vortex_ensure!(!ptr.is_null(), "{label} data pointer is null"); let mut bytes = [0u8; N]; bytes.copy_from_slice(unsafe { slice::from_raw_parts(ptr, N) }); Ok(bytes) diff --git a/vortex-ffi/src/scan.rs b/vortex-ffi/src/scan.rs index 80b6e5bc842..b58caddfb69 100644 --- a/vortex-ffi/src/scan.rs +++ b/vortex-ffi/src/scan.rs @@ -79,10 +79,10 @@ box_wrapper!( pub unsafe fn vx_partition_into_array_stream( partition: *mut vx_partition, ) -> VortexResult { - vortex_ensure!(!partition.is_null(), InvalidArgument: "null vx_partition"); + vortex_ensure!(!partition.is_null(), "null vx_partition"); match *vx_partition::into_box(partition) { VxPartitionScan::Pending(partition) => partition.execute(), - _ => vortex_bail!(InvalidArgument: "partition already being consumed"), + _ => vortex_bail!("partition already being consumed"), } } @@ -269,7 +269,7 @@ pub unsafe extern "C-unwind" fn vx_scan_dtype( try_or(err, ptr::null(), || { let scan = vx_scan::as_ref(scan); let VxScan::Pending(scan) = scan else { - vortex_bail!(InvalidArgument: "dtype unavailable: scan already started"); + vortex_bail!("dtype unavailable: scan already started"); }; Ok(vx_dtype::new(scan.dtype().clone())) }) @@ -335,7 +335,7 @@ pub unsafe extern "C-unwind" fn vx_partition_row_count( try_or(err, 1, || { let partition = vx_partition::as_ref(partition); let VxPartitionScan::Pending(partition) = partition else { - vortex_bail!(InvalidArgument: "row count unavailable: partition already started"); + vortex_bail!("row count unavailable: partition already started"); }; write_estimate(partition.row_count(), unsafe { &mut *count }); Ok(0) @@ -362,7 +362,7 @@ pub unsafe extern "C-unwind" fn vx_partition_scan_arrow( let partition = match *vx_partition::into_box(partition) { VxPartitionScan::Pending(partition) => partition, _ => vortex_bail!( - InvalidArgument: "Can't consume partition into ArrowArrayStream: partition already being consumed" + "Can't consume partition into ArrowArrayStream: partition already being consumed" ), }; let array_stream = partition.execute()?; diff --git a/vortex-ffi/src/session.rs b/vortex-ffi/src/session.rs index cc66474bf63..f0679a7c4c9 100644 --- a/vortex-ffi/src/session.rs +++ b/vortex-ffi/src/session.rs @@ -50,7 +50,7 @@ pub unsafe extern "C-unwind" fn vx_session_clone(session: *const vx_session) -> /// `session` must be null or a valid `vx_session` pointer created by this crate, and must stay /// valid for the returned reference. pub unsafe fn vx_session_ref<'a>(session: *const vx_session) -> VortexResult<&'a VortexSession> { - vortex_ensure!(!session.is_null(), InvalidArgument: "null vx_session"); + vortex_ensure!(!session.is_null(), "null vx_session"); Ok(vx_session::as_ref(session)) } diff --git a/vortex-ffi/src/sink.rs b/vortex-ffi/src/sink.rs index 7c9168253fd..f7cd88d7de9 100644 --- a/vortex-ffi/src/sink.rs +++ b/vortex-ffi/src/sink.rs @@ -69,7 +69,7 @@ pub unsafe fn vx_array_sink_open_file_with_strategy( let session = vx_session::as_ref(session).clone(); if path.ptr.is_null() { - vortex_bail!(InvalidArgument: "null path"); + vortex_bail!("null path"); } let path = unsafe { path.as_str() }?.to_string(); @@ -129,10 +129,10 @@ pub unsafe extern "C-unwind" fn vx_array_sink_push( let array = vx_array::as_ref(array); let sink = unsafe { &mut *sink }; - vortex_ensure_eq!(*array.dtype(), sink.dtype, MismatchedTypes); + vortex_ensure_eq!(*array.dtype(), sink.dtype); RUNTIME .block_on(sink.sink.send(Ok(array.clone()))) - .map_err(|e| vortex_err!(Io: "Send error: {e}")) + .map_err(|e| vortex_err!("Send error: {e}")) }) } diff --git a/vortex-ffi/src/string.rs b/vortex-ffi/src/string.rs index 96e4904f056..5585e7f0a5c 100644 --- a/vortex-ffi/src/string.rs +++ b/vortex-ffi/src/string.rs @@ -51,7 +51,7 @@ impl vx_view { /// "ptr" must be valid for "len" reads or NULL with "len == 0". pub(crate) unsafe fn as_bytes<'a>(&self) -> VortexResult<&'a [u8]> { if self.ptr.is_null() { - vortex_ensure_eq!(self.len, 0, InvalidArgument: "null vx_view pointer with non-zero length"); + vortex_ensure_eq!(self.len, 0, "null vx_view pointer with non-zero length"); return Ok(&[]); } Ok(unsafe { slice::from_raw_parts(self.ptr.cast(), self.len) }) @@ -63,8 +63,7 @@ impl vx_view { /// /// `self.ptr` must be valid for `self.len` reads, or null when `self.len` is zero. pub unsafe fn as_str<'a>(&self) -> VortexResult<&'a str> { - str::from_utf8(unsafe { self.as_bytes() }?) - .map_err(|e| vortex_err!(InvalidArgument: "invalid utf-8: {e}")) + str::from_utf8(unsafe { self.as_bytes() }?).map_err(|e| vortex_err!("invalid utf-8: {e}")) } } diff --git a/vortex-ffi/src/struct_array.rs b/vortex-ffi/src/struct_array.rs index f0c382dfe92..e1c00877866 100644 --- a/vortex-ffi/src/struct_array.rs +++ b/vortex-ffi/src/struct_array.rs @@ -73,7 +73,7 @@ pub unsafe extern "C" fn vx_struct_column_builder_add_field( if !builder.fields.is_empty() && field.len() != builder.fields[0].len() { vortex_bail!( - MismatchedTypes: "Field length mismatch: expected {}, got {}", + "Field length mismatch: expected {}, got {}", builder.fields[0].len(), field.len() ); diff --git a/vortex-file/src/footer/deserializer.rs b/vortex-file/src/footer/deserializer.rs index 3eee70d5c74..77320ef2204 100644 --- a/vortex-file/src/footer/deserializer.rs +++ b/vortex-file/src/footer/deserializer.rs @@ -119,7 +119,7 @@ impl FooterDeserializer { .then(|| { postscript.dtype.as_ref().ok_or_else(|| { vortex_err!( - Serde: "Vortex file doesn't embed a DType and none provided to VortexOpenOptions" + "Vortex file doesn't embed a DType and none provided to VortexOpenOptions" ) }) }) @@ -136,7 +136,7 @@ impl FooterDeserializer { .checked_sub(self.buffer.len() as u64) .ok_or_else(|| { vortex_err!( - Serde: "Footer buffer length {} exceeds declared file size {file_size}", + "Footer buffer length {} exceeds declared file size {file_size}", self.buffer.len() ) })?; @@ -193,11 +193,11 @@ impl FooterDeserializer { .offset .checked_add(u64::from(segment.length)) .ok_or_else(|| { - vortex_err!(Overflow: "Metadata segment {} range overflowed u64", metadata.key) + vortex_err!("Metadata segment {} range overflowed u64", metadata.key) })?; if end > file_size { vortex_bail!( - Serde: "Metadata segment {} range {}..{} exceeds file size {}", + "Metadata segment {} range {}..{} exceeds file size {}", metadata.key, segment.offset, end, @@ -207,7 +207,7 @@ impl FooterDeserializer { let offset = usize::try_from(segment.offset)?; if !segment.alignment.is_offset_aligned(offset) { vortex_bail!( - Serde: "Metadata segment {} offset {} is not aligned to {}", + "Metadata segment {} offset {} is not aligned to {}", metadata.key, segment.offset, segment.alignment @@ -236,7 +236,7 @@ impl FooterDeserializer { fn parse_postscript(&self, initial_read: &[u8]) -> VortexResult { if initial_read.len() < EOF_SIZE { vortex_bail!( - InvalidArgument: "Initial read must be at least EOF_SIZE ({}) bytes", + "Initial read must be at least EOF_SIZE ({}) bytes", EOF_SIZE ); } @@ -245,27 +245,27 @@ impl FooterDeserializer { let magic_number = &initial_read[magic_bytes_loc..]; if magic_number != MAGIC_BYTES { - vortex_bail!(Serde: "Malformed file, invalid magic bytes, got {magic_number:?}") + vortex_bail!("Malformed file, invalid magic bytes, got {magic_number:?}") } let version = u16::from_le_bytes( initial_read[eof_loc..eof_loc + 2] .try_into() - .map_err(|e| vortex_err!(Serde: "Version was not a u16 {e}"))?, + .map_err(|e| vortex_err!("Version was not a u16 {e}"))?, ); if version != VERSION { - vortex_bail!(Serde: "Malformed file, unsupported version {version}") + vortex_bail!("Malformed file, unsupported version {version}") } let ps_size = u16::from_le_bytes( initial_read[eof_loc + 2..eof_loc + 4] .try_into() - .map_err(|e| vortex_err!(Serde: "Postscript size was not a u16 {e}"))?, + .map_err(|e| vortex_err!("Postscript size was not a u16 {e}"))?, ) as usize; if initial_read.len() < ps_size + EOF_SIZE { vortex_bail!( - InvalidArgument: "Initial read must be at least {} bytes to include the Postscript", + "Initial read must be at least {} bytes to include the Postscript", ps_size + EOF_SIZE ); } @@ -341,7 +341,7 @@ fn checked_segment_slice<'a>( ) -> VortexResult<&'a [u8]> { let offset = usize::try_from(segment.offset.checked_sub(read_offset).ok_or_else(|| { vortex_err!( - Serde: "Segment offset {} is smaller than file read offset {read_offset}", + "Segment offset {} is smaller than file read offset {read_offset}", segment.offset ) })?)?; @@ -350,7 +350,7 @@ fn checked_segment_slice<'a>( .and_then(|end| read.get(offset..end)) .ok_or_else(|| { vortex_err!( - OutOfBounds: "Segment length {} (at offset {}) out of bounds of slice of length {}", + "Segment length {} (at offset {}) out of bounds of slice of length {}", segment.length, offset, read.len() diff --git a/vortex-file/src/footer/field_sizes.rs b/vortex-file/src/footer/field_sizes.rs index 481f3132a3c..afd47353d5b 100644 --- a/vortex-file/src/footer/field_sizes.rs +++ b/vortex-file/src/footer/field_sizes.rs @@ -72,7 +72,7 @@ impl CompressedFieldSizes { for (segment_id, path) in attribution { let segment = segments.get(*segment_id as usize).ok_or_else(|| { vortex_err!( - NotFound: "layout references missing segment {} (segment count: {})", + "layout references missing segment {} (segment count: {})", *segment_id, segments.len() ) diff --git a/vortex-file/src/footer/mod.rs b/vortex-file/src/footer/mod.rs index c11ddb25e5e..57be23ec74e 100644 --- a/vortex-file/src/footer/mod.rs +++ b/vortex-file/src/footer/mod.rs @@ -147,14 +147,14 @@ impl Footer { let segments: Arc<[SegmentSpec]> = fb_footer .segment_specs() - .ok_or_else(|| vortex_err!(NotFound: "FileLayout missing segment specs"))? + .ok_or_else(|| vortex_err!("FileLayout missing segment specs"))? .iter() .map(SegmentSpec::try_from) .try_collect()?; // Note this assertion is `<=` since we allow zero-length segments if !segments.is_sorted_by_key(|segment| segment.offset) { - vortex_bail!(Serde: "Segment offsets are not ordered"); + vortex_bail!("Segment offsets are not ordered"); } let segments_with_metadata = segments_with_metadata(&segments, &metadata); @@ -288,7 +288,7 @@ fn validate_segments_within_file(segments: &[SegmentSpec], file_size: u64) -> Vo .is_some_and(|end| end <= file_size); if !within_file { vortex_bail!( - OutOfBounds: "Segment at offset {} with length {} extends past the end of the \ + "Segment at offset {} with length {} extends past the end of the \ {file_size}-byte file", segment.offset, segment.length, diff --git a/vortex-file/src/footer/postscript.rs b/vortex-file/src/footer/postscript.rs index ae195220800..863b7da303e 100644 --- a/vortex-file/src/footer/postscript.rs +++ b/vortex-file/src/footer/postscript.rs @@ -116,7 +116,7 @@ impl ReadFlatBuffer for Postscript { .transpose()?, layout: PostscriptSegment::read_flatbuffer( &fb.layout() - .ok_or_else(|| vortex_err!(NotFound: "Postscript missing layout segment"))?, + .ok_or_else(|| vortex_err!("Postscript missing layout segment"))?, )?, statistics: fb .statistics() @@ -124,7 +124,7 @@ impl ReadFlatBuffer for Postscript { .transpose()?, footer: PostscriptSegment::read_flatbuffer( &fb.footer() - .ok_or_else(|| vortex_err!(Serde: "Postscript missing footer segment"))?, + .ok_or_else(|| vortex_err!("Postscript missing footer segment"))?, )?, metadata, }) @@ -149,7 +149,7 @@ fn validate_metadata_entries(metadata: &[PostscriptMetadata]) -> VortexResult<() fn metadata_count_error(metadata_len: usize) -> VortexError { vortex_err!( - InvalidArgument: "Postscript contains {} metadata segments, but Vortex supports at most {} metadata segments; metadata keys must be non-empty and at most {} bytes", + "Postscript contains {} metadata segments, but Vortex supports at most {} metadata segments; metadata keys must be non-empty and at most {} bytes", metadata_len, MAX_METADATA_SEGMENTS, MAX_METADATA_KEY_BYTES @@ -158,7 +158,7 @@ fn metadata_count_error(metadata_len: usize) -> VortexError { fn duplicate_metadata_key_error(key: &str) -> VortexError { vortex_err!( - InvalidArgument: "Postscript contains duplicate metadata key {key}; metadata keys must be unique, non-empty, and at most {} bytes, and files may contain at most {} metadata segments", + "Postscript contains duplicate metadata key {key}; metadata keys must be unique, non-empty, and at most {} bytes, and files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS ) @@ -167,7 +167,7 @@ fn duplicate_metadata_key_error(key: &str) -> VortexError { fn validate_metadata_key(key: &str) -> VortexResult<()> { if key.is_empty() { return Err(vortex_err!( - InvalidArgument: "Postscript metadata key must not be empty; metadata keys must be at most {} bytes and files may contain at most {} metadata segments", + "Postscript metadata key must not be empty; metadata keys must be at most {} bytes and files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS )); @@ -176,7 +176,7 @@ fn validate_metadata_key(key: &str) -> VortexResult<()> { let key_bytes = key.len(); if key_bytes > MAX_METADATA_KEY_BYTES { return Err(vortex_err!( - InvalidArgument: "Postscript metadata key {key:?} is {key_bytes} bytes, but metadata keys must be at most {} bytes and files may contain at most {} metadata segments", + "Postscript metadata key {key:?} is {key_bytes} bytes, but metadata keys must be at most {} bytes and files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS )); diff --git a/vortex-file/src/footer/serializer.rs b/vortex-file/src/footer/serializer.rs index 06ce54669a0..6997c1d30b0 100644 --- a/vortex-file/src/footer/serializer.rs +++ b/vortex-file/src/footer/serializer.rs @@ -176,7 +176,7 @@ impl FooterSerializer { let postscript_buffer = postscript.write_flatbuffer_bytes()?; if postscript_buffer.len() > MAX_POSTSCRIPT_SIZE as usize { Err(vortex_err!( - Overflow: "Postscript is too large ({} bytes); max postscript size is {}", + "Postscript is too large ({} bytes); max postscript size is {}", postscript_buffer.len(), MAX_POSTSCRIPT_SIZE ))?; @@ -225,7 +225,7 @@ fn write_flatbuffer( ) -> VortexResult<(ByteBuffer, PostscriptSegment)> { let buffer = flatbuffer.write_flatbuffer_bytes()?; let length = u32::try_from(buffer.len()) - .map_err(|_| vortex_err!(Serde: "flatbuffer length exceeds maximum u32"))?; + .map_err(|_| vortex_err!("flatbuffer length exceeds maximum u32"))?; let segment = PostscriptSegment { offset: *offset, @@ -243,7 +243,7 @@ fn write_buffer( buffer: ByteBuffer, ) -> VortexResult<(Vec, PostscriptSegment)> { let length = u32::try_from(buffer.len()) - .map_err(|_| vortex_err!(Overflow: "metadata segment length exceeds maximum u32"))?; + .map_err(|_| vortex_err!("metadata segment length exceeds maximum u32"))?; let alignment = buffer.alignment(); let padding = offset.next_multiple_of(alignment.as_usize() as u64) - *offset; diff --git a/vortex-file/src/multi/mod.rs b/vortex-file/src/multi/mod.rs index 2cf222f5d75..03a80171ec5 100644 --- a/vortex-file/src/multi/mod.rs +++ b/vortex-file/src/multi/mod.rs @@ -123,7 +123,7 @@ impl MultiFileDataSource { /// and creates lazy factories for the remaining files. pub async fn build(self) -> VortexResult { if self.glob_sources.is_empty() { - vortex_bail!(InvalidArgument: "MultiFileDataSource requires at least one glob pattern"); + vortex_bail!("MultiFileDataSource requires at least one glob pattern"); } // Create local filesystem lazily if needed (only if any glob lacks a filesystem). @@ -163,7 +163,7 @@ impl MultiFileDataSource { let all_files: Vec<(FileListing, FileSystemRef)> = resolved.into_iter().flatten().collect(); if all_files.is_empty() { - vortex_bail!(NotFound: "No files matched the glob pattern(s): {:?}", globs); + vortex_bail!("No files matched the glob pattern(s): {:?}", globs); } let file_count = all_files.len(); @@ -219,7 +219,7 @@ fn create_local_filesystem(session: &VortexSession) -> VortexResult VortexResult { vortex_bail!( - NotImplemented: "The 'object_store' feature is required for automatic local filesystem creation. \ + "The 'object_store' feature is required for automatic local filesystem creation. \ Either enable the feature or provide a filesystem via .with_filesystem()." ); } @@ -255,7 +255,7 @@ pub async fn open_cached( key = uri.as_deref(); } let Some(key) = key else { - vortex_bail!(NotFound: "Missing cache key"); + vortex_bail!("Missing cache key"); }; let mut options = open_options_fn(session.open_options()); diff --git a/vortex-file/src/multi/uri.rs b/vortex-file/src/multi/uri.rs index 704bc3c0494..21b84c43110 100644 --- a/vortex-file/src/multi/uri.rs +++ b/vortex-file/src/multi/uri.rs @@ -71,10 +71,10 @@ pub fn parse_uri_or_path(uri_or_path: &str) -> VortexResult { target_os = "hermit" ))] fn file_path_to_url(path: &str) -> VortexResult { - let abs = absolute(Path::new(path)) - .map_err(|e| vortex_err!(Io: "failed to absolutize {path}: {e}"))?; + let abs = + absolute(Path::new(path)).map_err(|e| vortex_err!("failed to absolutize {path}: {e}"))?; Url::from_file_path(normalize_path(abs)) - .map_err(|_| vortex_err!(InvalidArgument: "neither URL nor path: {path}")) + .map_err(|_| vortex_err!("neither URL nor path: {path}")) } /// `Url::from_file_path` does not exist on targets without a filesystem, such as @@ -88,7 +88,7 @@ fn file_path_to_url(path: &str) -> VortexResult { )))] fn file_path_to_url(path: &str) -> VortexResult { Err(vortex_err!( - InvalidArgument: "bare file paths are not supported on this platform: {path}" + "bare file paths are not supported on this platform: {path}" )) } diff --git a/vortex-file/src/open.rs b/vortex-file/src/open.rs index 6d3878af416..3e06dbcfbf5 100644 --- a/vortex-file/src/open.rs +++ b/vortex-file/src/open.rs @@ -441,7 +441,7 @@ impl VortexOpenOptions { .filter(|end| *end <= initial_read.len()) .ok_or_else(|| { vortex_err!( - OutOfBounds: "Segment at offset {} with length {} is out of bounds of the \ + "Segment at offset {} with length {} is out of bounds of the \ {}-byte initial read", segment.offset, segment.length, @@ -853,7 +853,7 @@ mod tests { let initial_read = ByteBuffer::zeroed(16); let Err(err) = VortexOpenOptions::collect_initial_segments(0, &initial_read, &bad_footer) else { - vortex_bail!(AssertionFailed: "collecting an out-of-bounds segment must return an error"); + vortex_bail!("collecting an out-of-bounds segment must return an error"); }; assert!( err.to_string().contains("out of bounds"), @@ -900,7 +900,7 @@ mod tests { let mut deserializer = Footer::deserializer(footer_bytes.freeze(), session.clone()) .with_size(serialized_footer_size as u64); let DeserializeStep::Done(cached_footer) = deserializer.deserialize()? else { - vortex_bail!(Serde: "standalone footer bytes must be sufficient for deserialization"); + vortex_bail!("standalone footer bytes must be sufficient for deserialization"); }; session diff --git a/vortex-file/src/read/driver.rs b/vortex-file/src/read/driver.rs index 43b5a59138b..ad9c6570202 100644 --- a/vortex-file/src/read/driver.rs +++ b/vortex-file/src/read/driver.rs @@ -481,7 +481,7 @@ mod tests { let waker = futures::task::noop_waker(); let mut context = Context::from_waker(&waker); let Poll::Ready(Some(batch)) = batches.as_mut().poll_next(&mut context) else { - vortex_panic!(AssertionFailed: "partial batch was not emitted by the current poll"); + vortex_panic!("partial batch was not emitted by the current poll"); }; assert_eq!(batch.len(), 1); assert_eq!(batch[0].offset(), 0); diff --git a/vortex-file/src/read/request.rs b/vortex-file/src/read/request.rs index 939de6f9c06..1ef5beb3757 100644 --- a/vortex-file/src/read/request.rs +++ b/vortex-file/src/read/request.rs @@ -146,14 +146,14 @@ impl CoalescedRequest { ) -> VortexResult { vortex_ensure!( range.start <= range.end, - InvalidArgument: "CoalescedRequest: range.start, {}, must be less than or equal to range.end, {}.", + "CoalescedRequest: range.start, {}, must be less than or equal to range.end, {}.", range.start, range.end, ); for req in requests.iter() { vortex_ensure!( req.offset >= range.start, - InvalidArgument: "CoalescedRequest: sub-request for length {} at file offset {} precedes coalesced range: {}..{}. {:?}", + "CoalescedRequest: sub-request for length {} at file offset {} precedes coalesced range: {}..{}. {:?}", req.length, req.offset, range.start, @@ -162,7 +162,7 @@ impl CoalescedRequest { ); vortex_ensure!( req.offset.saturating_add(req.length as u64) <= range.end, - InvalidArgument: "CoalescedRequest: sub-request for length {} at file offset {} exceeds the coalesced range: {}..{}. {:?}", + "CoalescedRequest: sub-request for length {} at file offset {} exceeds the coalesced range: {}..{}. {:?}", req.length, req.offset, range.start, diff --git a/vortex-file/src/segments/source.rs b/vortex-file/src/segments/source.rs index a3a7a5c9766..704750d346f 100644 --- a/vortex-file/src/segments/source.rs +++ b/vortex-file/src/segments/source.rs @@ -101,7 +101,7 @@ fn validate_read_result( result.and_then(|buffer| { if request.len() != buffer.len() { return Err(vortex_err!( - MismatchedTypes: "FileSegmentSource: expected buffer of length {} but received {}. {:?}", + "FileSegmentSource: expected buffer of length {} but received {}. {:?}", request.len(), buffer.len(), request @@ -164,7 +164,7 @@ impl Stream for ReadRangeResults { return Poll::Ready(None); }; let error = vortex_err!( - Io: "FileSegmentSource: read_ranges ended before resolving request. {:?}", + "FileSegmentSource: read_ranges ended before resolving request. {:?}", req ); return Poll::Ready(Some((req, Err(error)))); @@ -269,7 +269,7 @@ impl Stream for ReadDriver { } Poll::Ready(None) if this.num_active == 0 => Poll::Pending, Poll::Ready(None) => { - vortex_panic!(AssertionFailed: "read result streams ended with active requests") + vortex_panic!("read result streams ended with active requests") } Poll::Pending => Poll::Pending, } @@ -316,7 +316,7 @@ impl FileSegmentSource { let concurrency = reader.concurrency(); if concurrency == 0 { vortex_panic!( - AssertionFailed: "VortexReadAt::concurrency returned 0 (uri={:?}); this would stall I/O", + "VortexReadAt::concurrency returned 0 (uri={:?}); this would stall I/O", reader.uri() ); } @@ -368,8 +368,7 @@ impl SegmentSource for FileSegmentSource { let spec = *match self.segments.get(*id as usize) { Some(spec) => spec, None => { - return future::ready(Err(vortex_err!(NotFound: "Missing segment: {}", id))) - .boxed(); + return future::ready(Err(vortex_err!("Missing segment: {}", id))).boxed(); } }; @@ -391,8 +390,7 @@ impl SegmentSource for FileSegmentSource { // If we fail to submit the event, we create a future that has failed. if let Err(e) = self.events.unbounded_send(event) { - return future::ready(Err(vortex_err!(Io: "Failed to submit read request: {e}"))) - .boxed(); + return future::ready(Err(vortex_err!("Failed to submit read request: {e}"))).boxed(); } let fut = ReadFuture { @@ -447,7 +445,7 @@ impl Future for ReadFuture { if let Some(panic) = self.driver_panic.lock().take() { std::panic::resume_unwind(panic); } - Poll::Ready(Err(vortex_err!(Io: "ReadRequest dropped by runtime: {e}"))) + Poll::Ready(Err(vortex_err!("ReadRequest dropped by runtime: {e}"))) } Poll::Pending => Poll::Pending, }, @@ -456,9 +454,7 @@ impl Future for ReadFuture { // Notify the I/O stream that this request has been polled. match self.events.unbounded_send(ReadEvent::Polled(self.id)) { Ok(()) => Poll::Pending, - Err(e) => { - Poll::Ready(Err(vortex_err!(Io: "ReadRequest dropped by runtime: {e}"))) - } + Err(e) => Poll::Ready(Err(vortex_err!("ReadRequest dropped by runtime: {e}"))), } } _ => Poll::Pending, @@ -542,8 +538,7 @@ impl SegmentSource for BufferSegmentSource { let spec = match self.segments.get(*id as usize) { Some(spec) => spec, None => { - return future::ready(Err(vortex_err!(NotFound: "Missing segment: {}", id))) - .boxed(); + return future::ready(Err(vortex_err!("Missing segment: {}", id))).boxed(); } }; @@ -551,7 +546,7 @@ impl SegmentSource for BufferSegmentSource { let end = start + spec.length as usize; if end > self.buffer.len() { return future::ready(Err(vortex_err!( - OutOfBounds: "Segment {} range {}..{} out of bounds for buffer of length {}", + "Segment {} range {}..{} out of bounds for buffer of length {}", *id, start, end, @@ -872,7 +867,7 @@ mod tests { let permits = Arc::clone(&self.permits); async move { let Ok(permit) = permits.acquire_owned().await else { - vortex_panic!(AssertionFailed: "test semaphore unexpectedly closed"); + vortex_panic!("test semaphore unexpectedly closed"); }; permit.forget(); active.fetch_sub(1, Ordering::SeqCst); @@ -1042,7 +1037,7 @@ mod tests { for _ in 0..(offset as usize % 5 + 1) { tokio::task::yield_now().await; } - vortex_bail!(Io: "slow read done") + vortex_bail!("slow read done") } .boxed() } diff --git a/vortex-file/src/segments/writer.rs b/vortex-file/src/segments/writer.rs index 183f1c2c95d..1673ce40101 100644 --- a/vortex-file/src/segments/writer.rs +++ b/vortex-file/src/segments/writer.rs @@ -54,7 +54,7 @@ impl SegmentSink for BufferedSegmentSink { let mut specs = self.segment_specs.lock(); let segment_id = SegmentId::from( u32::try_from(specs.len()) - .map_err(|_| vortex_err!(Overflow: "Too mant segments, u32 overflow"))?, + .map_err(|_| vortex_err!("Too mant segments, u32 overflow"))?, ); // The API requires us to write these buffers contiguously. Therefore, we can only @@ -66,7 +66,7 @@ impl SegmentSink for BufferedSegmentSink { .map(|buffer| buffer.alignment()) .unwrap_or_else(Alignment::none); let length = u32::try_from(buffers.iter().map(|buffer| buffer.len()).sum::()) - .map_err(|_| vortex_err!(Overflow: "segment buffer length exceeds maximum u32"))?; + .map_err(|_| vortex_err!("segment buffer length exceeds maximum u32"))?; // Add any padding required to align the segment. let byte_offset = self.byte_offset.load(Ordering::Relaxed); diff --git a/vortex-file/src/writer.rs b/vortex-file/src/writer.rs index 86b72c5418f..a5208014bfd 100644 --- a/vortex-file/src/writer.rs +++ b/vortex-file/src/writer.rs @@ -454,7 +454,7 @@ fn validate_dtype_editions(session: &VortexSession, dtype: &DType) -> VortexResu DType::Extension(extension) => { if !allowed.contains(&extension.id()) { vortex_bail!( - InvalidArgument: "Extension DType {} not permitted by enabled editions", + "Extension DType {} not permitted by enabled editions", extension.id() ); } @@ -486,7 +486,7 @@ fn new_layout_context(session: &VortexSession, enforce_editions: bool) -> Layout fn validate_metadata_segments(metadata: &HashMap) -> VortexResult<()> { if metadata.len() > MAX_METADATA_SEGMENTS { vortex_bail!( - InvalidArgument: "Vortex files may contain at most {} metadata segments; got {} metadata segments. Metadata keys must be non-empty and at most {} bytes", + "Vortex files may contain at most {} metadata segments; got {} metadata segments. Metadata keys must be non-empty and at most {} bytes", MAX_METADATA_SEGMENTS, metadata.len(), MAX_METADATA_KEY_BYTES @@ -496,7 +496,7 @@ fn validate_metadata_segments(metadata: &HashMap) -> VortexR for key in metadata.keys() { if key.is_empty() { vortex_bail!( - InvalidArgument: "Vortex metadata keys must be non-empty and at most {} bytes; files may contain at most {} metadata segments", + "Vortex metadata keys must be non-empty and at most {} bytes; files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS ); @@ -505,7 +505,7 @@ fn validate_metadata_segments(metadata: &HashMap) -> VortexR let key_bytes = key.len(); if key_bytes > MAX_METADATA_KEY_BYTES { vortex_bail!( - InvalidArgument: "Vortex metadata key {key:?} is {key_bytes} bytes, but keys must be at most {} bytes; files may contain at most {} metadata segments", + "Vortex metadata key {key:?} is {key_bytes} bytes, but keys must be at most {} bytes; files may contain at most {} metadata segments", MAX_METADATA_KEY_BYTES, MAX_METADATA_SEGMENTS ); @@ -548,7 +548,7 @@ impl Writer<'_> { // finish() is called. Therefore, we can assume the writer has failed. // The writer future has failed, we need to propagate the error. match result { - Ok(_) => vortex_bail!(AssertionFailed: "Internal error: writer future completed early"), + Ok(_) => vortex_bail!("Internal error: writer future completed early"), Err(e) => return Err(e), } } @@ -587,7 +587,7 @@ impl Writer<'_> { // finish() is called. Therefore, we can assume the writer has failed. // The writer future has failed, we need to propagate the error. match result { - Ok(_) => vortex_bail!(AssertionFailed: "Internal error: writer future completed early"), + Ok(_) => vortex_bail!("Internal error: writer future completed early"), Err(e) => return Err(e), } } @@ -620,7 +620,7 @@ impl Writer<'_> { async fn handle_failed_task(&mut self) -> VortexError { match (&mut self.future).await { Ok(_) => vortex_err!( - AssertionFailed: "Internal error: writer task completed successfully but write future finished early" + "Internal error: writer task completed successfully but write future finished early" ), Err(e) => e, } diff --git a/vortex-io/src/filesystem/glob.rs b/vortex-io/src/filesystem/glob.rs index e1684c280f2..030bf4f56d1 100644 --- a/vortex-io/src/filesystem/glob.rs +++ b/vortex-io/src/filesystem/glob.rs @@ -37,9 +37,8 @@ impl dyn FileSystem + '_ { return Ok(stream); } - let glob_pattern = glob::Pattern::new(pattern).map_err( - |e| vortex_err!(InvalidArgument: "Invalid glob pattern '{}': {}", pattern, e), - )?; + let glob_pattern = glob::Pattern::new(pattern) + .map_err(|e| vortex_err!("Invalid glob pattern '{}': {}", pattern, e))?; let listing_prefix = glob_list_prefix(pattern).trim_end_matches('/'); @@ -78,7 +77,7 @@ fn validate_glob(pattern: &str) -> VortexResult<()> { for escape_pattern in ["\\*", "\\?", "\\["] { if pattern.contains(escape_pattern) { vortex_bail!( - InvalidArgument: "Escaped glob characters are not allowed in patterns. Found '{}' in: {}", + "Escaped glob characters are not allowed in patterns. Found '{}' in: {}", escape_pattern, pattern ); @@ -125,7 +124,7 @@ mod tests { #[async_trait] impl FileSystem for HeadFileSystem { fn list(&self, _prefix: &str) -> BoxStream<'_, VortexResult> { - vortex_panic!(AssertionFailed: "list() must not be called for an exact path; glob should use head()") + vortex_panic!("list() must not be called for an exact path; glob should use head()") } async fn head(&self, path: &str) -> VortexResult> { @@ -137,11 +136,11 @@ mod tests { } async fn open_read(&self, _path: &str) -> VortexResult> { - vortex_panic!(AssertionFailed: "open_read() should not be called") + vortex_panic!("open_read() should not be called") } async fn delete(&self, _path: &str) -> VortexResult<()> { - vortex_panic!(AssertionFailed: "delete() should not be called") + vortex_panic!("delete() should not be called") } } diff --git a/vortex-io/src/object_store/read_at.rs b/vortex-io/src/object_store/read_at.rs index 050641f07eb..b354ea705e8 100644 --- a/vortex-io/src/object_store/read_at.rs +++ b/vortex-io/src/object_store/read_at.rs @@ -136,7 +136,7 @@ async fn read_object_store_range( let end = written + bytes.len(); vortex_ensure!( end <= length, - Io: "Object store stream returned too many bytes: {} > expected {} (range: {:?})", + "Object store stream returned too many bytes: {} > expected {} (range: {:?})", end, length, range @@ -148,7 +148,7 @@ async fn read_object_store_range( vortex_ensure_eq!( written, length, - Io: "Object store stream returned too few bytes (range: {:?})", + "Object store stream returned too few bytes (range: {:?})", range ); diff --git a/vortex-io/src/read_at.rs b/vortex-io/src/read_at.rs index 45c7d44b0c5..c24cd49620e 100644 --- a/vortex-io/src/read_at.rs +++ b/vortex-io/src/read_at.rs @@ -224,7 +224,7 @@ impl VortexReadAt for ByteBuffer { usize::try_from(offset + length as u64).vortex_expect("end too big for usize"); if end > buffer.len() { vortex_bail!( - OutOfBounds: "Requested range {}..{} out of bounds for buffer of length {}", + "Requested range {}..{} out of bounds for buffer of length {}", start, end, buffer.len() diff --git a/vortex-io/src/request/mod.rs b/vortex-io/src/request/mod.rs index 030a68cd1a8..efce222ba0f 100644 --- a/vortex-io/src/request/mod.rs +++ b/vortex-io/src/request/mod.rs @@ -180,7 +180,7 @@ impl IoSlot { /// its result has not been taken, since that is a bug in the owner. pub fn issue(&mut self, target: IoTarget) -> IoBatch { if self.request.is_some() || self.result.is_some() { - vortex_panic!(AssertionFailed: "IoSlot: issue while a request is outstanding"); + vortex_panic!("IoSlot: issue while a request is outstanding"); } let request = IoRequest { intent: IoIntent::Fetch, @@ -201,11 +201,11 @@ impl IoSlot { /// does not match the target, since the driver guarantees both. pub fn deliver(&mut self, id: IoRequestId, result: IoResult) { let Some(request) = self.request.take_if(|request| request.request == id) else { - vortex_panic!(AssertionFailed: "IoSlot: delivery of {id:?}, which is not outstanding"); + vortex_panic!("IoSlot: delivery of {id:?}, which is not outstanding"); }; if !result.matches(&request.target) { vortex_panic!( - AssertionFailed: "IoSlot: {id:?} for {:?} answered with {}", + "IoSlot: {id:?} for {:?} answered with {}", request.target, result.kind() ); diff --git a/vortex-io/src/request/source.rs b/vortex-io/src/request/source.rs index adabc379a08..cda9e2ebed3 100644 --- a/vortex-io/src/request/source.rs +++ b/vortex-io/src/request/source.rs @@ -50,7 +50,7 @@ impl IoSource for ReadAtIoSource { if let IoTarget::Range { offset, len, .. } = &request.target && offset.checked_add(*len as u64).is_none() { - vortex_bail!(Overflow: "ReadAtIoSource: range overflow for {:?}", request.request); + vortex_bail!("ReadAtIoSource: range overflow for {:?}", request.request); } } self.queued.lock().extend( @@ -72,9 +72,11 @@ impl IoSource for ReadAtIoSource { } fn wait(&self) -> VortexResult { - let (work, request) = self.queued.lock().pop_front().ok_or_else( - || vortex_err!(AssertionFailed: "ReadAtIoSource: wait with nothing outstanding"), - )?; + let (work, request) = self + .queued + .lock() + .pop_front() + .ok_or_else(|| vortex_err!("ReadAtIoSource: wait with nothing outstanding"))?; let result = match request.target { IoTarget::Size => self.runtime.block_on(self.read.size()).map(IoResult::Size), IoTarget::Range { diff --git a/vortex-io/src/request/source/tests.rs b/vortex-io/src/request/source/tests.rs index cca0458c806..fd6bcfd12a9 100644 --- a/vortex-io/src/request/source/tests.rs +++ b/vortex-io/src/request/source/tests.rs @@ -79,7 +79,7 @@ fn a_range_is_read_at_its_alignment() -> VortexResult<()> { }], )?; let IoResult::Bytes(bytes) = source.wait()?.result? else { - vortex_bail!(AssertionFailed: "expected bytes"); + vortex_bail!("expected bytes"); }; assert!(bytes.try_into_host_sync()?.is_aligned(alignment)); assert_eq!(read.alignments(), vec![alignment]); diff --git a/vortex-io/src/runtime/blocking_pool.rs b/vortex-io/src/runtime/blocking_pool.rs index 767be97ca23..fc315844831 100644 --- a/vortex-io/src/runtime/blocking_pool.rs +++ b/vortex-io/src/runtime/blocking_pool.rs @@ -61,7 +61,7 @@ impl BlockingPool { }) .is_err() { - vortex_panic!(InvalidArgument: "cannot spawn blocking work on a shut down runtime"); + vortex_panic!("cannot spawn blocking work on a shut down runtime"); } state.queued_job_count += 1; if state.queued_job_count > state.idle_thread_count { @@ -83,7 +83,7 @@ impl BlockingPool { .spawn(move || worker_loop(receiver, worker_state)) { state.thread_count -= 1; - vortex_panic!(Io: "failed to spawn a blocking I/O worker: {error}"); + vortex_panic!("failed to spawn a blocking I/O worker: {error}"); } } } @@ -210,7 +210,7 @@ mod tests { assert_eq!( recv.recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!(Io: "blocking job did not finish: {error}"))?, + .map_err(|error| vortex_err!("blocking job did not finish: {error}"))?, 42 ); Ok(()) @@ -227,7 +227,7 @@ mod tests { }))); started_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!(Io: "first blocking job did not start: {error}"))?; + .map_err(|error| vortex_err!("first blocking job did not start: {error}"))?; let (ran_send, ran_recv) = mpsc::sync_channel(1); pool.spawn(Box::new(move || { @@ -242,7 +242,7 @@ mod tests { let _ = release_send.send(()); done_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!(Io: "blocking queue did not drain: {error}"))?; + .map_err(|error| vortex_err!("blocking queue did not drain: {error}"))?; assert!(ran_recv.try_recv().is_err()); Ok(()) } @@ -265,7 +265,7 @@ mod tests { for _ in 0..2 { started_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!(Io: "blocking job did not start: {error}"))?; + .map_err(|error| vortex_err!("blocking job did not start: {error}"))?; } barrier.wait(); Ok(()) @@ -280,12 +280,12 @@ mod tests { }))); let first_thread = first_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!(Io: "first blocking job did not finish: {error}"))?; + .map_err(|error| vortex_err!("first blocking job did not finish: {error}"))?; let deadline = Instant::now() + Duration::from_secs(5); while pool.state.lock().idle_thread_count != 1 { if Instant::now() >= deadline { - return Err(vortex_err!(Io: "blocking worker did not become idle")); + return Err(vortex_err!("blocking worker did not become idle")); } std::thread::yield_now(); } @@ -298,7 +298,7 @@ mod tests { }))); let second_thread = started_recv .recv_timeout(Duration::from_secs(5)) - .map_err(|error| vortex_err!(Io: "second blocking job did not finish: {error}"))?; + .map_err(|error| vortex_err!("second blocking job did not finish: {error}"))?; assert_eq!(first_thread, second_thread); let state = pool.state.lock(); diff --git a/vortex-io/src/runtime/handle.rs b/vortex-io/src/runtime/handle.rs index e8e5aad6225..c08f3114310 100644 --- a/vortex-io/src/runtime/handle.rs +++ b/vortex-io/src/runtime/handle.rs @@ -38,7 +38,7 @@ impl Handle { fn runtime(&self) -> Arc { self.runtime.upgrade().unwrap_or_else(|| { - vortex_panic!(InvalidArgument: "Attempted to use a Handle after its runtime was dropped") + vortex_panic!("Attempted to use a Handle after its runtime was dropped") }) } diff --git a/vortex-io/src/runtime/single.rs b/vortex-io/src/runtime/single.rs index 62fa475888b..9f241d6bf55 100644 --- a/vortex-io/src/runtime/single.rs +++ b/vortex-io/src/runtime/single.rs @@ -129,7 +129,7 @@ impl Executor for Sender { future, task_callback: send, }) { - vortex_panic!(AssertionFailed: "Executor missing: {}", e); + vortex_panic!("Executor missing: {}", e); } Box::new(LazyAbortHandle { task: Mutex::new(recv), @@ -142,7 +142,7 @@ impl Executor for Sender { sync: cpu, task_callback: send, }) { - vortex_panic!(AssertionFailed: "Executor missing: {}", e); + vortex_panic!("Executor missing: {}", e); } Box::new(LazyAbortHandle { task: Mutex::new(recv), @@ -155,7 +155,7 @@ impl Executor for Sender { sync: work, task_callback: send, }) { - vortex_panic!(AssertionFailed: "Executor missing: {}", e); + vortex_panic!("Executor missing: {}", e); } Box::new(LazyAbortHandle { task: Mutex::new(recv), diff --git a/vortex-io/src/runtime/tokio.rs b/vortex-io/src/runtime/tokio.rs index 046ebe98682..a1696e50c20 100644 --- a/vortex-io/src/runtime/tokio.rs +++ b/vortex-io/src/runtime/tokio.rs @@ -128,7 +128,7 @@ impl BlockingRuntime for TokioRuntime { { // Assert that we're not currently inside the Tokio context. if tokio::runtime::Handle::try_current().is_ok() { - vortex_error::vortex_panic!(InvalidArgument: "block_on cannot be called from within a Tokio runtime"); + vortex_error::vortex_panic!("block_on cannot be called from within a Tokio runtime"); } let handle = Arc::clone(&self.0); tokio::task::block_in_place(move || handle.block_on(fut)) @@ -142,7 +142,7 @@ impl BlockingRuntime for TokioRuntime { // Assert that we're not currently inside the Tokio context. if tokio::runtime::Handle::try_current().is_ok() { vortex_error::vortex_panic!( - InvalidArgument: "block_on_stream cannot be called from within a Tokio runtime" + "block_on_stream cannot be called from within a Tokio runtime" ); } let handle = Arc::clone(&self.0); diff --git a/vortex-ipc/src/iterator.rs b/vortex-ipc/src/iterator.rs index 2201d051035..64f52b4bbf8 100644 --- a/vortex-ipc/src/iterator.rs +++ b/vortex-ipc/src/iterator.rs @@ -41,10 +41,10 @@ impl SyncIPCReader { }) } msg => { - vortex_bail!(MismatchedTypes: "Expected DType message, got {:?}", msg); + vortex_bail!("Expected DType message, got {:?}", msg); } }, - None => vortex_bail!(MismatchedTypes: "Expected DType message, got EOF"), + None => vortex_bail!("Expected DType message, got EOF"), } } } @@ -67,7 +67,7 @@ impl Iterator for SyncIPCReader { .and_then(|array| { if array.dtype() != self.dtype() { Err(vortex_err!( - MismatchedTypes: "Array data type mismatch: expected {:?}, got {:?}", + "Array data type mismatch: expected {:?}, got {:?}", self.dtype(), array.dtype() )) @@ -76,7 +76,7 @@ impl Iterator for SyncIPCReader { } }), ), - msg => Some(Err(vortex_err!(MismatchedTypes: "Expected Array message, got {:?}", msg))), + msg => Some(Err(vortex_err!("Expected Array message, got {:?}", msg))), }, Err(e) => Some(Err(e)), } diff --git a/vortex-ipc/src/messages/decoder.rs b/vortex-ipc/src/messages/decoder.rs index ba950f3c360..73cdd235485 100644 --- a/vortex-ipc/src/messages/decoder.rs +++ b/vortex-ipc/src/messages/decoder.rs @@ -95,7 +95,7 @@ impl MessageDecoder { let msg_bytes = bytes.copy_to_const_aligned(*msg_length); let msg = root::(msg_bytes.as_ref())?; if msg.version() != MessageVersion::V0 { - vortex_bail!(InvalidArgument: "Unsupported message version {:?}", msg.version()); + vortex_bail!("Unsupported message version {:?}", msg.version()); } self.state = State::Reading(msg_bytes); @@ -106,7 +106,7 @@ impl MessageDecoder { // Now we read the body let body_length = usize::try_from(msg.body_size()).map_err(|_| { - vortex_err!(Overflow: "body size {} is too large for usize", msg.body_size()) + vortex_err!("body size {} is too large for usize", msg.body_size()) })?; if bytes.remaining() < body_length { return Ok(PollRead::NeedMore(body_length)); @@ -157,7 +157,7 @@ impl MessageDecoder { return Ok(PollRead::Some(DecoderMessage::DType(dtype))); } _ => { - vortex_bail!(InvalidArgument: "Unsupported message header {:?}", msg.header_type()); + vortex_bail!("Unsupported message header {:?}", msg.header_type()); } } } @@ -195,7 +195,7 @@ mod test { let mut buffer = BytesMut::from(ipc_bytes.as_ref()); let (array_parts, ctx, row_count) = match decoder.read_next(&mut buffer).unwrap() { PollRead::Some(DecoderMessage::Array(array_parts)) => array_parts, - otherwise => vortex_panic!(MismatchedTypes: "Expected an array, got {:?}", otherwise), + otherwise => vortex_panic!("Expected an array, got {:?}", otherwise), }; // Decode the array parts with the context diff --git a/vortex-ipc/src/messages/encoder.rs b/vortex-ipc/src/messages/encoder.rs index 6f2a0c813bf..4b056052b3a 100644 --- a/vortex-ipc/src/messages/encoder.rs +++ b/vortex-ipc/src/messages/encoder.rs @@ -76,7 +76,7 @@ impl MessageEncoder { &mut fbb, &fb::ArrayMessageArgs { row_count: u32::try_from(array.len()) - .map_err(|_| vortex_err!(Overflow: "Array length must fit into u32"))?, + .map_err(|_| vortex_err!("Array length must fit into u32"))?, encodings: Some(array_encodings), }, ) @@ -127,7 +127,7 @@ impl MessageEncoder { let (fbv, pos) = fbb.collapse(); let fb_buffer = FlatBuffer::copy_from(&fbv[pos..]); let fb_buffer_len = u32::try_from(fb_buffer.len()) - .map_err(|_| vortex_err!(Overflow: "Array flatbuffer length must fit into u32"))?; + .map_err(|_| vortex_err!("Array flatbuffer length must fit into u32"))?; buffers[0] = Bytes::from(fb_buffer_len.to_le_bytes().to_vec()); buffers[1] = fb_buffer.into_inner().into_bytes(); diff --git a/vortex-ipc/src/messages/reader_async.rs b/vortex-ipc/src/messages/reader_async.rs index 5284dcff9b7..9a6cd946690 100644 --- a/vortex-ipc/src/messages/reader_async.rs +++ b/vortex-ipc/src/messages/reader_async.rs @@ -81,7 +81,7 @@ fn poll_fill_buffer( Poll::Ready(if bytes_read == 0 { if *total_bytes_read > 0 { Err(vortex_err!( - InvalidArgument: "unexpected EOF during partial read: read {total_bytes_read} of {} expected bytes", + "unexpected EOF during partial read: read {total_bytes_read} of {} expected bytes", buffer.len() )) } else { diff --git a/vortex-ipc/src/messages/reader_buf.rs b/vortex-ipc/src/messages/reader_buf.rs index 79685f2f4ad..faf2694f707 100644 --- a/vortex-ipc/src/messages/reader_buf.rs +++ b/vortex-ipc/src/messages/reader_buf.rs @@ -35,7 +35,7 @@ impl Iterator for BufMessageReader { match self.decoder.read_next(&mut self.buffer) { Ok(PollRead::Some(msg)) => Some(Ok(msg)), Ok(PollRead::NeedMore(_)) => Some(Err(vortex_err!( - Serde: "Buffer did not have sufficient bytes for an IPC message" + "Buffer did not have sufficient bytes for an IPC message" ))), Err(e) => Some(Err(e)), } diff --git a/vortex-ipc/src/messages/reader_sync.rs b/vortex-ipc/src/messages/reader_sync.rs index f9fbe8b2eeb..7af395eb9ae 100644 --- a/vortex-ipc/src/messages/reader_sync.rs +++ b/vortex-ipc/src/messages/reader_sync.rs @@ -51,7 +51,7 @@ impl Iterator for SyncMessageReader { return None; } return Some(Err(vortex_err!( - InvalidArgument: "unexpected EOF during partial read: read {total_bytes_read} of {nbytes} expected bytes" + "unexpected EOF during partial read: read {total_bytes_read} of {nbytes} expected bytes" ))); } Ok(n) => total_bytes_read += n, @@ -117,7 +117,7 @@ mod tests { let DecoderMessage::Array((parts, ctx, row_count)) = messages.next().vortex_expect("expected a message")? else { - vortex_panic!(AssertionFailed: "expected an array message"); + vortex_panic!("expected an array message"); }; let actual = parts.decode(array.dtype(), row_count, &ctx, &SESSION)?; assert_eq!(actual.len(), array.len()); diff --git a/vortex-ipc/src/stream.rs b/vortex-ipc/src/stream.rs index 8a46692d07c..d8da4935115 100644 --- a/vortex-ipc/src/stream.rs +++ b/vortex-ipc/src/stream.rs @@ -46,10 +46,10 @@ impl AsyncIPCReader { Some(msg) => match msg { DecoderMessage::DType(dtype) => dtype, msg => { - vortex_bail!(MismatchedTypes: "Expected DType message, got {:?}", msg); + vortex_bail!("Expected DType message, got {:?}", msg); } }, - None => vortex_bail!(MismatchedTypes: "Expected DType message, got EOF"), + None => vortex_bail!("Expected DType message, got EOF"), }; let dtype = DType::from_flatbuffer(dtype, session)?; @@ -86,7 +86,7 @@ impl Stream for AsyncIPCReader { .and_then(|array| { if array.dtype() != this.dtype { Err(vortex_err!( - MismatchedTypes: "Array data type mismatch: expected {:?}, got {:?}", + "Array data type mismatch: expected {:?}, got {:?}", this.dtype, array.dtype() )) @@ -96,7 +96,7 @@ impl Stream for AsyncIPCReader { }), )), Ok(msg) => Poll::Ready(Some(Err(vortex_err!( - MismatchedTypes: "Expected Array message, got {:?}", + "Expected Array message, got {:?}", msg )))), Err(e) => Poll::Ready(Some(Err(e))), @@ -183,9 +183,7 @@ impl Stream for ArrayStreamIPCBytes { .encoder .encode(EncoderMessage::DType(this.stream.dtype())) else { - return Poll::Ready(Some(Err( - vortex_err!(Serde: "Failed to encode DType message"), - ))); + return Poll::Ready(Some(Err(vortex_err!("Failed to encode DType message")))); }; this.buffers.extend(buffers); this.written_dtype = true; diff --git a/vortex-jni/src/data_source.rs b/vortex-jni/src/data_source.rs index 098facdbe81..7e50b0d934b 100644 --- a/vortex-jni/src/data_source.rs +++ b/vortex-jni/src/data_source.rs @@ -84,7 +84,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_open( } } if glob_strings.is_empty() { - return Err(vortex_err!(InvalidArgument: "no paths provided").into()); + return Err(vortex_err!("no paths provided").into()); } let glob_urls: Vec = glob_strings @@ -129,10 +129,10 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_openFiles( let count = readables.len(env)?; if count == 0 { - throw_runtime!(InvalidArgument: "no readables provided"); + throw_runtime!("no readables provided"); } if paths.len(env)? != count || lengths.len(env)? != count { - throw_runtime!(InvalidArgument: "readables, paths, and lengths must have equal length"); + throw_runtime!("readables, paths, and lengths must have equal length"); } let mut sizes = vec![0 as jlong; count]; @@ -146,14 +146,14 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_openFiles( let path_obj = paths.get_element(env, idx)?; let path: String = env.cast_local::(path_obj)?.try_to_string(env)?; if path.contains(['*', '?', '[']) { - throw_runtime!(InvalidArgument: "path '{path}' contains glob characters, which are unsupported"); + throw_runtime!("path '{path}' contains glob characters, which are unsupported"); } let size = u64::try_from(sizes[idx]) - .map_err(|_| vortex_err!(InvalidArgument: "negative length for path '{path}'"))?; + .map_err(|_| vortex_err!("negative length for path '{path}'"))?; let readable = readables.get_element(env, idx)?; if readable.is_null() { - throw_runtime!(InvalidArgument: "null readable for path '{path}'"); + throw_runtime!("null readable for path '{path}'"); } let readable = Arc::new(env.new_global_ref(&readable)?); @@ -200,7 +200,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeDataSource_arrowSchema( ) { try_or_throw(&mut env, |_| { if schema_addr == 0 { - throw_runtime!(InvalidArgument: "null arrow schema address"); + throw_runtime!("null arrow schema address"); } let session = unsafe { session_ref(session_ptr) }; let ds = unsafe { NativeDataSource::from_ptr(pointer) }; diff --git a/vortex-jni/src/errors.rs b/vortex-jni/src/errors.rs index 7902d8aada7..0e903406ae0 100644 --- a/vortex-jni/src/errors.rs +++ b/vortex-jni/src/errors.rs @@ -43,7 +43,7 @@ impl From for VortexError { fn from(error: JNIError) -> Self { match error { JNIError::Vortex(error) => error, - JNIError::Custom(error) => vortex_err!(Other: "JNI: {error}"), + JNIError::Custom(error) => vortex_err!("JNI: {error}"), } } } diff --git a/vortex-jni/src/expression.rs b/vortex-jni/src/expression.rs index 1d3d85e0dbd..afcefe990c4 100644 --- a/vortex-jni/src/expression.rs +++ b/vortex-jni/src/expression.rs @@ -111,7 +111,7 @@ fn parse_op(op: jbyte) -> Result { 9 => Operator::Sub, 10 => Operator::Mul, 11 => Operator::Div, - other => throw_runtime!(InvalidArgument: "unknown binary operator code: {other}"), + other => throw_runtime!("unknown binary operator code: {other}"), }) } @@ -127,7 +127,7 @@ fn parse_duplicate_handling(tag: jbyte) -> Result { Ok(match tag { 0 => DuplicateHandling::RightMost, 1 => DuplicateHandling::Error, - other => throw_runtime!(InvalidArgument: "unknown duplicate handling code: {other}"), + other => throw_runtime!("unknown duplicate handling code: {other}"), }) } @@ -215,7 +215,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_pack( let name: FieldName = s.try_to_string(env)?.into(); let expr_ptr = *expressions.get(idx).ok_or_else(|| -> JNIError { - vortex_err!(NotFound: "missing pack expression child").into() + vortex_err!("missing pack expression child").into() })?; let expr = unsafe { expr_ref(expr_ptr) }.clone(); @@ -254,7 +254,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_and( let exprs = collect_operands(env, &operands)?; and_collect(exprs) .map(into_raw) - .ok_or_else(|| vortex_err!(InvalidArgument: "empty AND expression").into()) + .ok_or_else(|| vortex_err!("empty AND expression").into()) }) } @@ -268,7 +268,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_or( let exprs = collect_operands(env, &operands)?; or_collect(exprs) .map(into_raw) - .ok_or_else(|| vortex_err!(InvalidArgument: "empty OR expression").into()) + .ok_or_else(|| vortex_err!("empty OR expression").into()) }) } @@ -323,7 +323,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_spatial( 6 => SpatialIntersects.try_new_expr(EmptyOptions, operands), 7 => SpatialLength.try_new_expr(EmptyOptions, operands), 8 => SpatialMakeLine.try_new_expr(EmptyOptions, operands), - other => throw_runtime!(InvalidArgument: "unknown spatial function code: {other}"), + other => throw_runtime!("unknown spatial function code: {other}"), }?; Ok(into_raw(expr)) }) @@ -551,9 +551,9 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalDecimal( ) -> jlong { try_or_throw(&mut env, |env| { let precision = u8::try_from(precision) - .map_err(|_| vortex_err!(OutOfBounds: "decimal precision out of range: {precision}"))?; - let scale = i8::try_from(scale) - .map_err(|_| vortex_err!(OutOfBounds: "decimal scale out of range: {scale}"))?; + .map_err(|_| vortex_err!("decimal precision out of range: {precision}"))?; + let scale = + i8::try_from(scale).map_err(|_| vortex_err!("decimal scale out of range: {scale}"))?; let decimal_dtype = DecimalDType::try_new(precision, scale)?; if is_null_flag { return Ok(into_raw(lit(Scalar::null(DType::Decimal( @@ -562,7 +562,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalDecimal( ))))); } if unscaled_big_endian.len(env)? > 32 { - throw_runtime!(Overflow: "Decimal value must fit with 32 bytes"); + throw_runtime!("Decimal value must fit with 32 bytes"); } let bytes = env.convert_byte_array(&unscaled_big_endian)?; @@ -582,31 +582,31 @@ fn decimal_value_from_be_bytes( dtype: &DecimalDType, ) -> Result { if bytes.is_empty() { - throw_runtime!(InvalidArgument: "decimal unscaled value must have at least one byte"); + throw_runtime!("decimal unscaled value must have at least one byte"); } let value = i256_from_twos_complement_be(bytes); // Pick the narrowest backing integer that fits the dtype's precision. let required_bits = dtype.required_bit_width(); if required_bits <= 8 { - let v = BigCast::from(value) - .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i8"))?; + let v = + BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i8"))?; Ok(DecimalValue::I8(v)) } else if required_bits <= 16 { - let v = BigCast::from(value) - .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i16"))?; + let v = + BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i16"))?; Ok(DecimalValue::I16(v)) } else if required_bits <= 32 { - let v = BigCast::from(value) - .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i32"))?; + let v = + BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i32"))?; Ok(DecimalValue::I32(v)) } else if required_bits <= 64 { - let v = BigCast::from(value) - .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i64"))?; + let v = + BigCast::from(value).ok_or_else(|| vortex_err!("decimal value does not fit in i64"))?; Ok(DecimalValue::I64(v)) } else if required_bits <= 128 { let v = value .maybe_i128() - .ok_or_else(|| vortex_err!(Overflow: "decimal value does not fit in i128"))?; + .ok_or_else(|| vortex_err!("decimal value does not fit in i128"))?; Ok(DecimalValue::I128(v)) } else { Ok(DecimalValue::I256(value)) @@ -652,11 +652,12 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalDate( return Ok(into_raw(lit(Scalar::null(dtype)))); } let storage_value = match unit { - TimeUnit::Days => ScalarValue::from(i32::try_from(value).map_err( - |_| vortex_err!(Overflow: "date value does not fit in i32 days: {value}"), - )?), + TimeUnit::Days => ScalarValue::from( + i32::try_from(value) + .map_err(|_| vortex_err!("date value does not fit in i32 days: {value}"))?, + ), TimeUnit::Milliseconds => ScalarValue::from(value), - other => throw_runtime!(InvalidArgument: "date does not support time unit {other}"), + other => throw_runtime!("date does not support time unit {other}"), }; Ok(into_raw(lit(Scalar::try_new(dtype, Some(storage_value))?))) }) @@ -721,11 +722,10 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalTime( return Ok(into_raw(lit(Scalar::null(dtype)))); } let storage_value = match unit { - TimeUnit::Seconds | TimeUnit::Milliseconds => { - ScalarValue::from(i32::try_from(value).map_err( - |_| vortex_err!(Overflow: "time value does not fit in i32 {unit}: {value}"), - )?) - } + TimeUnit::Seconds | TimeUnit::Milliseconds => ScalarValue::from( + i32::try_from(value) + .map_err(|_| vortex_err!("time value does not fit in i32 {unit}: {value}"))?, + ), _ => ScalarValue::from(value), }; Ok(into_raw(lit(Scalar::try_new(dtype, Some(storage_value))?))) @@ -746,11 +746,11 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalGeometry( ) -> jlong { try_or_throw(&mut env, |env| { if wkb.is_null() { - throw_runtime!(InvalidArgument: "geometry literal WKB bytes must not be null"); + throw_runtime!("geometry literal WKB bytes must not be null"); } let bytes = env.convert_byte_array(&wkb)?; let scalar = native_geometry_scalar_from_wkb(&bytes, &VortexSession::default())? - .ok_or_else(|| vortex_err!(InvalidArgument: "unsupported WKB geometry type for a geometry literal"))?; + .ok_or_else(|| vortex_err!("unsupported WKB geometry type for a geometry literal"))?; Ok(into_raw(lit(scalar))) }) } @@ -764,9 +764,8 @@ const UUID_BYTE_LEN: usize = 16; /// Arrow's canonical UUID type. The metadata records no version constraint, so the dtype is /// compatible with any UUID column regardless of the UUID versions it contains. fn uuid_dtype(nullability: Nullability) -> Result { - let list_size = u32::try_from(UUID_BYTE_LEN).map_err( - |_| vortex_err!(Overflow: "UUID byte length {UUID_BYTE_LEN} does not fit in u32"), - )?; + let list_size = u32::try_from(UUID_BYTE_LEN) + .map_err(|_| vortex_err!("UUID byte length {UUID_BYTE_LEN} does not fit in u32"))?; let storage_dtype = DType::FixedSizeList( Arc::new(DType::Primitive(PType::U8, Nullability::NonNullable)), list_size, @@ -780,7 +779,7 @@ fn uuid_dtype(nullability: Nullability) -> Result { fn uuid_scalar(bytes: &[u8]) -> Result { if bytes.len() != UUID_BYTE_LEN { throw_runtime!( - InvalidArgument: "UUID literal must be exactly {UUID_BYTE_LEN} bytes, got {}", + "UUID literal must be exactly {UUID_BYTE_LEN} bytes, got {}", bytes.len() ); } @@ -819,7 +818,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalUuid( )?)))); } if value.is_null() { - throw_runtime!(InvalidArgument: "UUID literal bytes must not be null"); + throw_runtime!("UUID literal bytes must not be null"); } let bytes = env.convert_byte_array(&value)?; Ok(into_raw(lit(uuid_scalar(&bytes)?))) @@ -831,9 +830,8 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalUuid( /// SAFETY: `ptr` must satisfy the contract of [`expr_ref`]. unsafe fn literal_scalar<'a>(ptr: jlong, role: &str) -> Result<&'a Scalar, JNIError> { let expr = unsafe { expr_ref(ptr) }; - expr.as_opt::().ok_or_else(|| { - vortex_err!(InvalidArgument: "{role} must be a literal expression, got {expr}").into() - }) + expr.as_opt::() + .ok_or_else(|| vortex_err!("{role} must be a literal expression, got {expr}").into()) } /// The dtype of the literal `ptr`, used as a type prototype, with `nullability` applied. @@ -912,9 +910,8 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalFixedSizeList is_null_flag: jboolean, ) -> jlong { try_or_throw(&mut env, |env| { - let size = u32::try_from(size).map_err( - |_| vortex_err!(InvalidArgument: "fixed-size list size must not be negative: {size}"), - )?; + let size = u32::try_from(size) + .map_err(|_| vortex_err!("fixed-size list size must not be negative: {size}"))?; let element_dtype = unsafe { prototype_dtype( element_type, @@ -932,7 +929,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalFixedSizeList let children = cast_literals(env, &elements, "fixed-size list element", &element_dtype)?; if children.len() != size as usize { throw_runtime!( - InvalidArgument: "fixed-size list literal of size {size} has {} elements", + "fixed-size list literal of size {size} has {} elements", children.len() ); } @@ -961,7 +958,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalStruct( let ptrs = unsafe { fields.get_elements(env, ReleaseMode::NoCopyBack) }?; if ptrs.len() != count { throw_runtime!( - InvalidArgument: "struct literal has {count} field names but {} fields", + "struct literal has {count} field names but {} fields", ptrs.len() ); } @@ -1023,7 +1020,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalMap( let values = cast_literals(env, &values, "map value", &value_dtype)?; if keys.len() != values.len() { throw_runtime!( - InvalidArgument: "map literal has {} keys but {} values", + "map literal has {} keys but {} values", keys.len(), values.len() ); @@ -1061,7 +1058,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeExpression_literalNull( 11 => DType::Primitive(PType::U32, Nullability::Nullable), 12 => DType::Primitive(PType::U64, Nullability::Nullable), 13 => DType::Primitive(PType::F16, Nullability::Nullable), - other => throw_runtime!(InvalidArgument: "unknown null dtype tag: {other}"), + other => throw_runtime!("unknown null dtype tag: {other}"), }; Ok(into_raw(lit(Scalar::null(dtype)))) }) diff --git a/vortex-jni/src/file.rs b/vortex-jni/src/file.rs index 946b0e174e3..552d36675c7 100644 --- a/vortex-jni/src/file.rs +++ b/vortex-jni/src/file.rs @@ -76,7 +76,7 @@ pub(crate) fn extract_metadata( let key_str = env.cast_local::(key_obj)?; let key = key_str.try_to_string(env)?; if val_obj.is_null() { - return Err(vortex_err!(InvalidArgument: "null metadata value for key '{key}'").into()); + return Err(vortex_err!("null metadata value for key '{key}'").into()); } let bytes = env.cast_local::(val_obj)?; segments.insert(key, ByteBuffer::from(env.convert_byte_array(&bytes)?)); @@ -183,14 +183,14 @@ pub extern "system" fn Java_dev_vortex_jni_NativeFiles_readMetadataFromReadable( try_or_throw(&mut env, |env| { let session = unsafe { session_ref(session_ptr) }; if readable.is_null() { - throw_runtime!(InvalidArgument: "null readable"); + throw_runtime!("null readable"); } let name: String = name.try_to_string(env)?; if name.is_empty() { - throw_runtime!(InvalidArgument: "readable name must not be empty"); + throw_runtime!("readable name must not be empty"); } - let length = u64::try_from(length) - .map_err(|_| vortex_err!(InvalidArgument: "negative readable length: {length}"))?; + let length = + u64::try_from(length).map_err(|_| vortex_err!("negative readable length: {length}"))?; let vm = env.get_java_vm()?; let readable = Arc::new(env.new_global_ref(&readable)?); diff --git a/vortex-jni/src/io/mod.rs b/vortex-jni/src/io/mod.rs index cf6d286c98d..d1f2c14df44 100644 --- a/vortex-jni/src/io/mod.rs +++ b/vortex-jni/src/io/mod.rs @@ -140,7 +140,7 @@ pub(crate) mod tests { } std::thread::sleep(Duration::from_millis(10)); } - vortex_bail!(AssertionFailed: "JNI global reference leaked: weak reference still has a referent") + vortex_bail!("JNI global reference leaked: weak reference still has a referent") } #[test] diff --git a/vortex-jni/src/io/read_at.rs b/vortex-jni/src/io/read_at.rs index 182e7877c32..2c45fc347cd 100644 --- a/vortex-jni/src/io/read_at.rs +++ b/vortex-jni/src/io/read_at.rs @@ -135,16 +135,16 @@ impl VortexReadAt for JavaReadable { let _permit = permit; let end = offset .checked_add(length as u64) - .ok_or_else(|| vortex_err!(Overflow: "read {offset}+{length} overflows u64"))?; + .ok_or_else(|| vortex_err!("read {offset}+{length} overflows u64"))?; if end > len { - vortex_bail!(OutOfBounds: "read {offset}..{end} out of bounds for file of length {len}"); + vortex_bail!("read {offset}..{end} out of bounds for file of length {len}"); } // `java.nio.Buffer` capacities are Java ints. if i32::try_from(length).is_err() { - vortex_bail!(Overflow: "read length {length} exceeds ByteBuffer limit"); + vortex_bail!("read length {length} exceeds ByteBuffer limit"); } let joffset = i64::try_from(offset) - .map_err(|_| vortex_err!(Overflow: "read offset {offset} exceeds i64"))?; + .map_err(|_| vortex_err!("read offset {offset} exceeds i64"))?; let mut buffer = ByteBufferMut::with_capacity_aligned(length, alignment); with_jvm(&vm, |env| { @@ -176,7 +176,7 @@ impl VortexReadAt for JavaReadable { .i()?; if remaining != 0 { return Err(vortex_err!( - Io: "readFully returned with {remaining} of {length} bytes unfilled" + "readFully returned with {remaining} of {length} bytes unfilled" ) .into()); } @@ -252,7 +252,7 @@ impl JavaFileSystem { ) -> VortexResult<()> { match self.files.entry_ref(&path) { EntryRef::Occupied(_) => { - vortex_bail!(InvalidArgument: "multiple Java readables normalize to path '{path}'"); + vortex_bail!("multiple Java readables normalize to path '{path}'"); } EntryRef::Vacant(v) => v.insert(JavaFileEntry { readable, size }), }; @@ -294,9 +294,10 @@ impl FileSystem for JavaFileSystem { } async fn open_read(&self, path: &str) -> VortexResult> { - let entry = self.files.get(path).ok_or_else( - || vortex_err!(NotFound: "no Java readable registered for path '{path}'"), - )?; + let entry = self + .files + .get(path) + .ok_or_else(|| vortex_err!("no Java readable registered for path '{path}'"))?; Ok(Arc::new(JavaReadable::new( self.vm.clone(), Arc::clone(&entry.readable), @@ -307,6 +308,6 @@ impl FileSystem for JavaFileSystem { } async fn delete(&self, path: &str) -> VortexResult<()> { - vortex_bail!(InvalidArgument: "delete('{path}') is not supported by a Java-readable file system") + vortex_bail!("delete('{path}') is not supported by a Java-readable file system") } } diff --git a/vortex-jni/src/io/write.rs b/vortex-jni/src/io/write.rs index fd8fc607f94..ffadf400e17 100644 --- a/vortex-jni/src/io/write.rs +++ b/vortex-jni/src/io/write.rs @@ -137,12 +137,12 @@ mod tests { // exits, at which point the attachment is torn down automatically. let attached = thread_vm .is_thread_attached() - .map_err(|e| vortex_err!(Other: "is_thread_attached failed: {e}"))?; + .map_err(|e| vortex_err!("is_thread_attached failed: {e}"))?; assert!(attached, "write upcalls should leave the thread attached"); VortexResult::Ok(()) }) .join() - .map_err(|_| vortex_err!(Other: "writer thread panicked"))??; + .map_err(|_| vortex_err!("writer thread panicked"))??; let written = with_jvm(vm, |env| { let array = env diff --git a/vortex-jni/src/object_store.rs b/vortex-jni/src/object_store.rs index ce30a64a3e1..24d9c80ed1f 100644 --- a/vortex-jni/src/object_store.rs +++ b/vortex-jni/src/object_store.rs @@ -55,9 +55,8 @@ pub(crate) fn make_object_store( // OpenDAL schemes take the services' own property names (e.g. `secret_id`), not environment // names, and mount at the URL authority, which makes the authority-keyed cache sound. if vortex_cloud::opendal::supports_scheme(url.scheme()) { - let path = Path::from_url_path(url.path()).map_err( - |e| vortex_err!(InvalidArgument: "cannot parse url path as object_store Path: {e}"), - )?; + let path = Path::from_url_path(url.path()) + .map_err(|e| vortex_err!("cannot parse url path as object_store Path: {e}"))?; let cache_key = url_cache_key(url, properties); { if let Some(cached) = OPENDAL_STORES.lock().get(&cache_key) { @@ -132,7 +131,7 @@ mod tests { use super::*; fn parse(url: &str) -> VortexResult { - Url::parse(url).map_err(|e| vortex_err!(InvalidArgument: "{e}")) + Url::parse(url).map_err(|e| vortex_err!("{e}")) } #[test] @@ -179,7 +178,7 @@ mod tests { assert_eq!(path.as_ref(), "dir/data file.vortex"); let mut debug_str = String::new(); - write!(&mut debug_str, "{store:?}").map_err(|e| vortex_err!(AssertionFailed: "{e}"))?; + write!(&mut debug_str, "{store:?}").map_err(|e| vortex_err!("{e}"))?; assert!(debug_str.contains("eu-central-9"), "{debug_str}"); assert!(debug_str.contains("localhost:9000"), "{debug_str}"); Ok(()) diff --git a/vortex-jni/src/runtime.rs b/vortex-jni/src/runtime.rs index 4822b7ff721..06d18de8a07 100644 --- a/vortex-jni/src/runtime.rs +++ b/vortex-jni/src/runtime.rs @@ -23,7 +23,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeRuntime_setWorkerThreads( ) { try_or_throw(&mut env, |_| { if n < 0 { - throw_runtime!(InvalidArgument: "worker thread count must be non-negative"); + throw_runtime!("worker thread count must be non-negative"); } POOL.set_workers(n as usize); Ok(()) diff --git a/vortex-jni/src/scan.rs b/vortex-jni/src/scan.rs index 82324ccfaef..125558256f9 100644 --- a/vortex-jni/src/scan.rs +++ b/vortex-jni/src/scan.rs @@ -104,7 +104,7 @@ fn build_scan_request( ))?), 3 => Selection::IncludeRoaring(deserialize_roaring_selection(selection_roaring_bitmap)?), 4 => Selection::ExcludeRoaring(deserialize_roaring_selection(selection_roaring_bitmap)?), - other => vortex_bail!(Serde: "unknown selection include code: {other}"), + other => vortex_bail!("unknown selection include code: {other}"), }; let row_range = (row_range_begin > 0 || row_range_end > 0).then_some(Range { @@ -128,7 +128,7 @@ fn build_scan_request( fn deserialize_roaring_selection(bytes: &[u8]) -> VortexResult { if bytes.is_empty() { - vortex_bail!(Serde: "serialized roaring row selection must not be empty"); + vortex_bail!("serialized roaring row selection must not be empty"); } let cursor = Cursor::new(bytes); Ok(roaring::RoaringTreemap::deserialize_from(cursor)?) @@ -162,7 +162,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeScan_create( let mut out: Vec = Vec::with_capacity(elements.len()); for v in elements.iter() { if *v < 0 { - throw_runtime!(InvalidArgument: "row selection index must be non-negative"); + throw_runtime!("row selection index must be non-negative"); } out.push(*v as u64); } @@ -215,12 +215,12 @@ pub extern "system" fn Java_dev_vortex_jni_NativeScan_arrowSchema( ) { try_or_throw(&mut env, |_| { if schema_addr == 0 { - throw_runtime!(InvalidArgument: "null arrow schema address"); + throw_runtime!("null arrow schema address"); } let session = unsafe { session_ref(session_ptr) }; let scan = unsafe { &*(pointer as *const NativeScan) }; let NativeScan::Pending(scan) = scan else { - throw_runtime!(InvalidArgument: "schema unavailable: scan already started"); + throw_runtime!("schema unavailable: scan already started"); }; let arrow_schema = session.arrow().to_arrow_schema(scan.dtype())?; let ffi_schema = FFI_ArrowSchema::try_from(&arrow_schema)?; @@ -242,7 +242,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativeScan_partitionCount( try_or_throw(&mut env, |env| { let scan = unsafe { &*(pointer as *const NativeScan) }; let NativeScan::Pending(scan) = scan else { - throw_runtime!(InvalidArgument: "partition count unavailable: scan already started"); + throw_runtime!("partition count unavailable: scan already started"); }; let (rows, cardinality) = match scan.partition_count() { Precision::Exact(v) => (v as jlong, 2), @@ -312,7 +312,7 @@ pub extern "system" fn Java_dev_vortex_jni_NativePartition_rowCount( try_or_throw(&mut env, |env| { let partition = unsafe { &*(pointer as *const NativePartition) }; let NativePartition::Pending(partition) = partition else { - throw_runtime!(InvalidArgument: "row count unavailable: partition already started"); + throw_runtime!("row count unavailable: partition already started"); }; let (rows, cardinality) = match partition.row_count() { Precision::Exact(v) => (v as jlong, 2), @@ -343,12 +343,12 @@ pub extern "system" fn Java_dev_vortex_jni_NativePartition_scanArrow( try_or_throw(&mut env, |_| { if stream_addr == 0 { - throw_runtime!(InvalidArgument: "null arrow stream address"); + throw_runtime!("null arrow stream address"); } let partition = match partition { NativePartition::Pending(p) => p, - _ => throw_runtime!(InvalidArgument: "partition already consumed"), + _ => throw_runtime!("partition already consumed"), }; let array_stream = partition.execute()?; diff --git a/vortex-jni/src/writer.rs b/vortex-jni/src/writer.rs index 027fd00c006..794aa1cc65c 100644 --- a/vortex-jni/src/writer.rs +++ b/vortex-jni/src/writer.rs @@ -86,7 +86,7 @@ fn resolve_store( if url.scheme() == "file" { let path = url .to_file_path() - .map_err(|_| vortex_err!(InvalidArgument: "invalid file URL: {url_or_path}"))?; + .map_err(|_| vortex_err!("invalid file URL: {url_or_path}"))?; Ok(ResolvedStore::Path(path)) } else { let (store, path) = make_object_store(&url, properties)?; @@ -148,7 +148,7 @@ impl NativeWriter { .from_arrow_record_batch(batch, self.arrow_schema.as_ref())?; if !vortex_batch.dtype().eq(&self.write_schema) { return Err(vortex_err!( - MismatchedTypes: "write schema mismatch: expected {}, got {}", + "write schema mismatch: expected {}, got {}", self.write_schema, vortex_batch.dtype() )); @@ -156,7 +156,7 @@ impl NativeWriter { let mut sender = self.sender.clone(); RUNTIME .block_on(async move { sender.send(Ok(vortex_batch)).await }) - .map_err(|e| vortex_err!(Io: "failed to send batch: {e}")) + .map_err(|e| vortex_err!("failed to send batch: {e}")) } fn bytes_written(&self) -> u64 { @@ -172,14 +172,13 @@ impl NativeWriter { let handle = self .handle .take() - .ok_or_else(|| vortex_err!(InvalidArgument: "writer already closed"))?; + .ok_or_else(|| vortex_err!("writer already closed"))?; RUNTIME.block_on(handle) } } fn checked_jlong(value: u64, name: &str) -> VortexResult { - jlong::try_from(value) - .map_err(|_| vortex_err!(Overflow: "{name} exceeds Java long range: {value}")) + jlong::try_from(value).map_err(|_| vortex_err!("{name} exceeds Java long range: {value}")) } fn exact_count_jlong( @@ -255,7 +254,7 @@ fn scalar_to_java<'local>( ScalarValue::Decimal(value) => { let DType::Decimal(decimal_dtype, _) = scalar.dtype() else { return Err(JNIError::Vortex(vortex_err!( - MismatchedTypes: "decimal statistic has non-decimal dtype {}", + "decimal statistic has non-decimal dtype {}", scalar.dtype() ))); }; @@ -273,7 +272,7 @@ fn scalar_to_java<'local>( ScalarValue::Binary(value) => Ok(env.byte_array_from_slice(value.as_slice())?.into()), ScalarValue::Tuple(_) | ScalarValue::Union(_) | ScalarValue::Variant(_) => { Err(JNIError::Vortex(vortex_err!( - NotImplemented: "cannot return nested scalar write statistic with dtype {} to Java", + "cannot return nested scalar write statistic with dtype {} to Java", scalar.dtype() ))) } @@ -288,7 +287,7 @@ fn write_summary_to_java<'local>( let file_stats = summary.footer().statistics(); let columns = env.new_object_array( i32::try_from(column_sizes.len()) - .map_err(|_| vortex_err!(Overflow: "column count exceeds Java array range"))?, + .map_err(|_| vortex_err!("column count exceeds Java array range"))?, jni::jni_str!("dev/vortex/api/VortexColumnStatistics"), JObject::null(), )?; @@ -323,9 +322,10 @@ fn write_summary_to_java<'local>( jni::jni_str!("dev/vortex/api/VortexColumnStatistics"), jni::jni_sig!("(IJJJJLjava/lang/Object;Ljava/lang/Object;)V"), &[ - JValue::Int(i32::try_from(column_index).map_err( - |_| vortex_err!(Overflow: "column index exceeds Java int range"), - )?), + JValue::Int( + i32::try_from(column_index) + .map_err(|_| vortex_err!("column index exceeds Java int range"))?, + ), JValue::Long(checked_jlong(compressed_size, "compressed column size")?), JValue::Long(checked_jlong(summary.row_count(), "row count")?), JValue::Long(null_count), @@ -362,10 +362,10 @@ pub extern "system" fn Java_dev_vortex_jni_NativeWriter_create( ) -> jlong { try_or_throw(&mut env, |env| { if session_ptr == 0 { - throw_runtime!(InvalidArgument: "null session pointer"); + throw_runtime!("null session pointer"); } if arrow_schema_addr == 0 { - throw_runtime!(InvalidArgument: "null arrow schema address"); + throw_runtime!("null arrow schema address"); } let session = unsafe { session_ref(session_ptr) }; @@ -446,13 +446,13 @@ pub extern "system" fn Java_dev_vortex_jni_NativeWriter_createStream( ) -> jlong { try_or_throw(&mut env, |env| { if session_ptr == 0 { - throw_runtime!(InvalidArgument: "null session pointer"); + throw_runtime!("null session pointer"); } if arrow_schema_addr == 0 { - throw_runtime!(InvalidArgument: "null arrow schema address"); + throw_runtime!("null arrow schema address"); } if writable.is_null() { - throw_runtime!(InvalidArgument: "null writable"); + throw_runtime!("null writable"); } let session = unsafe { session_ref(session_ptr) }; @@ -511,12 +511,8 @@ pub extern "system" fn Java_dev_vortex_jni_NativeWriter_writeBatch( unsafe { FFI_ArrowArray::from_raw(arrow_array_addr as *mut FFI_ArrowArray) }; let ffi_schema = unsafe { &*(arrow_schema_addr as *const FFI_ArrowSchema) }; - let array_data = - unsafe { arrow_array::ffi::from_ffi(ffi_array, ffi_schema) }.map_err(|e| { - JNIError::Vortex( - vortex_err!(InvalidArgument: "failed to import Arrow FFI data: {e}"), - ) - })?; + let array_data = unsafe { arrow_array::ffi::from_ffi(ffi_array, ffi_schema) } + .map_err(|e| JNIError::Vortex(vortex_err!("failed to import Arrow FFI data: {e}")))?; let batch = RecordBatch::from(StructArray::from(array_data)); writer.write_record_batch(batch)?; diff --git a/vortex-json/src/dtype.rs b/vortex-json/src/dtype.rs index d289ef9f341..2c5b30aeddd 100644 --- a/vortex-json/src/dtype.rs +++ b/vortex-json/src/dtype.rs @@ -31,14 +31,14 @@ impl ExtVTable for Json { } fn deserialize_metadata(&self, metadata: &[u8]) -> VortexResult { - vortex_ensure!(metadata.is_empty(), Serde: "JSON metadata must be empty"); + vortex_ensure!(metadata.is_empty(), "JSON metadata must be empty"); Ok(EmptyMetadata) } fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( ext_dtype.storage_dtype().is_utf8(), - MismatchedTypes: "JSON storage dtype must be utf8, got {}", + "JSON storage dtype must be utf8, got {}", ext_dtype.storage_dtype() ); Ok(()) @@ -49,7 +49,7 @@ impl ExtVTable for Json { storage_value: &'a ScalarValue, ) -> VortexResult> { let ScalarValue::Utf8(value) = storage_value else { - vortex_bail!(MismatchedTypes: "JSON storage scalar must be utf8, got {storage_value}"); + vortex_bail!("JSON storage scalar must be utf8, got {storage_value}"); }; Ok(value.as_str()) } diff --git a/vortex-json/src/json_to_variant.rs b/vortex-json/src/json_to_variant.rs index 2ebd2562a24..32538b7ad3d 100644 --- a/vortex-json/src/json_to_variant.rs +++ b/vortex-json/src/json_to_variant.rs @@ -121,7 +121,7 @@ impl ScalarFnVTable for JsonToVariant { let dtype = field .dtype .as_ref() - .ok_or_else(|| vortex_err!(NotFound: "ShreddingSpecField missing dtype")) + .ok_or_else(|| vortex_err!("ShreddingSpecField missing dtype")) .and_then(|dtype| DType::from_proto(dtype, session))?; Ok((path, dtype)) }) @@ -147,7 +147,7 @@ impl ScalarFnVTable for JsonToVariant { input_dtype .as_extension_opt() .is_some_and(|ext_dtype| ext_dtype.is::()), - MismatchedTypes: "JsonToVariant input must be a Json extension, found {input_dtype}" + "JsonToVariant input must be a Json extension, found {input_dtype}" ); Ok(DType::Variant(input_dtype.nullability())) @@ -169,7 +169,7 @@ impl ScalarFnVTable for JsonToVariant { // looping. let no_kernel = || { vortex_err!( - InvalidArgument: "json_to_variant requires a registered Variant encoding to build Variant values \ + "json_to_variant requires a registered Variant encoding to build Variant values \ from JSON, but none is registered with this session" ) }; @@ -185,7 +185,7 @@ impl ScalarFnVTable for JsonToVariant { input.execute::(ctx)?.into_array() } else { vortex_bail!( - MismatchedTypes: "JsonToVariant input must be a Json extension, found {}", + "JsonToVariant input must be a Json extension, found {}", input.dtype() ); }; @@ -243,7 +243,7 @@ impl ShreddingSpec { path.elements() .iter() .all(|element| matches!(element, VariantPathElement::Field(_))), - InvalidArgument: "ShreddingSpec paths must only contain object fields, found list index in {path}" + "ShreddingSpec paths must only contain object fields, found list index in {path}" ); } Ok(Self(fields)) diff --git a/vortex-layout/examples/reverse_index/main.rs b/vortex-layout/examples/reverse_index/main.rs index 6114e5f9f7f..a03a16d2d20 100644 --- a/vortex-layout/examples/reverse_index/main.rs +++ b/vortex-layout/examples/reverse_index/main.rs @@ -214,7 +214,7 @@ impl IndexVTable for ReverseIndex { let mut buffer = Vec::with_capacity(bitmap.serialized_size()); bitmap .serialize_into(&mut buffer) - .map_err(|err| vortex_err!(Serde: "Failed to serialize postings: {err}"))?; + .map_err(|err| vortex_err!("Failed to serialize postings: {err}"))?; lists.push(buffer); } @@ -244,7 +244,7 @@ impl IndexVTable for ReverseIndex { let postings = (0..lists.len()) .map(|idx| { RoaringBitmap::deserialize_from(lists.bytes_at(idx).as_slice()) - .map_err(|err| vortex_err!(Serde: "Failed to deserialize postings: {err}")) + .map_err(|err| vortex_err!("Failed to deserialize postings: {err}")) }) .collect::>()?; Ok(Entries { @@ -391,10 +391,10 @@ fn demo_session() -> VortexResult { .with::(); session .register_edition(&DEMO_EDITION_DECLARATION) - .map_err(|err| vortex_err!(Io: "{err}"))?; + .map_err(|err| vortex_err!("{err}"))?; session .enable_edition(DEMO_EDITION) - .map_err(|err| vortex_err!(Io: "{err}"))?; + .map_err(|err| vortex_err!("{err}"))?; session.indexes().register(ReverseIndex::new_ref()); Ok(session) } diff --git a/vortex-layout/src/arrays/shared/vtable.rs b/vortex-layout/src/arrays/shared/vtable.rs index a1a3df88895..e97505b0eb3 100644 --- a/vortex-layout/src/arrays/shared/vtable.rs +++ b/vortex-layout/src/arrays/shared/vtable.rs @@ -71,8 +71,8 @@ impl VTable for Shared { let source = slots[SharedSlots::SOURCE] .as_ref() .vortex_expect("SharedArray source slot must be present"); - vortex_error::vortex_ensure_eq!(source.dtype(), dtype, MismatchedTypes: "SharedArray dtype mismatch"); - vortex_error::vortex_ensure_eq!(source.len(), len, InvalidArgument: "SharedArray len mismatch"); + vortex_error::vortex_ensure_eq!(source.dtype(), dtype, "SharedArray dtype mismatch"); + vortex_error::vortex_ensure_eq!(source.len(), len, "SharedArray len mismatch"); Ok(()) } @@ -81,7 +81,7 @@ impl VTable for Shared { } fn buffer(_array: ArrayView<'_, Self>, _idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "SharedArray has no buffers") + vortex_panic!("SharedArray has no buffers") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -104,7 +104,7 @@ impl VTable for Shared { _array: ArrayView<'_, Self>, _session: &VortexSession, ) -> VortexResult>> { - vortex_error::vortex_bail!(Serde: "Shared array is not serializable") + vortex_error::vortex_bail!("Shared array is not serializable") } fn deserialize( @@ -117,7 +117,7 @@ impl VTable for Shared { _children: &dyn vortex_array::serde::ArrayChildren, _session: &VortexSession, ) -> VortexResult> { - vortex_error::vortex_bail!(Serde: "Shared array is not serializable") + vortex_error::vortex_bail!("Shared array is not serializable") } fn execute(array: Array, ctx: &mut ExecutionCtx) -> VortexResult { diff --git a/vortex-layout/src/children.rs b/vortex-layout/src/children.rs index 6079bbc0151..a1a582f72c2 100644 --- a/vortex-layout/src/children.rs +++ b/vortex-layout/src/children.rs @@ -100,11 +100,11 @@ impl LayoutChildren for OwnedLayoutChildren { fn child(&self, idx: usize, dtype: &DType) -> VortexResult { if idx >= self.0.len() { - vortex_bail!(OutOfBounds: "Child index out of bounds: {} of {}", idx, self.0.len()); + vortex_bail!("Child index out of bounds: {} of {}", idx, self.0.len()); } let child = &self.0[idx]; if child.dtype() != dtype { - vortex_bail!(MismatchedTypes: "Child dtype mismatch: {} != {}", child.dtype(), dtype); + vortex_bail!("Child dtype mismatch: {} != {}", child.dtype(), dtype); } Ok(Arc::clone(child)) } @@ -199,7 +199,7 @@ impl ViewedLayoutChildren { let encoding_id = self .layout_read_ctx .resolve(fb_layout.encoding()) - .ok_or_else(|| vortex_err!(NotFound: "Encoding not found: {}", fb_layout.encoding()))?; + .ok_or_else(|| vortex_err!("Encoding not found: {}", fb_layout.encoding()))?; let children = fb_layout .children() @@ -234,7 +234,7 @@ impl LayoutChildren for ViewedLayoutChildren { fn child(&self, idx: usize, dtype: &DType) -> VortexResult { if idx >= self.nchildren() { - vortex_bail!(OutOfBounds: "Child index out of bounds: {} of {}", idx, self.nchildren()); + vortex_bail!("Child index out of bounds: {} of {}", idx, self.nchildren()); } let layout_ref = self.cache[idx].get_or_try_init(|| { @@ -258,13 +258,13 @@ impl LayoutChildren for ViewedLayoutChildren { .layout_read_ctx .resolve(fb_child.encoding()) .ok_or_else(|| { - vortex_err!(NotFound: "Unknown layout encoding index: {}", fb_child.encoding()) + vortex_err!("Unknown layout encoding index: {}", fb_child.encoding()) })?; let Some(encoding) = self.layouts.get(&encoding_id) else { if self.allow_unknown { return viewed_children.foreign_layout_from_fb(fb_child, dtype); } - vortex_bail!(NotFound: "Unknown layout encoding: {encoding_id}"); + vortex_bail!("Unknown layout encoding: {encoding_id}"); }; let build_ctx = LayoutBuildContext { diff --git a/vortex-layout/src/layouts/chunked/mod.rs b/vortex-layout/src/layouts/chunked/mod.rs index 02959600145..459429046c2 100644 --- a/vortex-layout/src/layouts/chunked/mod.rs +++ b/vortex-layout/src/layouts/chunked/mod.rs @@ -65,7 +65,7 @@ impl VTable for Chunked { ) -> VortexResult { let chunk_offsets = chunk_offsets(args.children)?; if chunk_offsets.last().copied() != Some(args.row_count) { - vortex_bail!(InvalidArgument: "Chunked child row counts do not add up to parent row count"); + vortex_bail!("Chunked child row counts do not add up to parent row count"); } Ok(ChunkedData { chunk_offsets }) } @@ -134,7 +134,7 @@ fn chunk_offsets(children: &dyn LayoutChildren) -> VortexResult> { offsets.push( offsets[idx] .checked_add(children.child_row_count(idx)) - .ok_or_else(|| vortex_err!(Overflow: "Chunked child row counts overflow"))?, + .ok_or_else(|| vortex_err!("Chunked child row counts overflow"))?, ); } Ok(offsets) diff --git a/vortex-layout/src/layouts/chunked/reader.rs b/vortex-layout/src/layouts/chunked/reader.rs index 9e89d991f57..c658a83bb46 100644 --- a/vortex-layout/src/layouts/chunked/reader.rs +++ b/vortex-layout/src/layouts/chunked/reader.rs @@ -134,7 +134,7 @@ impl ChunkedReader { fn chunk_offset(&self, idx: usize) -> u64 { if idx >= self.layout.chunk_offsets.len() { vortex_panic!( - AssertionFailed: "Internal error: Chunk offset {idx} out of bounds (num_children: {}, num_offsets: {}). \ + "Internal error: Chunk offset {idx} out of bounds (num_children: {}, num_offsets: {}). \ This indicates a bug in ChunkedReader initialization or chunk_range calculation.", self.layout.nchildren(), self.layout.chunk_offsets.len() @@ -415,7 +415,7 @@ impl LayoutReader for ChunkedReader { // Split the mask over each chunk. let chunks: Vec<_> = FuturesOrdered::from_iter(chunk_evals).try_collect().await?; - vortex_ensure!(!chunks.is_empty(), AssertionFailed: "Empty chunks were checked earlier"); + vortex_ensure!(!chunks.is_empty(), "Empty chunks were checked earlier"); // If there is only one chunk, we can return it directly. if chunks.len() == 1 { diff --git a/vortex-layout/src/layouts/dict/mod.rs b/vortex-layout/src/layouts/dict/mod.rs index d7442ee3436..eee88f916d3 100644 --- a/vortex-layout/src/layouts/dict/mod.rs +++ b/vortex-layout/src/layouts/dict/mod.rs @@ -74,7 +74,7 @@ impl VTable for Dict { vortex_ensure_eq!( args.children.nchildren(), 2, - InvalidArgument: "DictLayout expects exactly 2 children" + "DictLayout expects exactly 2 children" ); let codes_nullable = metadata .is_nullable_codes @@ -86,7 +86,7 @@ impl VTable for Dict { vortex_ensure_eq!( codes.row_count(), args.row_count, - InvalidArgument: "Dictionary codes row count does not match parent" + "Dictionary codes row count does not match parent" ); Ok(DictData { codes_dtype, @@ -98,7 +98,7 @@ impl VTable for Dict { match idx { 0 => Ok(layout.dtype().clone()), 1 => Ok(layout.codes_dtype.clone()), - _ => vortex_bail!(OutOfBounds: "Dict child index out of bounds: {idx}"), + _ => vortex_bail!("Dict child index out of bounds: {idx}"), } } @@ -106,7 +106,7 @@ impl VTable for Dict { match idx { 0 => LayoutChildType::Auxiliary("values".into()), 1 => LayoutChildType::Transparent("codes".into()), - _ => vortex_panic!(OutOfBounds: "Dict child index out of bounds: {idx}"), + _ => vortex_panic!("Dict child index out of bounds: {idx}"), } } diff --git a/vortex-layout/src/layouts/dict/writer.rs b/vortex-layout/src/layouts/dict/writer.rs index e0f562bc11e..7808777a8c2 100644 --- a/vortex-layout/src/layouts/dict/writer.rs +++ b/vortex-layout/src/layouts/dict/writer.rs @@ -423,7 +423,7 @@ impl Stream for DictionaryTransformer { // Receiver dropped, close this group self.active_codes_tx = None; if let Some(values_tx) = self.active_values_tx.take() { - drop(values_tx.send(Err(vortex_err!(Io: "values receiver dropped")))); + drop(values_tx.send(Err(vortex_err!("values receiver dropped")))); } } Poll::Pending => { @@ -467,7 +467,7 @@ impl Stream for DictionaryTransformer { let values_future = async move { values_rx .await - .map_err(|e| vortex_err!(Io: "values sender dropped: {}", e)) + .map_err(|e| vortex_err!("values sender dropped: {}", e)) .flatten() } .boxed(); @@ -501,7 +501,7 @@ impl Stream for DictionaryTransformer { Poll::Ready(None) => { // Handle any incomplete group if let Some(values_tx) = self.active_values_tx.take() { - drop(values_tx.send(Err(vortex_err!(Io: "Incomplete dictionary group")))); + drop(values_tx.send(Err(vortex_err!("Incomplete dictionary group")))); } self.active_codes_tx = None; return Poll::Ready(None); diff --git a/vortex-layout/src/layouts/file_stats.rs b/vortex-layout/src/layouts/file_stats.rs index dbbba0fd939..97669808eef 100644 --- a/vortex-layout/src/layouts/file_stats.rs +++ b/vortex-layout/src/layouts/file_stats.rs @@ -466,7 +466,7 @@ impl FileStatsAccumulator { if dtype.nullability() == Nullability::Nullable { // top level dtype could be nullable, but we don't support it yet vortex_panic!( - NotImplemented: "FileStatsAccumulator temporarily does not support nullable top-level structs, got: {}. Use Validity::NonNullable", + "FileStatsAccumulator temporarily does not support nullable top-level structs, got: {}. Use Validity::NonNullable", dtype ); } diff --git a/vortex-layout/src/layouts/flat/mod.rs b/vortex-layout/src/layouts/flat/mod.rs index b860ee8bf1b..6913d2fc0c4 100644 --- a/vortex-layout/src/layouts/flat/mod.rs +++ b/vortex-layout/src/layouts/flat/mod.rs @@ -83,10 +83,10 @@ impl VTable for Flat { metadata: &FlatLayoutMetadata, ) -> VortexResult { if args.segment_ids.len() != 1 { - vortex_bail!(InvalidArgument: "Flat layout must have exactly one segment ID"); + vortex_bail!("Flat layout must have exactly one segment ID"); } if args.children.nchildren() != 0 { - vortex_bail!(InvalidArgument: "Flat layout must not have children"); + vortex_bail!("Flat layout must not have children"); } Ok(FlatData { segment_id: args.segment_ids[0], @@ -99,11 +99,11 @@ impl VTable for Flat { } fn child_dtype(_layout: &Layout, idx: usize) -> VortexResult { - vortex_bail!(OutOfBounds: "Flat layout has no child {idx}") + vortex_bail!("Flat layout has no child {idx}") } fn child_type(_layout: &Layout, idx: usize) -> LayoutChildType { - vortex_panic!(OutOfBounds: "Flat layout has no child {idx}") + vortex_panic!("Flat layout has no child {idx}") } fn new_reader( diff --git a/vortex-layout/src/layouts/flat/writer.rs b/vortex-layout/src/layouts/flat/writer.rs index e6272980cc0..ac8bd44045a 100644 --- a/vortex-layout/src/layouts/flat/writer.rs +++ b/vortex-layout/src/layouts/flat/writer.rs @@ -157,7 +157,7 @@ impl LayoutStrategy for FlatLayoutStrategy { let segment_id = segment_sink.write(sequence_id, buffers).await?; let None = stream.next().await else { - vortex_bail!(InvalidArgument: "flat layout received stream with more than a single chunk"); + vortex_bail!("flat layout received stream with more than a single chunk"); }; Ok(FlatLayout::new_with_metadata( row_count, diff --git a/vortex-layout/src/layouts/foreign/mod.rs b/vortex-layout/src/layouts/foreign/mod.rs index c33126f604d..c2e32ffa253 100644 --- a/vortex-layout/src/layouts/foreign/mod.rs +++ b/vortex-layout/src/layouts/foreign/mod.rs @@ -172,7 +172,7 @@ impl DynLayout for ForeignLayout { _ctx: &crate::LayoutReaderContext, ) -> VortexResult { vortex_bail!( - NotFound: "Cannot read unknown layout encoding '{}'", + "Cannot read unknown layout encoding '{}'", self.encoding.id() ) } diff --git a/vortex-layout/src/layouts/indexed/mod.rs b/vortex-layout/src/layouts/indexed/mod.rs index d82a9a32cd7..d668e7b9363 100644 --- a/vortex-layout/src/layouts/indexed/mod.rs +++ b/vortex-layout/src/layouts/indexed/mod.rs @@ -186,26 +186,26 @@ impl IndexPartitioning { fn validate(&self, id: IndexId, data_row_count: u64, index_row_count: u64) -> VortexResult<()> { vortex_ensure!( self.partition_len > 0, - InvalidArgument: "Index {id} has a zero partition length" + "Index {id} has a zero partition length" ); let expected = data_row_count.div_ceil(self.partition_len); vortex_ensure!( self.index_ends.len() as u64 == expected, - InvalidArgument: "Index {id} has {} partitions, expected {expected} for {data_row_count} rows at {} rows each", + "Index {id} has {} partitions, expected {expected} for {data_row_count} rows at {} rows each", self.index_ends.len(), self.partition_len ); vortex_ensure!( self.index_ends.is_sorted(), - InvalidArgument: "Index {id} partition ends must be non-decreasing" + "Index {id} partition ends must be non-decreasing" ); vortex_ensure!( self.index_ends.last().copied().unwrap_or(0) == index_row_count, - InvalidArgument: "Index {id} partition ends do not cover its {index_row_count}-row child" + "Index {id} partition ends do not cover its {index_row_count}-row child" ); vortex_ensure!( self.declined.max().is_none_or(|p| u64::from(p) < expected), - InvalidArgument: "Index {id} declines a partition past its last" + "Index {id} declines a partition past its last" ); Ok(()) } @@ -288,14 +288,14 @@ impl IndexedLayout { ) -> VortexResult { vortex_ensure!( index_layouts.len() == indexes.len(), - InvalidArgument: "IndexedLayout got {} index children for {} specs", + "IndexedLayout got {} index children for {} specs", index_layouts.len(), indexes.len() ); for (layout, spec) in index_layouts.iter().zip(&indexes) { vortex_ensure!( layout.dtype() == &spec.index_dtype, - MismatchedTypes: "Index child dtype {} does not match spec dtype {} for {}", + "Index child dtype {} does not match spec dtype {} for {}", layout.dtype(), spec.index_dtype, spec.id @@ -375,7 +375,7 @@ impl VTable for Indexed { ) -> VortexResult { vortex_ensure!( args.children.nchildren() == 1 + metadata.indexes.len(), - InvalidArgument: "IndexedLayout expects {} children (data + {} indexes), got {}", + "IndexedLayout expects {} children (data + {} indexes), got {}", 1 + metadata.indexes.len(), metadata.indexes.len(), args.children.nchildren() @@ -392,9 +392,7 @@ impl VTable for Indexed { .as_ref() .map(|dtype| DType::from_proto(dtype, args.session)) .transpose()? - .ok_or_else( - || vortex_err!(Serde: "Index spec {} is missing its dtype", spec.id), - )?; + .ok_or_else(|| vortex_err!("Index spec {} is missing its dtype", spec.id))?; let id = IndexId::from(spec.id.as_str()); let partitioning = spec @@ -442,7 +440,7 @@ impl VTable for Indexed { 0 => Ok(layout.dtype().clone()), _ => { let Some(spec) = layout.indexes.get(slot - 1) else { - vortex_bail!(OutOfBounds: "Invalid child index: {}", slot); + vortex_bail!("Invalid child index: {}", slot); }; Ok(spec.index_dtype.clone()) } @@ -454,7 +452,7 @@ impl VTable for Indexed { 0 => LayoutChildType::Transparent("data".into()), _ => match layout.indexes.get(slot - 1) { Some(spec) => LayoutChildType::Auxiliary(format!("index:{}", spec.id).into()), - None => vortex_panic!(OutOfBounds: "Invalid child index: {}", slot), + None => vortex_panic!("Invalid child index: {}", slot), }, } } @@ -527,16 +525,16 @@ impl DeserializeMetadata for IndexedMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { let Some((&version, proto_bytes)) = metadata.split_first() else { - vortex_bail!(Serde: "Indexed metadata missing protobuf version"); + vortex_bail!("Indexed metadata missing protobuf version"); }; vortex_ensure!( version == INDEXED_METADATA_VERSION, - Serde: "Unsupported indexed metadata version: {}", + "Unsupported indexed metadata version: {}", version ); let proto = IndexedMetadataProto::decode(proto_bytes) - .map_err(|err| vortex_err!(Serde: "Failed to decode indexed metadata: {err}"))?; + .map_err(|err| vortex_err!("Failed to decode indexed metadata: {err}"))?; Ok(Self { indexes: proto.indexes.into(), }) diff --git a/vortex-layout/src/layouts/indexed/test_harness.rs b/vortex-layout/src/layouts/indexed/test_harness.rs index 716e4f197cb..90a126b83d2 100644 --- a/vortex-layout/src/layouts/indexed/test_harness.rs +++ b/vortex-layout/src/layouts/indexed/test_harness.rs @@ -29,17 +29,17 @@ pub fn check_roundtrip( let parsed = vtable.deserialize_options(&blob)?; vortex_ensure!( vtable.serialize_options(&parsed) == blob, - AssertionFailed: "Index {} options do not re-serialize to the same blob", + "Index {} options do not re-serialize to the same blob", vtable.id() ); - let declared = vtable.index_dtype(data_dtype, options).ok_or_else( - || vortex_err!(AssertionFailed: "Index {} cannot index {data_dtype}", vtable.id()), - )?; + let declared = vtable + .index_dtype(data_dtype, options) + .ok_or_else(|| vortex_err!("Index {} cannot index {data_dtype}", vtable.id()))?; let encoded = vtable.encode(chunk, options, ctx)?; vortex_ensure!( encoded.dtype() == &declared, - AssertionFailed: "Index {} encoded dtype {}, but declared {declared}", + "Index {} encoded dtype {}, but declared {declared}", vtable.id(), encoded.dtype() ); diff --git a/vortex-layout/src/layouts/indexed/tests.rs b/vortex-layout/src/layouts/indexed/tests.rs index cd0fa567b49..f2f28b54509 100644 --- a/vortex-layout/src/layouts/indexed/tests.rs +++ b/vortex-layout/src/layouts/indexed/tests.rs @@ -149,7 +149,7 @@ fn partitioned_strategy(configs: Vec) -> IndexedStrategy { fn partitioned(config: IndexConfig, partition_len: u64) -> VortexResult { let partition_len = NonZeroU64::new(partition_len) - .ok_or_else(|| vortex_err!(AssertionFailed: "partition length must be non-zero"))?; + .ok_or_else(|| vortex_err!("partition length must be non-zero"))?; Ok(config.with_partition_len(partition_len)) } @@ -336,7 +336,7 @@ async fn layout_carries_one_auxiliary_child_per_index() -> VortexResult<()> { // Index content is an ordinary layout tree, so it inherits chunking and zone maps for free. let index_child = layout .slot(1)? - .ok_or_else(|| vortex_err!(AssertionFailed: "an exact-value index was configured"))?; + .ok_or_else(|| vortex_err!("an exact-value index was configured"))?; assert_eq!( index_child .dtype() @@ -512,7 +512,7 @@ async fn writer_rejects_an_index_that_does_not_match_its_declared_dtype() -> Vor .await; let Err(err) = result else { - vortex_bail!(AssertionFailed: "writing an index that does not match its declared dtype should fail"); + vortex_bail!("writing an index that does not match its declared dtype should fail"); }; assert!(err.to_string().contains("declared"), "{err}"); Ok(()) @@ -551,10 +551,10 @@ async fn index_whose_stored_dtype_no_longer_matches_its_kind_is_skipped() -> Vor ); let data = layout .slot(0)? - .ok_or_else(|| vortex_err!(AssertionFailed: "indexed layout has a data child"))?; + .ok_or_else(|| vortex_err!("indexed layout has a data child"))?; let index = layout .slot(1)? - .ok_or_else(|| vortex_err!(AssertionFailed: "an index was configured"))?; + .ok_or_else(|| vortex_err!("an index was configured"))?; let changed = IndexedLayout::try_new(data, vec![index], vec![changed])?.into_layout(); let reader = text_reader(&session, &changed, segments)?; @@ -578,7 +578,7 @@ fn exact_value_index_roundtrips( let vtable = ExactValueIndex::new_ref(); let kind = vtable .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "new_ref makes an ExactValueIndex"))?; + .ok_or_else(|| vortex_err!("new_ref makes an ExactValueIndex"))?; let mut ctx = new_session().create_execution_ctx(); check_roundtrip( kind, @@ -594,7 +594,7 @@ fn fixed_superset_index_roundtrips() -> VortexResult<()> { let vtable = FixedSupersetIndex::new_ref("test.idx.fixed", RoaringBitmap::new()); let kind = vtable .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "new_ref makes a FixedSupersetIndex"))?; + .ok_or_else(|| vortex_err!("new_ref makes a FixedSupersetIndex"))?; let mut ctx = new_session().create_execution_ctx(); check_roundtrip( kind, @@ -648,7 +648,7 @@ fn partitioning(layout: &LayoutRef) -> VortexResult { layout.as_::().indexes()[0] .partitioning() .cloned() - .ok_or_else(|| vortex_err!(AssertionFailed: "index should be partitioned")) + .ok_or_else(|| vortex_err!("index should be partitioned")) } /// Partitioning changes how the index is built and probed, never what it answers: every value @@ -673,7 +673,7 @@ async fn partitioned_index_answers_like_an_unpartitioned_one( // One data chunk, several index partitions: the two widths really are independent. let data = layout .slot(0)? - .ok_or_else(|| vortex_err!(AssertionFailed: "indexed layout has a data child"))?; + .ok_or_else(|| vortex_err!("indexed layout has a data child"))?; assert!(data.as_opt::().is_some()); assert_eq!( partitioning(&layout)?.index_ends().len() as u64, @@ -740,7 +740,7 @@ impl CountingFixture { let index = layout .slot(1)? - .ok_or_else(|| vortex_err!(AssertionFailed: "an index was configured"))?; + .ok_or_else(|| vortex_err!("an index was configured"))?; // Each partition is its own index-child chunk, so chunk `p` holds partition `p`. assert_eq!(index.nslots(), 3); let partitions = (0..index.nslots()) @@ -748,7 +748,7 @@ impl CountingFixture { segment_ids( &index .slot(p)? - .ok_or_else(|| vortex_err!(AssertionFailed: "partition {p} has a chunk"))?, + .ok_or_else(|| vortex_err!("partition {p} has a chunk"))?, ) }) .collect::>()?; @@ -857,8 +857,7 @@ async fn probing_loads_only_the_index_chunks_its_filter_cannot_prune() -> Vortex ChunkedLayoutStrategy::new(FlatLayoutStrategy::default()), FlatLayoutStrategy::default(), ZonedLayoutOptions { - block_size: NonZeroUsize::new(2) - .ok_or_else(|| vortex_err!(AssertionFailed: "non-zero"))?, + block_size: NonZeroUsize::new(2).ok_or_else(|| vortex_err!("non-zero"))?, ..Default::default() }, ), @@ -886,10 +885,10 @@ async fn probing_loads_only_the_index_chunks_its_filter_cannot_prune() -> Vortex let index = layout .slot(1)? - .ok_or_else(|| vortex_err!(AssertionFailed: "an index was configured"))?; + .ok_or_else(|| vortex_err!("an index was configured"))?; let chunks = index .slot(0)? - .ok_or_else(|| vortex_err!(AssertionFailed: "the zoned index child has data"))?; + .ok_or_else(|| vortex_err!("the zoned index child has data"))?; let chunk_count = usize::try_from(INDEX_ROWS)? / 2; assert_eq!(chunks.nslots(), chunk_count); let chunk_segments = (0..chunk_count) @@ -897,7 +896,7 @@ async fn probing_loads_only_the_index_chunks_its_filter_cannot_prune() -> Vortex segment_ids( &chunks .slot(chunk)? - .ok_or_else(|| vortex_err!(AssertionFailed: "chunk {chunk} exists"))?, + .ok_or_else(|| vortex_err!("chunk {chunk} exists"))?, ) }) .collect::>>()?; @@ -972,13 +971,13 @@ async fn probing_skips_partitions_the_selection_rules_out( let (send, recv) = oneshot::channel(); let pending = MaskFuture::new(ROWS.len(), async move { recv.await - .map_err(|_| vortex_err!(AssertionFailed: "selection sender dropped")) + .map_err(|_| vortex_err!("selection sender dropped")) }); let evaluated = reader.filter_evaluation(&all, &filter, pending)?; // Nothing can be skipped before the selection is known, so nothing is probed yet. assert!(fixture.index_requested().is_empty()); send.send(selection.clone()) - .map_err(|_| vortex_err!(AssertionFailed: "filter dropped the selection"))?; + .map_err(|_| vortex_err!("filter dropped the selection"))?; evaluated.await? } }; @@ -1240,7 +1239,7 @@ mod exact_value { let mut buffer = Vec::with_capacity(bitmap.serialized_size()); bitmap .serialize_into(&mut buffer) - .map_err(|err| vortex_err!(Serde: "Failed to serialize postings: {err}"))?; + .map_err(|err| vortex_err!("Failed to serialize postings: {err}"))?; lists.push(buffer); } @@ -1281,9 +1280,8 @@ mod exact_value { .keys .push(String::from_utf8_lossy(keys.bytes_at(idx).as_slice()).into_owned()); decoded.postings.push( - RoaringBitmap::deserialize_from(lists.bytes_at(idx).as_slice()).map_err( - |err| vortex_err!(Serde: "Failed to deserialize postings: {err}"), - )?, + RoaringBitmap::deserialize_from(lists.bytes_at(idx).as_slice()) + .map_err(|err| vortex_err!("Failed to deserialize postings: {err}"))?, ); } Ok(decoded) @@ -1421,7 +1419,7 @@ mod exact_value { _options: &(), _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!(AssertionFailed: "a declining index never builds content to encode") + vortex_bail!("a declining index never builds content to encode") } fn decode( diff --git a/vortex-layout/src/layouts/indexed/writer.rs b/vortex-layout/src/layouts/indexed/writer.rs index 066c1f112f3..67769334f96 100644 --- a/vortex-layout/src/layouts/indexed/writer.rs +++ b/vortex-layout/src/layouts/indexed/writer.rs @@ -182,7 +182,7 @@ impl PartitionBuilder for TypedPartitionBuilder { let array = vtable.encode(chunk, &options, &mut ctx)?; vortex_ensure!( array.dtype() == &index_dtype, - MismatchedTypes: "Index {} encoded a chunk of dtype {}, but the index kind declared {index_dtype}", + "Index {} encoded a chunk of dtype {}, but the index kind declared {index_dtype}", vtable.id(), array.dtype() ); @@ -392,7 +392,7 @@ impl IndexContent { // One spec records one options blob, so partitions may not disagree about it. Some(first) => vortex_ensure!( *first == partition_options, - InvalidArgument: "Index {id} partition {partition} finished with different options than earlier partitions" + "Index {id} partition {partition} finished with different options than earlier partitions" ), } built.push((partition, content)); @@ -460,14 +460,14 @@ impl LayoutStrategy for IndexedStrategy { }; let Some(block_len) = self.data_block_len.filter(|len| *len > 0) else { vortex_bail!( - InvalidArgument: "Index {} is partitioned every {partition_len} rows, which requires a non-zero \ + "Index {} is partitioned every {partition_len} rows, which requires a non-zero \ data block length (IndexedStrategy::with_data_block_len)", config.vtable.id() ); }; vortex_ensure!( partition_len.get() % block_len == 0, - InvalidArgument: "Index {} partition length {partition_len} must be a multiple of the data block \ + "Index {} partition length {partition_len} must be a multiple of the data block \ length {block_len}", config.vtable.id() ); diff --git a/vortex-layout/src/layouts/list/mod.rs b/vortex-layout/src/layouts/list/mod.rs index 75b793f5eb8..f5c8c618b15 100644 --- a/vortex-layout/src/layouts/list/mod.rs +++ b/vortex-layout/src/layouts/list/mod.rs @@ -79,16 +79,17 @@ impl VTable for List { metadata: &ListLayoutMetadata, ) -> VortexResult { ListLayout::validate_children(args.dtype, args.children.nchildren())?; - let elements_dtype = args.dtype.as_list_element_opt().ok_or_else( - || vortex_err!(InvalidArgument: "ListLayout requires a List dtype, got {}", args.dtype), - )?; + let elements_dtype = args + .dtype + .as_list_element_opt() + .ok_or_else(|| vortex_err!("ListLayout requires a List dtype, got {}", args.dtype))?; args.children.child(ELEMENTS_CHILD_INDEX, elements_dtype)?; let offsets_dtype = DType::Primitive(metadata.offsets_ptype(), Nullability::NonNullable); let offsets = args.children.child(OFFSETS_CHILD_INDEX, &offsets_dtype)?; vortex_ensure_eq!( offsets.row_count().saturating_sub(1), args.row_count, - InvalidArgument: "List offsets row count does not match parent" + "List offsets row count does not match parent" ); if args.dtype.is_nullable() { let validity = args @@ -97,7 +98,7 @@ impl VTable for List { vortex_ensure_eq!( validity.row_count(), args.row_count, - InvalidArgument: "List validity row count does not match parent" + "List validity row count does not match parent" ); } Ok(ListData { @@ -124,7 +125,7 @@ impl VTable for List { .dtype() .as_list_element_opt() .map(|dtype| dtype.as_ref().clone()) - .ok_or_else(|| vortex_err!(InvalidArgument: "ListLayout requires a List dtype")), + .ok_or_else(|| vortex_err!("ListLayout requires a List dtype")), OFFSETS_CHILD_INDEX => Ok(DType::Primitive( layout.offsets_ptype, Nullability::NonNullable, @@ -132,7 +133,7 @@ impl VTable for List { VALIDITY_CHILD_INDEX if layout.dtype().is_nullable() => { Ok(DType::Bool(Nullability::NonNullable)) } - _ => vortex_bail!(OutOfBounds: "Invalid child index {idx} for ListLayout"), + _ => vortex_bail!("Invalid child index {idx} for ListLayout"), } } @@ -143,7 +144,7 @@ impl VTable for List { VALIDITY_CHILD_INDEX if layout.dtype().is_nullable() => { LayoutChildType::Auxiliary("validity".into()) } - _ => vortex_panic!(OutOfBounds: "Invalid child index {idx} for ListLayout"), + _ => vortex_panic!("Invalid child index {idx} for ListLayout"), } } @@ -191,13 +192,13 @@ impl Layout { /// Returns the elements child. pub fn elements(&self) -> VortexResult { self.slot(ELEMENTS_CHILD_INDEX)? - .ok_or_else(|| vortex_err!(AssertionFailed: "ListLayout elements slot is absent")) + .ok_or_else(|| vortex_err!("ListLayout elements slot is absent")) } /// Returns the offsets child. pub fn offsets(&self) -> VortexResult { self.slot(OFFSETS_CHILD_INDEX)? - .ok_or_else(|| vortex_err!(AssertionFailed: "ListLayout offsets slot is absent")) + .ok_or_else(|| vortex_err!("ListLayout offsets slot is absent")) } /// Returns the optional validity child. diff --git a/vortex-layout/src/layouts/list/writer.rs b/vortex-layout/src/layouts/list/writer.rs index c5dbab7a3e9..8e3a25cf407 100644 --- a/vortex-layout/src/layouts/list/writer.rs +++ b/vortex-layout/src/layouts/list/writer.rs @@ -267,7 +267,7 @@ async fn transpose_list_column( .is_err() || offsets_tx.send(Ok((sp.advance(), offsets))).await.is_err() { - vortex_bail!(Io: "list child writer finished before all chunks were sent"); + vortex_bail!("list child writer finished before all chunks were sent"); } if let Some(validity_tx) = &validity_tx { let validity = validity @@ -278,7 +278,7 @@ async fn transpose_list_column( .await .is_err() { - vortex_bail!(Io: "list validity writer finished before all chunks were sent"); + vortex_bail!("list validity writer finished before all chunks were sent"); } } } diff --git a/vortex-layout/src/layouts/repartition.rs b/vortex-layout/src/layouts/repartition.rs index 03865377c53..b213ddd7749 100644 --- a/vortex-layout/src/layouts/repartition.rs +++ b/vortex-layout/src/layouts/repartition.rs @@ -280,7 +280,7 @@ fn exact_size(chunk: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult { return Ok(chunk.nbytes()); } let size = uncompressed_size_in_bytes(chunk, UncompressedSizeOpts::exact(), ctx)?; - u64::try_from(size).map_err(|e| vortex_err!(Overflow: "block size does not fit in u64: {e}")) + u64::try_from(size).map_err(|e| vortex_err!("block size does not fit in u64: {e}")) } #[cfg(test)] diff --git a/vortex-layout/src/layouts/row_idx/expr.rs b/vortex-layout/src/layouts/row_idx/expr.rs index 4b10fbe1387..659eb1f69d7 100644 --- a/vortex-layout/src/layouts/row_idx/expr.rs +++ b/vortex-layout/src/layouts/row_idx/expr.rs @@ -59,7 +59,7 @@ impl ScalarFnVTable for RowIdx { _ctx: &mut vortex_array::ExecutionCtx, ) -> VortexResult { vortex_bail!( - AssertionFailed: "RowIdxExpr should not be executed directly, use it in the context of a Vortex scan and it will be substituted for a row index array" + "RowIdxExpr should not be executed directly, use it in the context of a Vortex scan and it will be substituted for a row index array" ); } diff --git a/vortex-layout/src/layouts/struct_/mod.rs b/vortex-layout/src/layouts/struct_/mod.rs index a973943e2ba..4506a0b6e20 100644 --- a/vortex-layout/src/layouts/struct_/mod.rs +++ b/vortex-layout/src/layouts/struct_/mod.rs @@ -70,7 +70,7 @@ impl VTable for Struct { vortex_ensure_eq!( child_row_count, args.row_count, - InvalidArgument: "Struct child {idx} row count does not match parent" + "Struct child {idx} row count does not match parent" ); } Ok(()) @@ -164,12 +164,12 @@ impl Layout { continue; }; let Field::Name(field_name) = field else { - vortex_bail!(MismatchedTypes: "Expected field name, got {field:?}"); + vortex_bail!("Expected field name, got {field:?}"); }; let idx = self .struct_fields() .find(field_name) - .ok_or_else(|| vortex_err!(NotFound: "Field not found: {field_name}"))?; + .ok_or_else(|| vortex_err!("Field not found: {field_name}"))?; per_child(path.clone().step_into()?, idx)?; } Ok(()) @@ -178,9 +178,9 @@ impl Layout { fn validate_children(dtype: &DType, nchildren: usize) -> VortexResult<()> { let fields = dtype .as_struct_fields_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "Expected struct dtype"))?; + .ok_or_else(|| vortex_err!("Expected struct dtype"))?; let expected = fields.nfields() + usize::from(dtype.is_nullable()); - vortex_ensure_eq!(nchildren, expected, InvalidArgument); + vortex_ensure_eq!(nchildren, expected); Ok(()) } @@ -193,7 +193,7 @@ impl Layout { dtype .as_struct_fields_opt() .and_then(|fields| fields.field_by_index(slot - 1)) - .ok_or_else(|| vortex_err!(NotFound: "Missing field {}", slot - 1)) + .ok_or_else(|| vortex_err!("Missing field {}", slot - 1)) } } } diff --git a/vortex-layout/src/layouts/struct_/reader.rs b/vortex-layout/src/layouts/struct_/reader.rs index d595bdd5c52..9d9630473c8 100644 --- a/vortex-layout/src/layouts/struct_/reader.rs +++ b/vortex-layout/src/layouts/struct_/reader.rs @@ -165,9 +165,9 @@ impl StructReader { fn field_reader(&self, item: &Item) -> VortexResult<&LayoutReaderRef> { let name = match item { Item::Validity => { - return self.validity()?.ok_or_else( - || vortex_err!(AssertionFailed: "Non-nullable struct layout has no validity"), - ); + return self + .validity()? + .ok_or_else(|| vortex_err!("Non-nullable struct layout has no validity")); } Item::Field(name) => name, }; @@ -176,7 +176,7 @@ impl StructReader { .as_ref() .and_then(|lookup| lookup.get(name).copied()) .or_else(|| self.struct_fields().find(name)) - .ok_or_else(|| vortex_err!(NotFound: "Field {} not found in struct layout", name))?; + .ok_or_else(|| vortex_err!("Field {} not found in struct layout", name))?; self.field_reader_by_index(idx) } @@ -284,7 +284,7 @@ impl StructReader { let field_index = |name: &FieldName| { fields .find(name) - .ok_or_else(|| vortex_err!(NotFound: "Field {name} not found in struct layout")) + .ok_or_else(|| vortex_err!("Field {name} not found in struct layout")) }; let (names, indices) = if expr.is_root() { @@ -320,7 +320,7 @@ impl StructReader { .map(|idx: usize| -> VortexResult<_> { let dtype = fields .field_by_index(idx) - .ok_or_else(|| vortex_err!(OutOfBounds: "Field index {idx} out of bounds"))?; + .ok_or_else(|| vortex_err!("Field index {idx} out of bounds"))?; Ok((idx, BoundExpression::new_root(dtype))) }) .try_collect()?; @@ -426,7 +426,7 @@ fn expand_struct_root( if let Some(field_name) = scalar_fn.as_opt::() { let idx = fields.find(field_name).ok_or_else(|| { - vortex_err!(NotFound: "Field {field_name} not found while expanding struct root") + vortex_err!("Field {field_name} not found while expanding struct root") })?; let child = packed.children()[idx].clone(); return Ok(Transformed { @@ -650,7 +650,7 @@ impl LayoutReader for StructReader { ), Partitioned::Direct(_) => { vortex_bail!( - NotImplemented: "Cannot evaluate struct projection {expr} as a filter over {}", + "Cannot evaluate struct projection {expr} as a filter over {}", self.name ) } diff --git a/vortex-layout/src/layouts/struct_/writer.rs b/vortex-layout/src/layouts/struct_/writer.rs index 69f9792e826..0e9960a7c74 100644 --- a/vortex-layout/src/layouts/struct_/writer.rs +++ b/vortex-layout/src/layouts/struct_/writer.rs @@ -114,14 +114,14 @@ impl LayoutStrategy for StructStrategy { let dtype = stream.dtype().clone(); let Some(struct_dtype) = dtype.as_struct_fields_opt() else { - vortex_bail!(MismatchedTypes: "StructStrategy can only write struct-typed streams, got {dtype}"); + vortex_bail!("StructStrategy can only write struct-typed streams, got {dtype}"); }; // Check for unique field names at write time. if HashSet::<_, DefaultHashBuilder>::from_iter(struct_dtype.names().iter()).len() != struct_dtype.names().len() { - vortex_bail!(InvalidArgument: "StructLayout must have unique field names"); + vortex_bail!("StructLayout must have unique field names"); } let is_nullable = dtype.is_nullable(); @@ -183,7 +183,7 @@ impl LayoutStrategy for StructStrategy { for (tx, column) in column_streams_tx.iter().zip_eq(columns) { if tx.send(Ok(column)).await.is_err() { vortex_bail!( - Io: "struct column writer finished before all chunks were sent" + "struct column writer finished before all chunks were sent" ); } } diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs index 3a5e6dfbddc..3401e359103 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/bool.rs @@ -98,9 +98,7 @@ mod tests { .iter() .copied() .collect::>>() - .ok_or_else( - || vortex_err!(AssertionFailed: "non-null test case contains a null"), - )?, + .ok_or_else(|| vortex_err!("non-null test case contains a null"))?, ), Nullability::Nullable => BoolArray::from_iter(values.iter().copied()), }; diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs index 2a703ac5b5b..cdc900bd339 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/canonical/mod.rs @@ -43,7 +43,7 @@ pub(super) fn accumulate_canonical( | Canonical::Union(_) | Canonical::Map(_) => { vortex_bail!( - InvalidArgument: "Unsupported canonical type for bloom filter: {}", + "Unsupported canonical type for bloom filter: {}", canonical.dtype() ) } diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs index 8d994ef4f80..a13118c5729 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/mod.rs @@ -99,20 +99,19 @@ impl BloomOptions { vortex_ensure_eq!( bytes.len(), OPTIONS_BYTES_LEN, - Serde: "invalid bloom metadata length" + "invalid bloom metadata length" ); // Both options are u32 let (chunks, remainder) = bytes.as_chunks::<4>(); - vortex_ensure_eq!(remainder.len(), 0, Serde: "expected no trailing metadata bytes"); + vortex_ensure_eq!(remainder.len(), 0, "expected no trailing metadata bytes"); let blocks_count = u32::from_le_bytes(chunks[0]); let hash_fn = HashFn::try_from(u32::from_le_bytes(chunks[1]))?; Ok(Self { - blocks_count: NonZeroU32::new(blocks_count).ok_or_else( - || vortex_err!(InvalidArgument: "bloom blocks length must be non-zero"), - )?, + blocks_count: NonZeroU32::new(blocks_count) + .ok_or_else(|| vortex_err!("bloom blocks length must be non-zero"))?, hash_fn, }) } @@ -321,16 +320,12 @@ impl AggregateFnVTable for BloomFilter { let bytes = scalar .as_binary() .value() - .ok_or_else(|| vortex_err!(AssertionFailed: "non-null bloom partial has no bytes"))?; + .ok_or_else(|| vortex_err!("non-null bloom partial has no bytes"))?; let partial = BloomPartial::deserialize(bytes.clone())?; // `deserialize` validates the byte length, but it cannot know the options the filter was // built with, so compare the block count here. - vortex_ensure_eq!( - partial.len(), - args.options.blocks_count().get() as usize, - InvalidArgument - ); + vortex_ensure_eq!(partial.len(), args.options.blocks_count().get() as usize); Ok(partial) } @@ -454,7 +449,7 @@ pub(in crate::layouts::zoned::aggregates::bloom_filter) mod test_utils { let bytes = state .as_binary() .value() - .ok_or_else(|| vortex_err!(InvalidArgument: "bloom state must be non-null"))?; + .ok_or_else(|| vortex_err!("bloom state must be non-null"))?; let bloom_filter = BloomPartial::deserialize(bytes.clone())?; diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs index 550712f9f07..61457a3a6d8 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/aggregate.rs @@ -37,7 +37,7 @@ impl BloomPartial { vortex_ensure_eq!( self.len(), other.len(), - InvalidArgument: "bloom partial block count mismatch" + "bloom partial block count mismatch" ); // One flat `u32` slice each: the compiler turns the flat OR into wide loads and stores, diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs index b4ea657d629..db7da6f700e 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/mod.rs @@ -77,7 +77,7 @@ impl TryFrom for HashFn { fn try_from(value: u32) -> Result { match value { 0 => Ok(Self::XxHash3_64), - _ => Err(vortex_err!(NotFound: "unknown bloom hash function ID: {value}")), + _ => Err(vortex_err!("unknown bloom hash function ID: {value}")), } } } diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs index b9fe5343091..509a735fc94 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/scalar.rs @@ -69,7 +69,7 @@ impl BloomPartial { } other => { return Err(vortex_err!( - InvalidArgument: "Unsupported scalar type for bloom filter: {other}" + "Unsupported scalar type for bloom filter: {other}" )); } }) diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs index 16fbee72242..6d7400ccbc3 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/partial/serde.rs @@ -30,12 +30,12 @@ impl BloomPartial { pub(in crate::layouts::zoned) fn deserialize(bytes: ByteBuffer) -> VortexResult { vortex_ensure!( !bytes.is_empty() && bytes.len().is_multiple_of(BLOCK_SIZE), - Serde: "invalid bloom filter byte length: {}", + "invalid bloom filter byte length: {}", bytes.len() ); vortex_ensure!( u32::try_from(bytes.len() / BLOCK_SIZE).is_ok(), - Serde: "bloom blocks length must be non-zero and lower than u32::MAX", + "bloom blocks length must be non-zero and lower than u32::MAX", ); let blocks = Buffer::::from_byte_buffer(bytes.aligned(Alignment::of::())); diff --git a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs index 552fe0ecfb7..fc8f91627cb 100644 --- a/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs +++ b/vortex-layout/src/layouts/zoned/aggregates/bloom_filter/scalar_fn.rs @@ -88,12 +88,12 @@ impl ScalarFnVTable for BloomContains { fn return_dtype(&self, _options: &Self::Options, args: &[DType]) -> VortexResult { vortex_ensure!( matches!(args[0], DType::Binary(_)), - MismatchedTypes: "bloom filter must be Binary" + "bloom filter must be Binary" ); vortex_ensure!( is_bloom_valid_dtype(&args[1]), - MismatchedTypes: "bloom filter needle value type is unsupported" + "bloom filter needle value type is unsupported" ); Ok(DType::Bool(args[0].nullability() | args[1].nullability())) @@ -114,9 +114,9 @@ impl ScalarFnVTable for BloomContains { // For now, a bloom filter can execute only when the needle is a literal, // so anything other than a constant here is unexpected. let needle_array = args.get(1)?; - let needle = needle_array.as_constant().ok_or_else( - || vortex_err!(InvalidArgument: "bloom filter needle must be a constant"), - )?; + let needle = needle_array + .as_constant() + .ok_or_else(|| vortex_err!("bloom filter needle must be a constant"))?; // The bloom filter doesn't consider nulls as values // whose presence it should detect. During writes, the filter @@ -180,8 +180,7 @@ impl ScalarFnVTable for BloomContains { // Bloom filter length is never larger than a `u32`. This is intentional // and a property of the implementation. u32::try_from(partial.len()).vortex_expect("valid u32 size"), - options.blocks_count().get(), - InvalidArgument + options.blocks_count().get() ); partial.contains_scalar(&needle) }; @@ -361,9 +360,9 @@ mod tests { )?; let dtype = DType::Primitive(PType::I64, Nullability::NonNullable); - let proof = eq(root(dtype), lit(42i64)).falsify(&session)?.ok_or_else( - || vortex_error::vortex_err!(AssertionFailed: "equality should have a bloom falsifier"), - )?; + let proof = eq(root(dtype), lit(42i64)) + .falsify(&session)? + .ok_or_else(|| vortex_error::vortex_err!("equality should have a bloom falsifier"))?; let mut ctx = session.create_execution_ctx(); assert_arrays_eq!( @@ -399,7 +398,7 @@ mod tests { let dtype = DType::Primitive(PType::I64, Nullability::NonNullable); let proof = eq(root(dtype.clone()), lit(42i64)) .falsify(&session)? - .ok_or_else(|| vortex_error::vortex_err!(AssertionFailed: "equality should have a bloom falsifier"))?; + .ok_or_else(|| vortex_error::vortex_err!("equality should have a bloom falsifier"))?; let zone_map = ZoneMap::try_new( dtype, diff --git a/vortex-layout/src/layouts/zoned/builder.rs b/vortex-layout/src/layouts/zoned/builder.rs index e94e2107e6c..97290ad731d 100644 --- a/vortex-layout/src/layouts/zoned/builder.rs +++ b/vortex-layout/src/layouts/zoned/builder.rs @@ -60,7 +60,7 @@ impl AggregateStatsAccumulator { vortex_ensure_eq!( partials.len(), self.builders.len(), - AssertionFailed: "aggregate partial count must match zone stats builder count" + "aggregate partial count must match zone stats builder count" ); for (builder, value) in self.builders.iter_mut().zip_eq(partials) { diff --git a/vortex-layout/src/layouts/zoned/mod.rs b/vortex-layout/src/layouts/zoned/mod.rs index a8a0eed1653..ff6aaba350b 100644 --- a/vortex-layout/src/layouts/zoned/mod.rs +++ b/vortex-layout/src/layouts/zoned/mod.rs @@ -107,7 +107,7 @@ impl VTable for Zoned { ) } ZoneMapSchema::LegacyStats(_) => { - vortex_panic!(NotImplemented: "Cannot serialize legacy stats schema as vortex.zoned") + vortex_panic!("Cannot serialize legacy stats schema as vortex.zoned") } }, } @@ -121,7 +121,7 @@ impl VTable for Zoned { vortex_ensure_eq!( args.children.nchildren(), 2, - InvalidArgument: "ZonedLayout expects exactly 2 children (data, zones)" + "ZonedLayout expects exactly 2 children (data, zones)" ); vortex_ensure_eq!(args.children.child_row_count(0), args.row_count); let Some(aggregate_fns) = @@ -149,7 +149,7 @@ impl VTable for Zoned { match idx { 0 => Ok(layout.dtype().clone()), 1 => Ok(layout.stats_table_dtype.clone()), - _ => vortex_bail!(OutOfBounds: "Invalid child index: {idx}"), + _ => vortex_bail!("Invalid child index: {idx}"), } } @@ -157,7 +157,7 @@ impl VTable for Zoned { match idx { 0 => LayoutChildType::Transparent("data".into()), 1 => LayoutChildType::Auxiliary("zones".into()), - _ => vortex_panic!(OutOfBounds: "Invalid child index: {}", idx), + _ => vortex_panic!("Invalid child index: {}", idx), } } @@ -196,7 +196,7 @@ impl VTable for LegacyStats { vortex_ensure_eq!( args.children.nchildren(), 2, - InvalidArgument: "LegacyStatsLayout expects exactly 2 children (data, zones)" + "LegacyStatsLayout expects exactly 2 children (data, zones)" ); let stats_table_dtype = match &metadata.zone_map_schema { ZoneMapSchema::LegacyStats(stats) => legacy_stats_table_dtype(args.dtype, stats), @@ -217,7 +217,7 @@ impl VTable for LegacyStats { match idx { 0 => Ok(layout.dtype().clone()), 1 => Ok(layout.stats_table_dtype.clone()), - _ => vortex_bail!(OutOfBounds: "Invalid child index: {idx}"), + _ => vortex_bail!("Invalid child index: {idx}"), } } @@ -225,7 +225,7 @@ impl VTable for LegacyStats { match idx { 0 => LayoutChildType::Transparent("data".into()), 1 => LayoutChildType::Auxiliary("zones".into()), - _ => vortex_panic!(OutOfBounds: "Invalid child index: {idx}"), + _ => vortex_panic!("Invalid child index: {idx}"), } } @@ -293,7 +293,7 @@ impl ZonedLayout { ) -> VortexResult { let expected_dtype = aggregate_stats_table_dtype(data.dtype(), &aggregate_fns); if zones.dtype() != &expected_dtype { - vortex_bail!(MismatchedTypes: "Invalid zone map layout: zones dtype does not match expected dtype"); + vortex_bail!("Invalid zone map layout: zones dtype does not match expected dtype"); } // Verify that every aggregate is serializable. @@ -437,15 +437,15 @@ impl DeserializeMetadata for ZonedMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { let Some((&version, proto_bytes)) = metadata.split_first() else { - vortex_bail!(Serde: "Zoned metadata missing protobuf version"); + vortex_bail!("Zoned metadata missing protobuf version"); }; vortex_ensure_eq!( version, ZONED_METADATA_PROTO_VERSION, - Serde: "Unsupported zoned metadata version" + "Unsupported zoned metadata version" ); - vortex_ensure!(!proto_bytes.is_empty(), Serde: "Zoned metadata missing protobuf"); + vortex_ensure!(!proto_bytes.is_empty(), "Zoned metadata missing protobuf"); let proto = ZonedMetadataProto::decode(proto_bytes)?; Ok(Self { @@ -473,7 +473,7 @@ impl DeserializeMetadata for LegacyStatsMetadata { fn deserialize(metadata: &[u8]) -> VortexResult { vortex_ensure!( metadata.len() >= 4, - Serde: "Legacy zoned metadata must contain at least 4 bytes for zone length, got {}", + "Legacy zoned metadata must contain at least 4 bytes for zone length, got {}", metadata.len() ); @@ -499,7 +499,7 @@ impl SerializeMetadata for LegacyStatsMetadata { metadata } ZoneMapSchema::AggregateFns(_) => { - vortex_panic!(NotImplemented: "Cannot serialize aggregate specs as legacy stats metadata") + vortex_panic!("Cannot serialize aggregate specs as legacy stats metadata") } } } diff --git a/vortex-layout/src/layouts/zoned/reader.rs b/vortex-layout/src/layouts/zoned/reader.rs index b91ef0d7527..46f1d229c46 100644 --- a/vortex-layout/src/layouts/zoned/reader.rs +++ b/vortex-layout/src/layouts/zoned/reader.rs @@ -71,13 +71,13 @@ impl ZonedReader { // A zone count that disagrees with `row_count` / `zone_len` would index past the mask. vortex_ensure!( zone_len > 0, - InvalidArgument: "zoned layout reader requires a non-zero zone length" + "zoned layout reader requires a non-zero zone length" ); let expected_zones = row_count.div_ceil(zone_len as u64); vortex_ensure_eq!( zone_count as u64, expected_zones, - Serde: "zoned layout zone count must cover {row_count} rows of {zone_len}-row zones" + "zoned layout zone count must cover {row_count} rows of {zone_len}-row zones" ); Ok(Self { diff --git a/vortex-layout/src/layouts/zoned/schema.rs b/vortex-layout/src/layouts/zoned/schema.rs index 3b30ca6664c..0e4d9db318a 100644 --- a/vortex-layout/src/layouts/zoned/schema.rs +++ b/vortex-layout/src/layouts/zoned/schema.rs @@ -37,7 +37,7 @@ impl AggregateSpecProto { pub(crate) fn try_from_aggregate_fn(aggregate_fn: &AggregateFnRef) -> VortexResult { let options = aggregate_fn.options().serialize()?.ok_or_else(|| { vortex_err!( - Serde: "Aggregate function '{}' is not serializable", + "Aggregate function '{}' is not serializable", aggregate_fn.id() ) })?; @@ -62,13 +62,13 @@ impl AggregateSpecProto { return Ok(None); } - vortex_bail!(NotFound: "unknown aggregate function id: {}", self.id); + vortex_bail!("unknown aggregate function id: {}", self.id); }; let aggregate_fn = plugin.deserialize(&self.options, session)?; if aggregate_fn.id() != aggregate_fn_id { vortex_bail!( - MismatchedTypes: "Aggregate function ID mismatch: expected {}, got {}", + "Aggregate function ID mismatch: expected {}, got {}", aggregate_fn_id, aggregate_fn.id() ); diff --git a/vortex-layout/src/layouts/zoned/writer.rs b/vortex-layout/src/layouts/zoned/writer.rs index 2cb11860f46..6326f1b05eb 100644 --- a/vortex-layout/src/layouts/zoned/writer.rs +++ b/vortex-layout/src/layouts/zoned/writer.rs @@ -137,7 +137,7 @@ impl LayoutStrategy for ZonedStrategy { let aggregate_fns = stats_accumulator.lock().aggregate_fns(); for aggregate_fn in aggregate_fns.iter() { if !ctx.allows_aggregate(&aggregate_fn.id()) { - vortex_bail!(InvalidArgument: "Aggregate {} not permitted by ctx", aggregate_fn.id()); + vortex_bail!("Aggregate {} not permitted by ctx", aggregate_fn.id()); } } diff --git a/vortex-layout/src/layouts/zoned/zone_map.rs b/vortex-layout/src/layouts/zoned/zone_map.rs index 8279e9ff4ca..2b9011e330c 100644 --- a/vortex-layout/src/layouts/zoned/zone_map.rs +++ b/vortex-layout/src/layouts/zoned/zone_map.rs @@ -80,7 +80,7 @@ impl ZoneMap { ) -> VortexResult { let expected_dtype = aggregate_stats_table_dtype(&column_dtype, &aggregate_fns); if &expected_dtype != array.dtype() { - vortex_bail!(MismatchedTypes: "Array dtype does not match expected zone map dtype: {expected_dtype}"); + vortex_bail!("Array dtype does not match expected zone map dtype: {expected_dtype}"); } // SAFETY: We checked that the array matches the expected stats-table schema. @@ -121,7 +121,7 @@ impl ZoneMap { ) -> VortexResult { let expected_dtype = legacy_stats_table_dtype(&column_dtype, &stats); if &expected_dtype != array.dtype() { - vortex_bail!(MismatchedTypes: "Array dtype does not match expected zone map dtype: {expected_dtype}"); + vortex_bail!("Array dtype does not match expected zone map dtype: {expected_dtype}"); } // SAFETY: We checked that the array matches the expected legacy stats-table schema. @@ -228,7 +228,7 @@ impl StatBinder for ZoneMapStatsBinder<'_> { vortex_ensure_eq!( input.dtype(), &self.zone_map.column_dtype, - MismatchedTypes: "Stats predicate root dtype does not match zone-map column dtype" + "Stats predicate root dtype does not match zone-map column dtype" ); if let Some(stat_expr) = self.zone_map.aggregate_field_expr(aggregate_fn) { @@ -364,7 +364,7 @@ fn row_count_array(zone_len: u64, row_count: u64, num_zones: usize) -> VortexRes let leading_rows = zone_len.saturating_mul((num_zones as u64) - 1); let Some(last_zone_len) = row_count.checked_sub(leading_rows) else { vortex_bail!( - Serde: "Zone map declares {num_zones} zones of {zone_len} rows, which is more than the \ + "Zone map declares {num_zones} zones of {zone_len} rows, which is more than the \ {row_count} rows of the layout" ); }; diff --git a/vortex-layout/src/plan/physical/children.rs b/vortex-layout/src/plan/physical/children.rs index 72b7fc93bcf..bfa1541b87c 100644 --- a/vortex-layout/src/plan/physical/children.rs +++ b/vortex-layout/src/plan/physical/children.rs @@ -58,9 +58,10 @@ impl PlanChildren { return Ok(Some(child)); } - let initializer = self.initializer.as_ref().ok_or_else( - || vortex_err!(AssertionFailed: "Plan child {index} was not initialized"), - )?; + let initializer = self + .initializer + .as_ref() + .ok_or_else(|| vortex_err!("Plan child {index} was not initialized"))?; Ok(Some(cell.get_or_try_init(|| initializer(index))?)) } @@ -68,7 +69,7 @@ impl PlanChildren { pub fn iter(&self) -> impl ExactSizeIterator> + '_ { (0..self.len()).map(|index| { self.get(index)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Plan child {index} is absent")) + .ok_or_else(|| vortex_err!("Plan child {index} is absent")) }) } @@ -76,7 +77,7 @@ impl PlanChildren { pub(crate) fn iter_refs(&self) -> impl ExactSizeIterator> + '_ { (0..self.len()).map(|index| { self.get_ref(index)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Plan child {index} is absent")) + .ok_or_else(|| vortex_err!("Plan child {index} is absent")) }) } diff --git a/vortex-layout/src/plan/physical/lower.rs b/vortex-layout/src/plan/physical/lower.rs index 0340c3dc4dd..1ea284cc1ca 100644 --- a/vortex-layout/src/plan/physical/lower.rs +++ b/vortex-layout/src/plan/physical/lower.rs @@ -67,7 +67,7 @@ pub fn lower(layout: &LayoutRef) -> VortexResult { return lower_zoned(layout); } vortex_bail!( - NotImplemented: "No physical plan implementation for layout '{}'", + "No physical plan implementation for layout '{}'", layout.encoding_id() ) } @@ -89,7 +89,7 @@ fn lower_chunked(layout: &ChunkedLayout) -> VortexResult { row_offsets.push(row_count); row_count = row_count .checked_add(layout.child_row_count(index)) - .ok_or_else(|| vortex_err!(Overflow: "Chunked row count overflow"))?; + .ok_or_else(|| vortex_err!("Chunked row count overflow"))?; } // SAFETY: Chunked layout construction validates that every child has the parent dtype and // that their row counts sum to the parent; offsets were computed with checked addition above. @@ -158,10 +158,10 @@ fn lazy_children(layout: LayoutRef, slots: Vec) -> PlanChildren { let slot = slots .get(index) .copied() - .ok_or_else(|| vortex_err!(NotFound: "Missing plan child slot {index}"))?; + .ok_or_else(|| vortex_err!("Missing plan child slot {index}"))?; let child = layout .slot(slot)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Layout child slot {slot} is absent"))?; + .ok_or_else(|| vortex_err!("Layout child slot {slot} is absent"))?; lower(&child) }) } @@ -173,7 +173,7 @@ fn lower_zoned(layout: &LayoutRef) -> VortexResult { } else if let Some(layout) = layout.as_opt::() { layout.data() } else { - vortex_bail!(AssertionFailed: "Zoned plan requires a zoned layout") + vortex_bail!("Zoned plan requires a zoned layout") }; // Without zones, or with a zone table holding no statistics, nothing can be pruned. let no_stats = metadata @@ -183,7 +183,7 @@ fn lower_zoned(layout: &LayoutRef) -> VortexResult { if metadata.zone_len() == 0 || no_stats { let data = layout .slot(0)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Zoned layout has no data child"))?; + .ok_or_else(|| vortex_err!("Zoned layout has no data child"))?; return lower(&data); } let children = lazy_children(Arc::clone(layout), vec![0, 1]); diff --git a/vortex-layout/src/plan/physical/mod.rs b/vortex-layout/src/plan/physical/mod.rs index 051d8581598..bedd3a7cad8 100644 --- a/vortex-layout/src/plan/physical/mod.rs +++ b/vortex-layout/src/plan/physical/mod.rs @@ -83,7 +83,7 @@ pub(crate) fn check_child_count( ) -> VortexResult<()> { if children.len() != expected { vortex_bail!( - InvalidArgument: "{name} expects {expected} children but got {}", + "{name} expects {expected} children but got {}", children.len() ); } diff --git a/vortex-layout/src/plan/physical/operators/concat.rs b/vortex-layout/src/plan/physical/operators/concat.rs index 54aa61e8e7a..57110556280 100644 --- a/vortex-layout/src/plan/physical/operators/concat.rs +++ b/vortex-layout/src/plan/physical/operators/concat.rs @@ -48,9 +48,11 @@ impl Operator for ConcatSource { Ok(if self.current == self.inlets { Step::End } else { - Step::Final(cx.inlet(self.current).take().ok_or_else( - || vortex_err!(AssertionFailed: "Concat computed before its inlet was ready"), - )?) + Step::Final( + cx.inlet(self.current) + .take() + .ok_or_else(|| vortex_err!("Concat computed before its inlet was ready"))?, + ) }) } } diff --git a/vortex-layout/src/plan/physical/operators/filter.rs b/vortex-layout/src/plan/physical/operators/filter.rs index 4948f8dbf4c..ecd0943f97c 100644 --- a/vortex-layout/src/plan/physical/operators/filter.rs +++ b/vortex-layout/src/plan/physical/operators/filter.rs @@ -46,7 +46,7 @@ impl Operator for MaskStage { let end = self.cursor + batch.len(); vortex_ensure!( end <= self.mask.len(), - AssertionFailed: "Filter input is longer than its mask" + "Filter input is longer than its mask" ); let mask = self.mask.slice(self.cursor..end); self.cursor = end; diff --git a/vortex-layout/src/plan/physical/operators/mod.rs b/vortex-layout/src/plan/physical/operators/mod.rs index 9488719d1b5..b0f5937d71d 100644 --- a/vortex-layout/src/plan/physical/operators/mod.rs +++ b/vortex-layout/src/plan/physical/operators/mod.rs @@ -44,9 +44,9 @@ fn take_rows(inlet: &mut Inlet<'_>, len: usize) -> VortexResult { let mut pieces: SmallVec<[ArrayRef; 2]> = SmallVec::new(); let mut left = len; while left > 0 { - let front = inlet.peek_mut().ok_or_else( - || vortex_err!(AssertionFailed: "Taking {len} rows from an inlet holding fewer"), - )?; + let front = inlet + .peek_mut() + .ok_or_else(|| vortex_err!("Taking {len} rows from an inlet holding fewer"))?; if front.len() <= left { left -= front.len(); pieces.extend(inlet.take()); diff --git a/vortex-layout/src/plan/physical/operators/pack.rs b/vortex-layout/src/plan/physical/operators/pack.rs index 5a66330cce0..4fefa368f05 100644 --- a/vortex-layout/src/plan/physical/operators/pack.rs +++ b/vortex-layout/src/plan/physical/operators/pack.rs @@ -78,7 +78,7 @@ impl Source for PackSource { let available = self.states.len() - self.waiting.indices().len() - self.ended; vortex_ensure!( self.ended == 0 || available == 0, - AssertionFailed: "Pack fields ended at different rows" + "Pack fields ended at different rows" ); Ok(match self.waiting.indices().last() { Some(&index) => SourceReady::Blocked(SourceBlocked::Inlet(index)), @@ -97,9 +97,9 @@ impl Operator for PackSource { let mut len = usize::MAX; for index in 0..self.states.len() { let mut inlet = cx.inlet(index); - let front = inlet.peek_mut().ok_or_else( - || vortex_err!(AssertionFailed: "Pack computed before every inlet was ready"), - )?; + let front = inlet + .peek_mut() + .ok_or_else(|| vortex_err!("Pack computed before every inlet was ready"))?; len = len.min(front.len()); } let mut arrays = Vec::with_capacity(self.states.len()); @@ -109,9 +109,11 @@ impl Operator for PackSource { self.observe(index, &inlet); } let validity = if self.nullable { - Validity::Array(arrays.pop().ok_or_else( - || vortex_err!(AssertionFailed: "Nullable Pack is missing its validity"), - )?) + Validity::Array( + arrays + .pop() + .ok_or_else(|| vortex_err!("Nullable Pack is missing its validity"))?, + ) } else { Validity::NonNullable }; diff --git a/vortex-layout/src/plan/physical/operators/scan.rs b/vortex-layout/src/plan/physical/operators/scan.rs index 0a0f6e7effe..842bd33ee87 100644 --- a/vortex-layout/src/plan/physical/operators/scan.rs +++ b/vortex-layout/src/plan/physical/operators/scan.rs @@ -105,7 +105,7 @@ impl Operator for ScanSource { } let (_, bytes) = cx .take_segment() - .ok_or_else(|| vortex_err!(AssertionFailed: "Segment scan ran without its bytes"))?; + .ok_or_else(|| vortex_err!("Segment scan ran without its bytes"))?; self.done = true; let array = decode(&self.plan, bytes, cx.session())?; Ok(Step::Final(select( diff --git a/vortex-layout/src/plan/physical/optimizer/rules.rs b/vortex-layout/src/plan/physical/optimizer/rules.rs index f31f4503d8b..1c32e9c6f60 100644 --- a/vortex-layout/src/plan/physical/optimizer/rules.rs +++ b/vortex-layout/src/plan/physical/optimizer/rules.rs @@ -106,12 +106,12 @@ impl PlanRuleSet { vortex_ensure_eq!( reduced.row_count(), plan.row_count(), - AssertionFailed: "Plan rewrite from {rule:?} changed row count" + "Plan rewrite from {rule:?} changed row count" ); vortex_ensure_eq!( reduced.dtype(), plan.dtype(), - AssertionFailed: "Plan rewrite from {rule:?} changed dtype" + "Plan rewrite from {rule:?} changed dtype" ); } @@ -239,12 +239,12 @@ impl PlanParentRuleSet { vortex_ensure_eq!( reduced.row_count(), parent.row_count(), - AssertionFailed: "Plan rewrite from {rule:?} changed row count" + "Plan rewrite from {rule:?} changed row count" ); vortex_ensure_eq!( reduced.dtype(), parent.dtype(), - AssertionFailed: "Plan rewrite from {rule:?} changed dtype" + "Plan rewrite from {rule:?} changed dtype" ); } diff --git a/vortex-layout/src/plan/physical/pipeline/scan.rs b/vortex-layout/src/plan/physical/pipeline/scan.rs index 6f757e89c6f..816c3566d7e 100644 --- a/vortex-layout/src/plan/physical/pipeline/scan.rs +++ b/vortex-layout/src/plan/physical/pipeline/scan.rs @@ -191,7 +191,7 @@ fn drive( cx.changed.clear(); vortex_ensure!( cx.reads.is_empty() || ready == SourceReady::Blocked(SourceBlocked::Io), - AssertionFailed: "A source that queues reads must block on IO" + "A source that queues reads must block on IO" ); match ready { SourceReady::Ready => {} @@ -395,7 +395,7 @@ impl Core { fn run(&mut self, id: PipelineId) -> VortexResult<()> { let pipe = self.pipelines[id] .as_mut() - .ok_or_else(|| vortex_err!(AssertionFailed: "Pipeline {id} is not live"))?; + .ok_or_else(|| vortex_err!("Pipeline {id} is not live"))?; pipe.queued = false; let mut reads = SmallVec::new(); let progress = drive( @@ -526,7 +526,7 @@ impl Core { let (owner, segment) = self .reads .remove(&read) - .ok_or_else(|| vortex_err!(AssertionFailed: "Unknown read {read:?}"))?; + .ok_or_else(|| vortex_err!("Unknown read {read:?}"))?; if let Some(id) = owner { let pipe = self.pipeline_mut(id); pipe.pending -= 1; @@ -629,7 +629,7 @@ impl Scan { split.rows.start <= split.rows.end && split.rows.end <= plan.row_count() && split.mask.len() as u64 == split.rows.end - split.rows.start, - InvalidArgument: "Split {:?} with a mask of {} rows does not fit a plan of {} rows", + "Split {:?} with a mask of {} rows does not fit a plan of {} rows", split.rows, split.mask.len(), plan.row_count() @@ -716,7 +716,7 @@ impl Scan { return Ok(Turn::Waiting); } vortex_bail!( - AssertionFailed: "Scan is stuck with nothing runnable and no read in flight: {}", + "Scan is stuck with nothing runnable and no read in flight: {}", self.core.describe_blocked() ); } @@ -733,19 +733,20 @@ impl Scan { .active .iter() .position(Option::is_none) - .ok_or_else(|| vortex_err!(AssertionFailed: "No free split slot"))?; + .ok_or_else(|| vortex_err!("No free split slot"))?; let index = self.next; self.next += 1; let split = self.splits[index].clone(); - let output = - match self.root.as_ref().ok_or_else( - || vortex_err!(AssertionFailed: "Scan has no plan for its next split"), - )? { - Root::Plan(plan) => { - self.core - .compile_stage(plan, split.rows.clone(), &split.mask, slot)? - } - }; + let output = match self + .root + .as_ref() + .ok_or_else(|| vortex_err!("Scan has no plan for its next split"))? + { + Root::Plan(plan) => { + self.core + .compile_stage(plan, split.rows.clone(), &split.mask, slot)? + } + }; if self.next == self.splits.len() { // Compiled operators own what they need. The last split no longer needs the // lowering tree or the source layouts retained by its lazy children. diff --git a/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs b/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs index 1fa3daed93d..19bcb5504db 100644 --- a/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs +++ b/vortex-layout/src/plan/physical/pipeline/scheduling_tests.rs @@ -66,7 +66,7 @@ fn run( } Turn::Waiting => { if inflight.is_empty() { - return Err(vortex_err!(AssertionFailed: "scan waits with no reads in flight")); + return Err(vortex_err!("scan waits with no reads in flight")); } let read = inflight.remove(pick(&inflight)); events.push(Some(*read.segment_id)); @@ -275,7 +275,7 @@ fn a_source_has_several_reads_in_flight(#[values(1, 3)] deliveries: usize) -> Vo for _ in 0..deliveries { let read = inflight .pop() - .ok_or_else(|| vortex_err!(AssertionFailed: "no read in flight"))?; + .ok_or_else(|| vortex_err!("no read in flight"))?; scan.deliver(read.id, empty_segment())?; } } @@ -325,7 +325,7 @@ impl Operator for ReadAfterInlet { }; let (segment, _) = cx .take_segment() - .ok_or_else(|| vortex_err!(AssertionFailed: "computed before the read arrived"))?; + .ok_or_else(|| vortex_err!("computed before the read arrived"))?; assert_eq!(*segment, u32::try_from(batch.len())?); Ok(Step::Final(batch)) } @@ -341,7 +341,7 @@ fn readiness_can_take_an_inlet_and_request_a_read() -> VortexResult<()> { move |rows, mask, compiler| { let chain = compiler .compile(&child, rows, mask)? - .ok_or_else(|| vortex_err!(AssertionFailed: "child has no rows"))?; + .ok_or_else(|| vortex_err!("child has no rows"))?; Ok(Some(compiler.join_with( vec![chain], |_| 1, @@ -389,9 +389,9 @@ impl Operator for FirstOf { if self.done { return Ok(Step::End); } - let (segment, _) = cx.take_segment().ok_or_else( - || vortex_err!(AssertionFailed: "FirstOf computed before a read arrived"), - )?; + let (segment, _) = cx + .take_segment() + .ok_or_else(|| vortex_err!("FirstOf computed before a read arrived"))?; self.done = true; Ok(Step::Final(indices([u64::from(*segment)]))) } @@ -627,7 +627,7 @@ mod contract { impl Operator for WaitsWhenFull { fn compute(&mut self, _input: Input, _cx: &mut Cx<'_>) -> VortexResult { - Err(vortex_err!(AssertionFailed: "a blocked source must not compute")) + Err(vortex_err!("a blocked source must not compute")) } } diff --git a/vortex-layout/src/plan/physical/pipeline/synthetic.rs b/vortex-layout/src/plan/physical/pipeline/synthetic.rs index 8cb21770bfd..82c4f5bc3f6 100644 --- a/vortex-layout/src/plan/physical/pipeline/synthetic.rs +++ b/vortex-layout/src/plan/physical/pipeline/synthetic.rs @@ -194,7 +194,7 @@ impl Operator for RowSource { if self.waiting { self.waiting = false; cx.take_segment() - .ok_or_else(|| vortex_err!(AssertionFailed: "RowSource ran without its bytes"))?; + .ok_or_else(|| vortex_err!("RowSource ran without its bytes"))?; } if self.remaining.is_empty() { return Ok(Step::End); diff --git a/vortex-layout/src/plan/physical/pipeline/tests.rs b/vortex-layout/src/plan/physical/pipeline/tests.rs index f844c56f86e..da9af0ab96c 100644 --- a/vortex-layout/src/plan/physical/pipeline/tests.rs +++ b/vortex-layout/src/plan/physical/pipeline/tests.rs @@ -232,7 +232,7 @@ fn drive( events.push(Event::Io(std::mem::take(&mut batch))); } if inflight.is_empty() { - return Err(vortex_err!(AssertionFailed: "scan waits with no reads in flight")); + return Err(vortex_err!("scan waits with no reads in flight")); } let read = inflight.remove(pick(&inflight)); events.push(Event::Delivered(*read.segment_id)); @@ -447,7 +447,7 @@ fn every_read_is_issued_before_any_is_delivered() -> VortexResult<()> { delivery(Delivery::Fifo), )?; let Some(Event::Io(first)) = run.events.first() else { - return Err(vortex_err!(AssertionFailed: "first event must be a read batch")); + return Err(vortex_err!("first event must be a read batch")); }; assert_eq!(first.len(), store.segments.len()); assert_eq!(reads(&run.events), store.segments.len()); @@ -592,7 +592,7 @@ fn scan_keeps_the_selection_with_or_without_a_filter(#[case] sel: Sel) -> Vortex let filtered = lower(&store.flat(&values)?)?; let scan = filtered .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "A flat layout lowers to a filter"))? + .ok_or_else(|| vortex_err!("A flat layout lowers to a filter"))? .child_plan()?; assert!(scan.is::()); @@ -807,7 +807,7 @@ fn pack_readiness_tracks_changes_and_consumption( assert_eq!(cx.touched.indices(), &[1]); let Step::Final(array) = pack.compute(Input::None, &mut cx)? else { return Err(vortex_err!( - AssertionFailed: "expected Pack's last currently available batch" + "expected Pack's last currently available batch" )); }; let expected = StructArray::from_fields(&[ @@ -868,7 +868,7 @@ fn bound_selection_never_initializes_skipped_chunks() -> VortexResult<()> { let children = PlanChildren::lazy(4, move |index| match index { 0 => Ok(first.clone()), 3 => Ok(last.clone()), - _ => Err(vortex_err!(AssertionFailed: "unselected chunk {index} was initialized")), + _ => Err(vortex_err!("unselected chunk {index} was initialized")), }); // SAFETY: All four logical chunks have five rows of the same primitive dtype. The two // unselected initializers deliberately fail to detect discovery as well as compilation. diff --git a/vortex-layout/src/plan/physical/plans/concat.rs b/vortex-layout/src/plan/physical/plans/concat.rs index ec9811adaed..0d74d705f4b 100644 --- a/vortex-layout/src/plan/physical/plans/concat.rs +++ b/vortex-layout/src/plan/physical/plans/concat.rs @@ -74,14 +74,14 @@ impl ConcatPlan { for child in &children { if child.dtype() != &dtype { vortex_bail!( - MismatchedTypes: "Concat child dtype {} does not match {dtype}", + "Concat child dtype {} does not match {dtype}", child.dtype() ); } row_offsets.push(row_count); row_count = row_count .checked_add(child.row_count()) - .ok_or_else(|| vortex_error::vortex_err!(Overflow: "Concat row count overflow"))?; + .ok_or_else(|| vortex_error::vortex_err!("Concat row count overflow"))?; } // SAFETY: Child dtypes and the checked cumulative row metadata were validated above. Ok(unsafe { @@ -111,7 +111,7 @@ impl ConcatPlan { children: PlanChildren::lazy(self.children().len(), move |index| { let child = children .get(index)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Missing chunk {index}"))?; + .ok_or_else(|| vortex_err!("Missing chunk {index}"))?; let rows = child.row_count(); let mapped = map(child)?; vortex_ensure_eq!(mapped.dtype(), &child_dtype); @@ -144,7 +144,7 @@ impl PlanVTable for Concat { ) -> VortexResult<()> { if children.len() != plan.children().len() { vortex_bail!( - InvalidArgument: "Concat expects {} children but got {}", + "Concat expects {} children but got {}", plan.children().len(), children.len() ); @@ -156,7 +156,7 @@ impl PlanVTable for Concat { let child = child?; if child.dtype() != plan.dtype() { vortex_bail!( - MismatchedTypes: "Concat child dtype {} does not match {}", + "Concat child dtype {} does not match {}", child.dtype(), plan.dtype() ); @@ -164,11 +164,11 @@ impl PlanVTable for Concat { row_offsets.push(row_count); row_count = row_count .checked_add(child.row_count()) - .ok_or_else(|| vortex_error::vortex_err!(Overflow: "Concat row count overflow"))?; + .ok_or_else(|| vortex_error::vortex_err!("Concat row count overflow"))?; } if row_count != plan.row_count() { vortex_bail!( - InvalidArgument: "Concat children have {row_count} rows but the plan has {}", + "Concat children have {row_count} rows but the plan has {}", plan.row_count() ); } diff --git a/vortex-layout/src/plan/physical/plans/eval.rs b/vortex-layout/src/plan/physical/plans/eval.rs index b897cf23d65..b6a2f1ff620 100644 --- a/vortex-layout/src/plan/physical/plans/eval.rs +++ b/vortex-layout/src/plan/physical/plans/eval.rs @@ -108,11 +108,11 @@ impl PlanVTable for Eval { check_child_count("Eval", children, 1)?; let child = children .get(0)? - .ok_or_else(|| vortex_error::vortex_err!(AssertionFailed: "Eval child is absent"))?; + .ok_or_else(|| vortex_error::vortex_err!("Eval child is absent"))?; validate_expression_child(plan.expression(), &child)?; if child.row_count() != plan.row_count() { vortex_error::vortex_bail!( - InvalidArgument: "Eval child has {} rows but the plan has {}", + "Eval child has {} rows but the plan has {}", child.row_count(), plan.row_count() ); @@ -142,7 +142,7 @@ impl PlanVTable for Eval { fn validate_expression_child(expression: &BoundExpression, child: &PlanRef) -> VortexResult<()> { if !expression.is_root_bound_to(child.dtype()) { vortex_bail!( - MismatchedTypes: "Eval expression is not bound to child dtype {}", + "Eval expression is not bound to child dtype {}", child.dtype() ); } diff --git a/vortex-layout/src/plan/physical/plans/filter.rs b/vortex-layout/src/plan/physical/plans/filter.rs index 7417208c38c..857a69a376e 100644 --- a/vortex-layout/src/plan/physical/plans/filter.rs +++ b/vortex-layout/src/plan/physical/plans/filter.rs @@ -78,9 +78,9 @@ impl PlanVTable for Filter { check_child_count("Filter", children, 1)?; let child = children .get(0)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Filter child is absent"))?; + .ok_or_else(|| vortex_err!("Filter child is absent"))?; if child.dtype() != plan.dtype() || child.row_count() != plan.row_count() { - vortex_bail!(MismatchedTypes: "Filter child does not match the filter's dtype and row count"); + vortex_bail!("Filter child does not match the filter's dtype and row count"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/legacy_stats.rs b/vortex-layout/src/plan/physical/plans/legacy_stats.rs index f8823e38545..7eb6bec85ff 100644 --- a/vortex-layout/src/plan/physical/plans/legacy_stats.rs +++ b/vortex-layout/src/plan/physical/plans/legacy_stats.rs @@ -121,9 +121,9 @@ impl PlanVTable for LegacyStats { check_child_count("LegacyStats", children, 2)?; let data = children .get(DATA)? - .ok_or_else(|| vortex_err!(AssertionFailed: "LegacyStats data child is absent"))?; + .ok_or_else(|| vortex_err!("LegacyStats data child is absent"))?; if data.dtype() != plan.dtype() || data.row_count() != plan.row_count() { - vortex_bail!(MismatchedTypes: "LegacyStats data child shape does not match the plan output"); + vortex_bail!("LegacyStats data child shape does not match the plan output"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/list_pack.rs b/vortex-layout/src/plan/physical/plans/list_pack.rs index 8a9ddf4d70c..bb075c7f4e2 100644 --- a/vortex-layout/src/plan/physical/plans/list_pack.rs +++ b/vortex-layout/src/plan/physical/plans/list_pack.rs @@ -127,23 +127,23 @@ impl PlanVTable for ListPack { } fn validate_children(dtype: &DType, row_count: u64, children: &PlanChildren) -> VortexResult<()> { - let elements_dtype = dtype.as_list_element_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "ListPack output dtype must be a list, got {dtype}"), - )?; + let elements_dtype = dtype + .as_list_element_opt() + .ok_or_else(|| vortex_err!("ListPack output dtype must be a list, got {dtype}"))?; let expected_children = 2 + usize::from(dtype.is_nullable()); if children.len() != expected_children { vortex_bail!( - InvalidArgument: "ListPack expects {expected_children} children but got {}", + "ListPack expects {expected_children} children but got {}", children.len() ); } let elements = children .get(ELEMENTS)? - .ok_or_else(|| vortex_err!(AssertionFailed: "ListPack elements child is absent"))?; + .ok_or_else(|| vortex_err!("ListPack elements child is absent"))?; if elements.dtype() != elements_dtype.as_ref() { vortex_bail!( - MismatchedTypes: "ListPack elements child has dtype {} but the list element dtype is {}", + "ListPack elements child has dtype {} but the list element dtype is {}", elements.dtype(), elements_dtype ); @@ -151,19 +151,19 @@ fn validate_children(dtype: &DType, row_count: u64, children: &PlanChildren) -> let offsets = children .get(OFFSETS)? - .ok_or_else(|| vortex_err!(AssertionFailed: "ListPack offsets child is absent"))?; + .ok_or_else(|| vortex_err!("ListPack offsets child is absent"))?; if !offsets.dtype().is_int() || offsets.dtype().is_nullable() { vortex_bail!( - MismatchedTypes: "ListPack offsets child must have a non-nullable integer dtype, got {}", + "ListPack offsets child must have a non-nullable integer dtype, got {}", offsets.dtype() ); } let offsets_row_count = row_count .checked_add(1) - .ok_or_else(|| vortex_err!(Overflow: "ListPack offsets row count overflow"))?; + .ok_or_else(|| vortex_err!("ListPack offsets row count overflow"))?; if offsets.row_count() != offsets_row_count { vortex_bail!( - InvalidArgument: "ListPack offsets child has {} rows but must have {offsets_row_count}", + "ListPack offsets child has {} rows but must have {offsets_row_count}", offsets.row_count() ); } @@ -171,17 +171,17 @@ fn validate_children(dtype: &DType, row_count: u64, children: &PlanChildren) -> if dtype.is_nullable() { let validity = children .get(VALIDITY)? - .ok_or_else(|| vortex_err!(AssertionFailed: "ListPack validity child is absent"))?; + .ok_or_else(|| vortex_err!("ListPack validity child is absent"))?; let validity_dtype = DType::Bool(Nullability::NonNullable); if validity.dtype() != &validity_dtype { vortex_bail!( - MismatchedTypes: "ListPack validity child has dtype {} but must have dtype {validity_dtype}", + "ListPack validity child has dtype {} but must have dtype {validity_dtype}", validity.dtype() ); } if validity.row_count() != row_count { vortex_bail!( - InvalidArgument: "ListPack validity child has {} rows but the plan has {row_count}", + "ListPack validity child has {} rows but the plan has {row_count}", validity.row_count() ); } diff --git a/vortex-layout/src/plan/physical/plans/pack.rs b/vortex-layout/src/plan/physical/plans/pack.rs index 01400b7568a..b37f50934e8 100644 --- a/vortex-layout/src/plan/physical/plans/pack.rs +++ b/vortex-layout/src/plan/physical/plans/pack.rs @@ -96,13 +96,13 @@ impl PackPlan { ) -> VortexResult { if field_plans.len() != fields.nfields() { vortex_bail!( - InvalidArgument: "Pack expects {} field children but got {}", + "Pack expects {} field children but got {}", fields.nfields(), field_plans.len() ); } if validity.is_some() != (nullability == Nullability::Nullable) { - vortex_bail!(InvalidArgument: "Pack validity child must be present exactly when the struct is nullable"); + vortex_bail!("Pack validity child must be present exactly when the struct is nullable"); } for (index, (field_dtype, field_plan)) in @@ -181,21 +181,21 @@ impl PlanVTable for Pack { let expected_children = plan.nfields() + usize::from(plan.dtype().is_nullable()); if children.len() != expected_children { vortex_bail!( - InvalidArgument: "Pack expects {expected_children} children but got {}", + "Pack expects {expected_children} children but got {}", children.len() ); } for (index, field_dtype) in plan.fields().fields().enumerate() { - let child = children.get(index)?.ok_or_else( - || vortex_err!(AssertionFailed: "Pack field child {index} is absent"), - )?; + let child = children + .get(index)? + .ok_or_else(|| vortex_err!("Pack field child {index} is absent"))?; validate_field_child(index, &field_dtype, plan.row_count(), &child)?; } if plan.dtype().is_nullable() { let validity = children .get(plan.nfields())? - .ok_or_else(|| vortex_err!(AssertionFailed: "Pack validity child is absent"))?; + .ok_or_else(|| vortex_err!("Pack validity child is absent"))?; validate_validity_child(plan.row_count(), &validity)?; } Ok(()) @@ -237,7 +237,7 @@ impl PlanVTable for Pack { chains.push( compiler .compile(child?, rows.clone(), mask)? - .ok_or_else(|| vortex_err!(AssertionFailed: "A Pack field produced no rows"))?, + .ok_or_else(|| vortex_err!("A Pack field produced no rows"))?, ); } let nullable = plan.dtype().is_nullable(); @@ -259,13 +259,13 @@ fn validate_field_child( ) -> VortexResult<()> { if child.dtype() != expected_dtype { vortex_bail!( - MismatchedTypes: "Pack field child {index} has dtype {} but the field has dtype {expected_dtype}", + "Pack field child {index} has dtype {} but the field has dtype {expected_dtype}", child.dtype() ); } if child.row_count() != expected_row_count { vortex_bail!( - InvalidArgument: "Pack field child {index} has {} rows but the plan has {expected_row_count}", + "Pack field child {index} has {} rows but the plan has {expected_row_count}", child.row_count() ); } @@ -276,13 +276,13 @@ fn validate_validity_child(expected_row_count: u64, child: &PlanRef) -> VortexRe let expected_dtype = DType::Bool(Nullability::NonNullable); if child.dtype() != &expected_dtype { vortex_bail!( - MismatchedTypes: "Pack validity child has dtype {} but must have dtype {expected_dtype}", + "Pack validity child has dtype {} but must have dtype {expected_dtype}", child.dtype() ); } if child.row_count() != expected_row_count { vortex_bail!( - InvalidArgument: "Pack validity child has {} rows but the plan has {expected_row_count}", + "Pack validity child has {} rows but the plan has {expected_row_count}", child.row_count() ); } @@ -300,7 +300,7 @@ impl PackPlan { ) -> VortexResult { vortex_ensure!( !self.dtype().is_nullable(), - InvalidArgument: "Cannot prune fields from a nullable Pack" + "Cannot prune fields from a nullable Pack" ); let struct_fields = StructFields::from_iter( fields @@ -377,10 +377,10 @@ impl PlanParentReduceRule for ExpressionPackRule { let name = partitioned .partition_names .get(0) - .ok_or_else(|| vortex_err!(NotFound: "Struct expression partition has no field"))?; - let index = fields.find(name).ok_or_else( - || vortex_err!(NotFound: "Struct expression references unknown field '{name}'"), - )?; + .ok_or_else(|| vortex_err!("Struct expression partition has no field"))?; + let index = fields.find(name).ok_or_else(|| { + vortex_err!("Struct expression references unknown field '{name}'") + })?; let field = field_plan(child, index)?; let lowered = step_into_struct_field(expanded, name, field.dtype().clone())?; return Ok(Some(EvalPlan::try_new(lowered, field)?.into_plan())); @@ -392,18 +392,19 @@ impl PlanParentReduceRule for ExpressionPackRule { for index in 0..partitioned.partitions.len() { let name = &partitioned.partition_names[index]; let partition = &partitioned.partitions[index]; - let field_index = fields.find(name).ok_or_else( - || vortex_err!(NotFound: "Struct expression references unknown field '{name}'"), - )?; + let field_index = fields.find(name).ok_or_else(|| { + vortex_err!("Struct expression references unknown field '{name}'") + })?; let field = field_plan(child, field_index)?; let lowered = if let Some(pack) = partition .as_scalar() .and_then(|scalar_fn| scalar_fn.as_opt::()) && partition.children().len() == 1 { - let value_name = pack.names.get(0).ok_or_else( - || vortex_err!(AssertionFailed: "Struct expression partition pack is empty"), - )?; + let value_name = pack + .names + .get(0) + .ok_or_else(|| vortex_err!("Struct expression partition pack is empty"))?; collapsed.push((name.clone(), value_name.clone())); partition.children()[0].clone() } else { @@ -493,13 +494,13 @@ pub(super) fn rewrite_partition_root( fn field_name(fields: &StructFields, index: usize) -> VortexResult { Ok(fields .field_name(index) - .ok_or_else(|| vortex_err!(AssertionFailed: "Struct field {index} has no name"))? + .ok_or_else(|| vortex_err!("Struct field {index} has no name"))? .clone()) } fn field_plan(plan: &Plan, index: usize) -> VortexResult { plan.child(index)? - .ok_or_else(|| vortex_err!(NotFound: "Struct field {index} has no plan")) + .ok_or_else(|| vortex_err!("Struct field {index} has no plan")) } fn expanded_struct_root( @@ -556,7 +557,7 @@ fn expand_struct_root( if let Some(field_name) = scalar_fn.as_opt::() { let index = fields.find(field_name).ok_or_else(|| { - vortex_err!(NotFound: "Field {field_name} not found while expanding struct root") + vortex_err!("Field {field_name} not found while expanding struct root") })?; return Ok(Transformed { value: expanded_root.children()[index].clone(), diff --git a/vortex-layout/src/plan/physical/plans/row_idx.rs b/vortex-layout/src/plan/physical/plans/row_idx.rs index 2c82ee57bdb..5c45d2cae4f 100644 --- a/vortex-layout/src/plan/physical/plans/row_idx.rs +++ b/vortex-layout/src/plan/physical/plans/row_idx.rs @@ -165,22 +165,18 @@ pub fn plan_row_idx_expression( vortex_ensure_eq!( partitioned.partition_annotations.len(), 2, - AssertionFailed: "Row-index expression produced more than two partitions" + "Row-index expression produced more than two partitions" ); let row_idx_index = partitioned .partition_annotations .iter() .position(|partition| *partition == RowIdxExpressionPartition::RowIdx) - .ok_or_else( - || vortex_err!(AssertionFailed: "Row-index expression has no row-index partition"), - )?; + .ok_or_else(|| vortex_err!("Row-index expression has no row-index partition"))?; let child_index = partitioned .partition_annotations .iter() .position(|partition| *partition == RowIdxExpressionPartition::Child) - .ok_or_else( - || vortex_err!(AssertionFailed: "Row-index expression has no data partition"), - )?; + .ok_or_else(|| vortex_err!("Row-index expression has no data partition"))?; let row_idx_partition = &partitioned.partitions[row_idx_index]; let child_partition = &partitioned.partitions[child_index]; @@ -193,7 +189,7 @@ pub fn plan_row_idx_expression( .and_then(|scalar_fn| scalar_fn.as_opt::()), ) else { return Err(vortex_err!( - MismatchedTypes: "Row-index expression partitions must be struct packs" + "Row-index expression partitions must be struct packs" )); }; let row_idx_partition_name = partitioned.partition_names[row_idx_index].clone(); @@ -202,7 +198,7 @@ pub fn plan_row_idx_expression( let row_idx_expression = if row_idx_partition.children().len() == 1 { let Some(value_name) = row_idx_pack.names.get(0) else { - return Err(vortex_err!(AssertionFailed: "Row-index expression partition is empty")); + return Err(vortex_err!("Row-index expression partition is empty")); }; collapsed.push((row_idx_partition_name, value_name.clone())); row_idx_partition.children()[0].clone() @@ -211,7 +207,7 @@ pub fn plan_row_idx_expression( }; let child_expression = if child_partition.children().len() == 1 { let Some(value_name) = child_pack.names.get(0) else { - return Err(vortex_err!(AssertionFailed: "Data expression partition is empty")); + return Err(vortex_err!("Data expression partition is empty")); }; collapsed.push((child_partition_name, value_name.clone())); child_partition.children()[0].clone() diff --git a/vortex-layout/src/plan/physical/plans/share.rs b/vortex-layout/src/plan/physical/plans/share.rs index 4e2697dde06..96166e7c81f 100644 --- a/vortex-layout/src/plan/physical/plans/share.rs +++ b/vortex-layout/src/plan/physical/plans/share.rs @@ -84,9 +84,9 @@ impl PlanVTable for Share { check_child_count("Share", children, 1)?; let child = children .get(0)? - .ok_or_else(|| vortex_err!(AssertionFailed: "Share child is absent"))?; + .ok_or_else(|| vortex_err!("Share child is absent"))?; if child.dtype() != plan.dtype() || child.row_count() != plan.row_count() { - vortex_bail!(MismatchedTypes: "Share child does not match the share's dtype and row count"); + vortex_bail!("Share child does not match the share's dtype and row count"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/take.rs b/vortex-layout/src/plan/physical/plans/take.rs index 8e354a923f3..b2a1703ff8a 100644 --- a/vortex-layout/src/plan/physical/plans/take.rs +++ b/vortex-layout/src/plan/physical/plans/take.rs @@ -114,17 +114,17 @@ impl PlanVTable for Take { _data: &mut Self::PlanData, ) -> VortexResult<()> { check_child_count("Take", children, 2)?; - let codes = children.get(CODES)?.ok_or_else( - || vortex_error::vortex_err!(AssertionFailed: "Take codes child is absent"), - )?; - let values = children.get(VALUES)?.ok_or_else( - || vortex_error::vortex_err!(AssertionFailed: "Take values child is absent"), - )?; + let codes = children + .get(CODES)? + .ok_or_else(|| vortex_error::vortex_err!("Take codes child is absent"))?; + let values = children + .get(VALUES)? + .ok_or_else(|| vortex_error::vortex_err!("Take values child is absent"))?; let dtype = values .dtype() .union_nullability(codes.dtype().nullability()); if codes.row_count() != plan.row_count() || &dtype != plan.dtype() { - vortex_error::vortex_bail!(MismatchedTypes: "Take child shape does not match the plan output"); + vortex_error::vortex_bail!("Take child shape does not match the plan output"); } Ok(()) } diff --git a/vortex-layout/src/plan/physical/plans/zoned.rs b/vortex-layout/src/plan/physical/plans/zoned.rs index 574b1534c5f..d1a17702ebf 100644 --- a/vortex-layout/src/plan/physical/plans/zoned.rs +++ b/vortex-layout/src/plan/physical/plans/zoned.rs @@ -307,11 +307,11 @@ impl PlanVTable for Zoned { } check_child_count("Zoned", children, 2)?; - let data = children.get(DATA)?.ok_or_else( - || vortex_error::vortex_err!(AssertionFailed: "Zoned data child is absent"), - )?; + let data = children + .get(DATA)? + .ok_or_else(|| vortex_error::vortex_err!("Zoned data child is absent"))?; if data.dtype() != plan.dtype() || data.row_count() != plan.row_count() { - vortex_error::vortex_bail!(MismatchedTypes: "Zoned data child shape does not match the plan output"); + vortex_error::vortex_bail!("Zoned data child shape does not match the plan output"); } Ok(()) } @@ -342,7 +342,7 @@ impl PlanVTable for Zoned { ) -> VortexResult> { if !plan.is_pruning() { let Some(data) = plan.data_plan()? else { - vortex_bail!(AssertionFailed: "Zoned plan has no data child"); + vortex_bail!("Zoned plan has no data child"); }; return compiler.compile(&data, rows, mask); } @@ -351,7 +351,7 @@ impl PlanVTable for Zoned { } let expression = plan .pruning_expression() - .ok_or_else(|| vortex_err!(AssertionFailed: "Zoned pruning plan has no expression"))?; + .ok_or_else(|| vortex_err!("Zoned pruning plan has no expression"))?; if let Some(pruned) = pruned_zones(plan)?.get(expression, compiler.session())? { return Ok(Some(Chain::new(OnceSource::new(expand_zones( plan, &rows, mask, &pruned, @@ -361,7 +361,7 @@ impl PlanVTable for Zoned { let count = usize::try_from(zones.row_count())?; let Some(chain) = compiler.compile(&zones, 0..zones.row_count(), &Mask::new_true(count))? else { - vortex_bail!(AssertionFailed: "Zoned pruning plan has an empty zone table"); + vortex_bail!("Zoned pruning plan has an empty zone table"); }; let zoned = plan.clone(); let mask = mask.clone(); @@ -376,7 +376,7 @@ impl PlanVTable for Zoned { /// The per-zone results kept on a pruning `plan`. fn pruned_zones(plan: &ZonedPlan) -> VortexResult<&Arc> { plan.pruned_zones() - .ok_or_else(|| vortex_err!(AssertionFailed: "Zone pruning needs a pruning plan")) + .ok_or_else(|| vortex_err!("Zone pruning needs a pruning plan")) } /// Builds the zone map from the zone table and proves the expression over it, one value per @@ -386,7 +386,7 @@ fn prune_zones(plan: &ZonedPlan, session: &VortexSession, table: ArrayRef) -> Vo let (Some(expression), Some(column_dtype)) = (plan.pruning_expression(), plan.pruning_column_dtype()) else { - vortex_bail!(AssertionFailed: "Zone pruning needs a pruning plan"); + vortex_bail!("Zone pruning needs a pruning plan"); }; let zone_map = ZoneMap::try_new( column_dtype.clone(), diff --git a/vortex-layout/src/plan/physical/selection.rs b/vortex-layout/src/plan/physical/selection.rs index d4e7d3daa41..1087ad61538 100644 --- a/vortex-layout/src/plan/physical/selection.rs +++ b/vortex-layout/src/plan/physical/selection.rs @@ -77,7 +77,7 @@ impl SelectedData { fn mask(&self, rows: &Range) -> VortexResult { vortex_ensure!( rows.start >= self.rows.start && rows.end <= self.rows.end, - OutOfBounds: "Selected plan requested outside its bound row range" + "Selected plan requested outside its bound row range" ); Ok(self.mask.slice( usize::try_from(rows.start - self.rows.start)? diff --git a/vortex-layout/src/plan/physical/tests.rs b/vortex-layout/src/plan/physical/tests.rs index 61ebbf72f26..47bad2dd94f 100644 --- a/vortex-layout/src/plan/physical/tests.rs +++ b/vortex-layout/src/plan/physical/tests.rs @@ -98,7 +98,7 @@ fn make_row_idx_plan(expression: Expression, child: PlanRef) -> VortexResult VortexResult { plan.child(index)? - .ok_or_else(|| vortex_err!(NotFound: "missing child {index}")) + .ok_or_else(|| vortex_err!("missing child {index}")) } fn assert_unsupported(error: vortex_error::VortexError) { @@ -114,9 +114,11 @@ fn assert_unsupported(error: vortex_error::VortexError) { fn unsupported_layout_has_no_plan() -> VortexResult<()> { let layout = unsupported(3, DType::Null); - assert_unsupported(lower(&layout).err().ok_or_else( - || vortex_err!(InvalidArgument: "unsupported layout unexpectedly produced a plan"), - )?); + assert_unsupported( + lower(&layout) + .err() + .ok_or_else(|| vortex_err!("unsupported layout unexpectedly produced a plan"))?, + ); Ok(()) } @@ -165,9 +167,9 @@ fn optimize_preserves_unvisited_concat_children() -> VortexResult<()> { let plan = optimize(make_plan(layout)?)?; assert_eq!(child_of(&plan, 0)?.row_count(), 2); assert_unsupported( - child_of(&plan, 1).err().ok_or_else( - || vortex_err!(AssertionFailed: "unsupported child unexpectedly lowered"), - )?, + child_of(&plan, 1) + .err() + .ok_or_else(|| vortex_err!("unsupported child unexpectedly lowered"))?, ); Ok(()) } @@ -187,9 +189,11 @@ fn chunked_plan_lowers_each_chunk_on_access() -> VortexResult<()> { let plan = make_plan(layout)?; assert_eq!(child_of(&plan, 0)?.row_count(), 1); - assert_unsupported(child_of(&plan, 1).err().ok_or_else( - || vortex_err!(InvalidArgument: "unsupported chunk unexpectedly produced a plan"), - )?); + assert_unsupported( + child_of(&plan, 1) + .err() + .ok_or_else(|| vortex_err!("unsupported chunk unexpectedly produced a plan"))?, + ); Ok(()) } @@ -208,9 +212,11 @@ fn struct_plan_lowers_each_field_on_access() -> VortexResult<()> { let plan = make_plan(layout)?; assert_eq!(child_of(&plan, 0)?.row_count(), 1); - assert_unsupported(child_of(&plan, 1).err().ok_or_else( - || vortex_err!(InvalidArgument: "unsupported field unexpectedly produced a plan"), - )?); + assert_unsupported( + child_of(&plan, 1) + .err() + .ok_or_else(|| vortex_err!("unsupported field unexpectedly produced a plan"))?, + ); Ok(()) } @@ -319,7 +325,7 @@ fn with_children_rejects_mismatched_arity() -> VortexResult<()> { let error = plan .with_children(vec![child_of(&plan, 0)?]) .err() - .ok_or_else(|| vortex_err!(MismatchedTypes: "mismatched arity unexpectedly succeeded"))?; + .ok_or_else(|| vortex_err!("mismatched arity unexpectedly succeeded"))?; assert!( error .to_string() @@ -352,9 +358,9 @@ fn eval_try_new_validates_expression_root_dtype() -> VortexResult<()> { let expression = root().bind(&primitive(PType::I32, Nullability::NonNullable))?; let child = make_plan(flat(3, primitive(PType::I64, Nullability::NonNullable), 0))?; - let error = EvalPlan::try_new(expression, child).err().ok_or_else( - || vortex_err!(MismatchedTypes: "mismatched Eval root dtype unexpectedly succeeded"), - )?; + let error = EvalPlan::try_new(expression, child) + .err() + .ok_or_else(|| vortex_err!("mismatched Eval root dtype unexpectedly succeeded"))?; assert!( error .to_string() @@ -640,13 +646,13 @@ fn empty_projection_prunes_row_idx_child_fields() -> VortexResult<()> { let plan = make_row_idx_plan(projection, make_plan(layout)?)?; let optimized = optimize(plan)?; - let projection = optimized.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "optimized plan has no projection expression"), - )?; + let projection = optimized + .as_opt::() + .ok_or_else(|| vortex_err!("optimized plan has no projection expression"))?; let child = projection.child_plan()?; - let empty_struct = child.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "empty projection did not prune the RowIdx child"), - )?; + let empty_struct = child + .as_opt::() + .ok_or_else(|| vortex_err!("empty projection did not prune the RowIdx child"))?; assert_eq!(empty_struct.nfields(), 0); assert_eq!(empty_struct.children().len(), 0); @@ -1174,7 +1180,7 @@ fn dictionary_pushdown_rejects_unsafe_expressions() -> VortexResult<()> { let plan = make_eval(expression.clone(), make_plan(Arc::clone(&dictionary))?)?.into_plan(); let optimized = optimize(plan)?; let eval = optimized.as_opt::().ok_or_else(|| { - vortex_err!(AssertionFailed: "Expression unexpectedly pushed into dictionary: {expression}") + vortex_err!("Expression unexpectedly pushed into dictionary: {expression}") })?; assert!(eval.child_plan()?.is::()); } @@ -1189,9 +1195,9 @@ fn non_strict_expression_pushes_into_dictionary_without_null_codes() -> VortexRe ) .into_layout(); let optimized = optimize(make_eval(is_null(root()), make_plan(dictionary)?)?.into_plan())?; - let take = optimized.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "is_null was not pushed into the dictionary: {optimized}"), - )?; + let take = optimized + .as_opt::() + .ok_or_else(|| vortex_err!("is_null was not pushed into the dictionary: {optimized}"))?; assert!(take.values()?.is::()); Ok(()) } @@ -1214,9 +1220,9 @@ fn nullable_struct_keeps_expression_above_parent_validity() -> VortexResult<()> let plan = make_eval(gt(get_item("a", root()), lit(5_i32)), make_plan(layout)?)?.into_plan(); let optimized = optimize(plan)?; - let eval = optimized.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "Nullable struct expression unexpectedly pushed down"), - )?; + let eval = optimized + .as_opt::() + .ok_or_else(|| vortex_err!("Nullable struct expression unexpectedly pushed down"))?; assert!(eval.child_plan()?.is::()); Ok(()) } @@ -1225,8 +1231,7 @@ fn nullable_struct_keeps_expression_above_parent_validity() -> VortexResult<()> fn zoned_plan_exposes_data_and_zones() -> VortexResult<()> { let dtype = primitive(PType::I32, Nullability::NonNullable); let (max, zones_dtype) = max_zones_dtype(&dtype)?; - let zone_len = - NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; + let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; let layout = ZonedLayout::try_new( flat(5, dtype, 0), flat(2, zones_dtype, 1), @@ -1253,13 +1258,12 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { let max = Max.bind(NumericalAggregateOpts::skip_nans()); let max_dtype = max .state_dtype(&dtype) - .ok_or_else(|| vortex_err!(AssertionFailed: "max does not support {dtype}"))?; + .ok_or_else(|| vortex_err!("max does not support {dtype}"))?; let zones_dtype = DType::Struct( StructFields::from_iter([(max.to_string(), max_dtype.as_nullable())]), Nullability::NonNullable, ); - let zone_len = - NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; + let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; let layout = ZonedLayout::try_new( flat(5, dtype.clone(), 0), flat(2, zones_dtype, 1), @@ -1272,7 +1276,7 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { let falsifier = filter .bind(&dtype)? .falsify(&session)? - .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; + .ok_or_else(|| vortex_err!("filter has no falsifier"))?; let source = make_plan(layout)?; let plan = EvalPlan::try_new(falsifier.clone(), source.clone())?.into_plan(); @@ -1293,7 +1297,7 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { "); let zoned = optimized .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "optimized pruning plan is not zoned"))?; + .ok_or_else(|| vortex_err!("optimized pruning plan is not zoned"))?; assert!(zoned.is_pruning()); assert_eq!(zoned.pruning_expression(), Some(&falsifier)); assert!(zoned.data_plan()?.is_none()); @@ -1301,15 +1305,15 @@ fn stats_expression_rewrites_to_zoned_pruning_plan() -> VortexResult<()> { let mixed_expression = bound_and(falsifier, gt(root(), lit(0_i32)).bind(&dtype)?); let mixed = optimize(EvalPlan::try_new(mixed_expression, source)?.into_plan())?; - let mixed = mixed.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "expression with a data reference was pushed into zones"), - )?; + let mixed = mixed + .as_opt::() + .ok_or_else(|| vortex_err!("expression with a data reference was pushed into zones"))?; let mixed_child = mixed.child_plan()?; assert!(mixed_child.is::()); assert!( !mixed_child .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "mixed expression child is not zoned"))? + .ok_or_else(|| vortex_err!("mixed expression child is not zoned"))? .is_pruning() ); Ok(()) @@ -1321,13 +1325,12 @@ fn pruning_expression_partitions_across_row_idx_and_zoned_struct_field() -> Vort let max = Max.bind(NumericalAggregateOpts::skip_nans()); let max_dtype = max .state_dtype(&value_dtype) - .ok_or_else(|| vortex_err!(AssertionFailed: "max does not support {value_dtype}"))?; + .ok_or_else(|| vortex_err!("max does not support {value_dtype}"))?; let zones_dtype = DType::Struct( StructFields::from_iter([(max.to_string(), max_dtype.as_nullable())]), Nullability::NonNullable, ); - let zone_len = - NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; + let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; let zoned = ZonedLayout::try_new( flat(5, value_dtype.clone(), 0), flat(2, zones_dtype, 1), @@ -1354,7 +1357,7 @@ fn pruning_expression_partitions_across_row_idx_and_zoned_struct_field() -> Vort let falsifier = filter .bind(&struct_dtype)? .falsify(&session)? - .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; + .ok_or_else(|| vortex_err!("filter has no falsifier"))?; let optimized = optimize(plan_row_idx_expression(falsifier, source)?)?; insta::assert_snapshot!(optimized.display_tree(), @r" @@ -1422,8 +1425,7 @@ fn legacy_stats_layout_lowers_to_legacy_stats_plan() -> VortexResult<()> { fn zoned_layouts_without_statistics_lower_to_their_data() -> VortexResult<()> { let dtype = primitive(PType::I32, Nullability::NonNullable); let empty = DType::Struct(StructFields::empty(), Nullability::NonNullable); - let zone_len = - NonZeroUsize::new(3).ok_or_else(|| vortex_err!(AssertionFailed: "zone length is zero"))?; + let zone_len = NonZeroUsize::new(3).ok_or_else(|| vortex_err!("zone length is zero"))?; let layouts = [ legacy_layout(&dtype, 0, &[Stat::Max], legacy_max_zones_dtype(&dtype))?, legacy_layout(&dtype, 3, &[], empty.clone())?, @@ -1469,7 +1471,7 @@ fn max_zones_dtype(dtype: &DType) -> VortexResult<(AggregateFnRef, DType)> { let max = Max.bind(NumericalAggregateOpts::skip_nans()); let max_dtype = max .state_dtype(dtype) - .ok_or_else(|| vortex_err!(AssertionFailed: "max does not support {dtype}"))?; + .ok_or_else(|| vortex_err!("max does not support {dtype}"))?; let zones_dtype = DType::Struct( StructFields::from_iter([(max.to_string(), max_dtype.as_nullable())]), Nullability::NonNullable, @@ -1486,7 +1488,7 @@ fn legacy_stats_rewrite_to_zoned_over_converted_zones() -> VortexResult<()> { let optimized = optimize(legacy.clone())?; let zoned = optimized .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "legacy stats did not become zoned"))?; + .ok_or_else(|| vortex_err!("legacy stats did not become zoned"))?; assert!(!zoned.is_pruning()); assert_eq!(zoned.zone_len(), 3); assert_eq!( @@ -1504,11 +1506,11 @@ fn legacy_stats_rewrite_to_zoned_over_converted_zones() -> VortexResult<()> { let falsifier = gt(root(), lit(5_i32)) .bind(&dtype)? .falsify(&SESSION)? - .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; + .ok_or_else(|| vortex_err!("filter has no falsifier"))?; let pruning = optimize(EvalPlan::try_new(falsifier, legacy)?.into_plan())?; - let pruning = pruning.as_opt::().ok_or_else( - || vortex_err!(AssertionFailed: "legacy stats predicate did not become a pruning plan"), - )?; + let pruning = pruning + .as_opt::() + .ok_or_else(|| vortex_err!("legacy stats predicate did not become a pruning plan"))?; assert!(pruning.is_pruning()); assert!(pruning.zones_plan()?.is::()); Ok(()) @@ -1540,7 +1542,7 @@ fn converted_legacy_zones_prune() -> VortexResult<()> { let falsifier = gt(root(), lit(5_i32)) .bind(&dtype)? .falsify(&SESSION)? - .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; + .ok_or_else(|| vortex_err!("filter has no falsifier"))?; // Only the first zone's max proves no row exceeds 5. assert_eq!( zone_map.prune(&falsifier, &SESSION)?, @@ -1560,7 +1562,7 @@ fn legacy_stats_under_zoned_are_dropped() -> VortexResult<()> { let optimized = optimize(plan)?; let zoned = optimized .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "zoned plan was rewritten away"))?; + .ok_or_else(|| vortex_err!("zoned plan was rewritten away"))?; assert!(zoned.data_plan()?.is_some_and(|data| data.is::())); assert!(PlanRef::ptr_eq(&zoned.zones_plan()?, &zones)); Ok(()) @@ -1628,11 +1630,11 @@ fn dynamic_predicates_stay_above_dictionary_values() -> VortexResult<()> { optimize(make_eval(predicate, make_plan(Arc::clone(&layout))?)?.into_plan())?; let eval = optimized .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "dynamic predicate was pushed down"))?; + .ok_or_else(|| vortex_err!("dynamic predicate was pushed down"))?; let take = eval .child_plan()? .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "dynamic predicate is not over the take"))? + .ok_or_else(|| vortex_err!("dynamic predicate is not over the take"))? .clone(); assert!(!take.values()?.is::(), "{}", optimized.display_tree()); } @@ -1659,11 +1661,11 @@ fn expression_pushes_onto_values_less_nullable_than_the_take() -> VortexResult<( assert_eq!(optimized.dtype(), &dtype); let take = optimized .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "predicate was not pushed onto the values"))?; + .ok_or_else(|| vortex_err!("predicate was not pushed onto the values"))?; let values = take.values()?; let eval = values .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "values are not evaluated"))?; + .ok_or_else(|| vortex_err!("values are not evaluated"))?; assert!(eval.expression().is_root_bound_to(&values_dtype)); Ok(()) } @@ -1684,14 +1686,14 @@ fn zoned_pruning_plan_with_new_zones_proves_them_again() -> VortexResult<()> { let falsifier = gt(root(), lit(5_i32)) .bind(&dtype)? .falsify(&SESSION)? - .ok_or_else(|| vortex_err!(AssertionFailed: "filter has no falsifier"))?; + .ok_or_else(|| vortex_err!("filter has no falsifier"))?; let pruning = optimize(EvalPlan::try_new(falsifier.clone(), source)?.into_plan())?; let pruning = pruning .as_opt::() - .ok_or_else(|| vortex_err!(AssertionFailed: "predicate did not become a pruning plan"))?; + .ok_or_else(|| vortex_err!("predicate did not become a pruning plan"))?; let proof = pruning .pruned_zones() - .ok_or_else(|| vortex_err!(AssertionFailed: "pruning plan has no proof"))?; + .ok_or_else(|| vortex_err!("pruning plan has no proof"))?; let zone_map = |bounds: [i32; 2]| { let table = StructArray::from_fields(&[( @@ -1711,7 +1713,7 @@ fn zoned_pruning_plan_with_new_zones_proves_them_again() -> VortexResult<()> { let rebuilt_proof = rebuilt .as_opt::() .and_then(|zoned| zoned.pruned_zones()) - .ok_or_else(|| vortex_err!(AssertionFailed: "rebuilt plan has no proof"))?; + .ok_or_else(|| vortex_err!("rebuilt plan has no proof"))?; assert!(rebuilt_proof.get(&falsifier, &SESSION)?.is_none()); let updated = Mask::from_iter([false, true]); assert_eq!( diff --git a/vortex-layout/src/plan/physical/typed.rs b/vortex-layout/src/plan/physical/typed.rs index 2b7618092a3..c783dc8137b 100644 --- a/vortex-layout/src/plan/physical/typed.rs +++ b/vortex-layout/src/plan/physical/typed.rs @@ -94,7 +94,7 @@ impl PlanRef { /// Returns the child at `index`, or an error when the index is out of bounds. pub fn child_required(&self, index: usize) -> VortexResult { self.child(index)? - .ok_or_else(|| vortex_err!(NotFound: "Missing plan child {index}")) + .ok_or_else(|| vortex_err!("Missing plan child {index}")) } /// Rebuilds this plan with `children` stored outside its erased operator data. @@ -143,12 +143,12 @@ impl PlanRef { ) -> VortexResult> { vortex_ensure!( rows.start <= rows.end && rows.end <= self.row_count(), - OutOfBounds: "Compile rows {rows:?} exceed plan row count {}", + "Compile rows {rows:?} exceed plan row count {}", self.row_count() ); vortex_ensure!( mask.len() as u64 == rows.end - rows.start, - InvalidArgument: "Compile mask length {} does not match rows {rows:?}", + "Compile mask length {} does not match rows {rows:?}", mask.len() ); self.dyn_plan().dyn_compile(self, rows, mask, compiler) diff --git a/vortex-layout/src/plan/physical/vtable.rs b/vortex-layout/src/plan/physical/vtable.rs index ac76b88c22f..75f3e4139c8 100644 --- a/vortex-layout/src/plan/physical/vtable.rs +++ b/vortex-layout/src/plan/physical/vtable.rs @@ -88,6 +88,6 @@ pub trait PlanVTable: 'static + Clone + Sized + Send + Sync + Debug { compiler: &mut Compiler<'_>, ) -> VortexResult> { let _ = (rows, mask, compiler); - vortex_bail!(NotImplemented: "Plan {} has no pipeline implementation", plan.vtable().id()) + vortex_bail!("Plan {} has no pipeline implementation", plan.vtable().id()) } } diff --git a/vortex-layout/src/reader.rs b/vortex-layout/src/reader.rs index dad6c5920d0..91dda0e23c5 100644 --- a/vortex-layout/src/reader.rs +++ b/vortex-layout/src/reader.rs @@ -41,7 +41,7 @@ impl SplitRange { /// Constructs a split range, returning an error if the local row range is invalid. pub fn try_new(row_offset: u64, row_range: Range) -> VortexResult { if row_range.start > row_range.end { - vortex_bail!(InvalidArgument: "Invalid split range {:?}", row_range); + vortex_bail!("Invalid split range {:?}", row_range); } Ok(Self { @@ -84,7 +84,7 @@ impl SplitRange { pub fn check_bounds(&self, row_count: u64) -> VortexResult<()> { if self.row_range.end > row_count { vortex_bail!( - OutOfBounds: "Split range {:?} is out of bounds for row count {}", + "Split range {:?} is out of bounds for row count {}", self.row_range, row_count ); @@ -364,7 +364,7 @@ impl LazyReaderChildren { /// Return the child reader at `idx`, constructing it on first access. pub fn get(&self, idx: usize) -> VortexResult<&LayoutReaderRef> { if idx >= self.cache.len() { - vortex_bail!(OutOfBounds: "Child index out of bounds: {} of {}", idx, self.cache.len()); + vortex_bail!("Child index out of bounds: {} of {}", idx, self.cache.len()); } self.cache[idx].get_or_try_init(|| { diff --git a/vortex-layout/src/scan/execution/adaptor.rs b/vortex-layout/src/scan/execution/adaptor.rs index a3989595e5e..fc6053d55ca 100644 --- a/vortex-layout/src/scan/execution/adaptor.rs +++ b/vortex-layout/src/scan/execution/adaptor.rs @@ -145,7 +145,7 @@ impl ScanAdaptor { self.next_id = self .next_id .checked_add(1) - .ok_or_else(|| vortex_err!(Overflow: "ScanAdaptor ran out of request ids"))?; + .ok_or_else(|| vortex_err!("ScanAdaptor ran out of request ids"))?; self.outstanding.insert(id, (read, segment_id)); Ok(request::IoRequest { intent: IoIntent::Fetch, @@ -159,10 +159,10 @@ impl ScanAdaptor { /// next compute. pub(super) fn set_io_result(&mut self, id: request::IoRequestId, result: IoResult) { let Some((read, segment_id)) = self.outstanding.remove(&id.0) else { - vortex_panic!(AssertionFailed: "ScanAdaptor: delivery of {id:?}, which is not outstanding"); + vortex_panic!("ScanAdaptor: delivery of {id:?}, which is not outstanding"); }; let IoResult::Bytes(bytes) = result else { - vortex_panic!(AssertionFailed: "ScanAdaptor: segment {segment_id} answered with a size"); + vortex_panic!("ScanAdaptor: segment {segment_id} answered with a size"); }; if let Err(error) = self.deliver(read, segment_id, bytes) && self.failed.is_none() @@ -191,6 +191,6 @@ impl ScanAdaptor { self.locations .get(*id as usize) .copied() - .ok_or_else(|| vortex_err!(NotFound: "segment {id} has no known location")) + .ok_or_else(|| vortex_err!("segment {id} has no known location")) } } diff --git a/vortex-layout/src/scan/execution/projection.rs b/vortex-layout/src/scan/execution/projection.rs index 38260dc1caf..00c0a0614f6 100644 --- a/vortex-layout/src/scan/execution/projection.rs +++ b/vortex-layout/src/scan/execution/projection.rs @@ -160,7 +160,7 @@ impl Morsel for ProjectionMorsel { fn compute(&mut self) -> VortexResult { if self.done { - vortex_bail!(AssertionFailed: "ProjectionMorsel: compute called after Done"); + vortex_bail!("ProjectionMorsel: compute called after Done"); } let Some(adaptor) = self.adaptor.as_mut() else { let plans = self diff --git a/vortex-layout/src/scan/filter.rs b/vortex-layout/src/scan/filter.rs index 0bd6b44b0ad..2cb36068913 100644 --- a/vortex-layout/src/scan/filter.rs +++ b/vortex-layout/src/scan/filter.rs @@ -97,7 +97,7 @@ impl FilterExpr { pub fn report_selectivity(&self, conjunct_idx: usize, selectivity: f64) { if !(0.0..=1.0).contains(&selectivity) { vortex_panic!( - InvalidArgument: "selectivity {} must be in the range [0.0, 1.0]", + "selectivity {} must be in the range [0.0, 1.0]", selectivity ); } @@ -121,7 +121,7 @@ impl FilterExpr { histogram .read() .quantile(self.selectivity_quantile) - .map_err(|e| vortex_err!(InvalidArgument: "{e}")) // Only errors when the quantile is out of range + .map_err(|e| vortex_err!("{e}")) // Only errors when the quantile is out of range .vortex_expect("quantile out of range") }) .collect::>>() diff --git a/vortex-layout/src/scan/layout.rs b/vortex-layout/src/scan/layout.rs index 229dbf71921..ae670958ff4 100644 --- a/vortex-layout/src/scan/layout.rs +++ b/vortex-layout/src/scan/layout.rs @@ -109,7 +109,7 @@ impl DataSource for LayoutReaderDataSource { _data: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!(Serde: "LayoutReader splits are not yet serializable"); + vortex_bail!("LayoutReader splits are not yet serializable"); } async fn scan(&self, scan_request: ScanRequest) -> VortexResult { diff --git a/vortex-layout/src/scan/multi.rs b/vortex-layout/src/scan/multi.rs index fe2227bb366..c4a0d56fe3b 100644 --- a/vortex-layout/src/scan/multi.rs +++ b/vortex-layout/src/scan/multi.rs @@ -287,7 +287,7 @@ impl DataSource for MultiLayoutDataSource { _data: &[u8], _session: &VortexSession, ) -> VortexResult { - vortex_bail!(Serde: "MultiLayoutDataSource partitions are not yet serializable") + vortex_bail!("MultiLayoutDataSource partitions are not yet serializable") } async fn scan(&self, scan_request: ScanRequest) -> VortexResult { @@ -488,7 +488,7 @@ fn reader_partition( ) -> PartitionStream { if reader.dtype() != source_dtype { let error = vortex_err!( - MismatchedTypes: "Multi-layout reader dtype mismatch: expected {}, got {}", + "Multi-layout reader dtype mismatch: expected {}, got {}", source_dtype, reader.dtype() ); diff --git a/vortex-layout/src/scan/repeated_scan.rs b/vortex-layout/src/scan/repeated_scan.rs index 9b655210a49..4200d00614a 100644 --- a/vortex-layout/src/scan/repeated_scan.rs +++ b/vortex-layout/src/scan/repeated_scan.rs @@ -109,7 +109,7 @@ impl RepeatedScan { row_range: Option>, ) -> VortexResult>>>> { if self.limit.is_some() { - vortex_bail!(NotImplemented: "Split futures do not support row limits; use a scan stream or iterator"); + vortex_bail!("Split futures do not support row limits; use a scan stream or iterator"); } let ctx = self.task_context(); @@ -467,7 +467,7 @@ mod tests { #[test] fn error_ends_before_pending_work() { - let arrays = stream::iter([Err::<(), _>(vortex_err!(Other: "scan failed"))]) + let arrays = stream::iter([Err::<(), _>(vortex_err!("scan failed"))]) .chain(stream::pending()) .boxed(); let mut stream = stop_on_error(arrays); diff --git a/vortex-layout/src/scan/scan_builder.rs b/vortex-layout/src/scan/scan_builder.rs index 0e111e498e8..21dc22c04ca 100644 --- a/vortex-layout/src/scan/scan_builder.rs +++ b/vortex-layout/src/scan/scan_builder.rs @@ -664,7 +664,7 @@ mod test { _expr: &BoundExpression, _mask: Mask, ) -> VortexResult { - vortex_bail!(NotImplemented: "not needed for this test"); + vortex_bail!("not needed for this test"); } fn filter_evaluation( @@ -673,7 +673,7 @@ mod test { _expr: &BoundExpression, _mask: MaskFuture, ) -> VortexResult { - vortex_bail!(NotImplemented: "not needed for this test"); + vortex_bail!("not needed for this test"); } fn projection_evaluation( @@ -792,22 +792,20 @@ mod test { _mask: MaskFuture, ) -> VortexResult { if let Some(blocking_projection) = &self.blocking_projection { - blocking_projection.started.send(()).map_err( - |_| vortex_err!(AssertionFailed: "test projection-start receiver dropped"), - )?; + blocking_projection + .started + .send(()) + .map_err(|_| vortex_err!("test projection-start receiver dropped"))?; let _guard = blocking_projection.gate.lock(); } let start = usize::try_from(row_range.start) - .map_err(|_| vortex_err!(Overflow: "row_range.start must fit in usize"))?; + .map_err(|_| vortex_err!("row_range.start must fit in usize"))?; let end = usize::try_from(row_range.end) - .map_err(|_| vortex_err!(Overflow: "row_range.end must fit in usize"))?; + .map_err(|_| vortex_err!("row_range.end must fit in usize"))?; let values: VortexResult> = (start..end) - .map(|v| { - i32::try_from(v) - .map_err(|_| vortex_err!(Overflow: "split value must fit in i32")) - }) + .map(|v| i32::try_from(v).map_err(|_| vortex_err!("split value must fit in i32"))) .collect(); let array = PrimitiveArray::from_iter(values?).into_array(); @@ -923,9 +921,8 @@ mod test { poll_result.is_ok_and(|poll_pending| poll_pending), "first poll must return while scan task construction is blocked" ); - projection_started.map_err( - |_| vortex_err!(AssertionFailed: "stream construction did not begin in the background"), - )?; + projection_started + .map_err(|_| vortex_err!("stream construction did not begin in the background"))?; assert_eq!(calls.load(Ordering::Relaxed), 1); Ok(()) @@ -1244,7 +1241,7 @@ mod test { _expr: &BoundExpression, _mask: Mask, ) -> VortexResult { - vortex_bail!(NotImplemented: "not needed for this test"); + vortex_bail!("not needed for this test"); } fn filter_evaluation( @@ -1253,7 +1250,7 @@ mod test { _expr: &BoundExpression, _mask: MaskFuture, ) -> VortexResult { - vortex_bail!(NotImplemented: "not needed for this test"); + vortex_bail!("not needed for this test"); } fn projection_evaluation( diff --git a/vortex-layout/src/scan/split_by.rs b/vortex-layout/src/scan/split_by.rs index 4023083ed3d..b995e46222f 100644 --- a/vortex-layout/src/scan/split_by.rs +++ b/vortex-layout/src/scan/split_by.rs @@ -62,7 +62,7 @@ impl SplitBy { SplitBy::LayoutSubSplitting { max_rows } => { vortex_ensure!( max_rows > 0, - InvalidArgument: "SplitBy::LayoutSubSplitting requires a non-zero max_rows" + "SplitBy::LayoutSubSplitting requires a non-zero max_rows" ); subdivide_large_spans( layout_boundaries(layout_reader, row_range, field_mask)?, @@ -291,7 +291,7 @@ mod test { _: &BoundExpression, _: Mask, ) -> VortexResult { - vortex_bail!(NotImplemented: "not needed for this test") + vortex_bail!("not needed for this test") } fn filter_evaluation( @@ -300,7 +300,7 @@ mod test { _: &BoundExpression, _: MaskFuture, ) -> VortexResult { - vortex_bail!(NotImplemented: "not needed for this test") + vortex_bail!("not needed for this test") } fn projection_evaluation( @@ -309,7 +309,7 @@ mod test { _: &BoundExpression, _: MaskFuture, ) -> VortexResult>> { - vortex_bail!(NotImplemented: "not needed for this test") + vortex_bail!("not needed for this test") } } diff --git a/vortex-layout/src/scan/test.rs b/vortex-layout/src/scan/test.rs index 598da4936bc..7d030f2c987 100644 --- a/vortex-layout/src/scan/test.rs +++ b/vortex-layout/src/scan/test.rs @@ -184,14 +184,14 @@ impl LayoutReader for TestLayoutReader { if self.fail_first_filter && row_range.start == 0 { let len = mask.len(); return Ok(MaskFuture::new(len, async move { - Err(vortex_err!(Other: "first split filter failed")) + Err(vortex_err!("first split filter failed")) })); } let row_range = row_range.clone(); let keep_row = self.keep_row; let row_count = usize::try_from(row_range.end - row_range.start) - .map_err(|_| vortex_err!(Overflow: "row range must fit in usize"))?; + .map_err(|_| vortex_err!("row range must fit in usize"))?; Ok(MaskFuture::new(row_count, async move { let input_mask = mask.await?; @@ -220,12 +220,12 @@ impl LayoutReader for TestLayoutReader { projection_masks.lock().push(mask.true_count()); } if fail { - return Err(vortex_err!(Other: "projection failed")); + return Err(vortex_err!("projection failed")); } let start = i32::try_from(row_range.start) - .map_err(|_| vortex_err!(Overflow: "row_range.start must fit in i32"))?; + .map_err(|_| vortex_err!("row_range.start must fit in i32"))?; let end = i32::try_from(row_range.end) - .map_err(|_| vortex_err!(Overflow: "row_range.end must fit in i32"))?; + .map_err(|_| vortex_err!("row_range.end must fit in i32"))?; PrimitiveArray::from_iter((start..end).map(|value| base + value)) .into_array() .filter(mask) diff --git a/vortex-layout/src/scan/v2/io.rs b/vortex-layout/src/scan/v2/io.rs index dc2eb5c48a9..ce565846d7e 100644 --- a/vortex-layout/src/scan/v2/io.rs +++ b/vortex-layout/src/scan/v2/io.rs @@ -110,14 +110,14 @@ impl IoSource for SegmentIoSource { for request in batch { let IoTarget::Range { offset, len, .. } = request.target else { vortex_bail!( - NotImplemented: "SegmentIoSource only serves byte ranges, not {:?}", + "SegmentIoSource only serves byte ranges, not {:?}", request.target ); }; let segment = *self .ranges .get(&(offset, len)) - .ok_or_else(|| vortex_err!(NotFound: "No segment at bytes {offset}+{len}"))?; + .ok_or_else(|| vortex_err!("No segment at bytes {offset}+{len}"))?; if request.intent == IoIntent::Announce { self.announced .lock() @@ -149,7 +149,7 @@ impl IoSource for SegmentIoSource { let mut bytes = match prefetched.remove(&segment) { Some(read) => read .map_err(move |err| { - vortex_err!(Io: "prefetched read of segment {segment} failed: {err}") + vortex_err!("prefetched read of segment {segment} failed: {err}") }) .boxed(), None => self @@ -204,14 +204,14 @@ impl IoSource for SegmentIoSource { match self.reads.lock().poll_next_unpin(cx) { Poll::Ready(Some(completion)) => Poll::Ready(Ok(completion)), Poll::Ready(None) => Poll::Ready(Err(vortex_err!( - AssertionFailed: "The split's driver is waiting with no reads in flight" + "The split's driver is waiting with no reads in flight" ))), Poll::Pending => Poll::Pending, } } fn wait(&self) -> VortexResult { - vortex_bail!(AssertionFailed: "SegmentIoSource is awaited through poll_completion, not waited on") + vortex_bail!("SegmentIoSource is awaited through poll_completion, not waited on") } fn release(&self, _owner: IoOwnerId) {} @@ -286,7 +286,7 @@ mod tests { receiver .await .map(BufferHandle::new_host) - .map_err(|err| vortex_err!(Io: "{err}")) + .map_err(|err| vortex_err!("{err}")) } .boxed() } diff --git a/vortex-layout/src/scan/v2/tests.rs b/vortex-layout/src/scan/v2/tests.rs index 8e32b7f3db1..29fbcf22d11 100644 --- a/vortex-layout/src/scan/v2/tests.rs +++ b/vortex-layout/src/scan/v2/tests.rs @@ -595,10 +595,10 @@ async fn unordered_yields_before_the_split_finishes() -> VortexResult<()> { .await?; let blocked = *layout .slot(1)? - .ok_or_else(|| vortex_err!(AssertionFailed: "second chunk is missing"))? + .ok_or_else(|| vortex_err!("second chunk is missing"))? .segment_ids() .first() - .ok_or_else(|| vortex_err!(AssertionFailed: "second chunk has no segment"))?; + .ok_or_else(|| vortex_err!("second chunk has no segment"))?; let (release, gate) = oneshot::channel(); let segments: Arc = Arc::new(GatedSegments { inner: segments, @@ -612,7 +612,7 @@ async fn unordered_yields_before_the_split_finishes() -> VortexResult<()> { let mut batches = scan.execute_stream()?; let first = batches.try_next().await; let _ = release.send(()); - let first = first?.ok_or_else(|| vortex_err!(AssertionFailed: "first batch is missing"))?; + let first = first?.ok_or_else(|| vortex_err!("first batch is missing"))?; assert_arrays_eq!( first, PrimitiveArray::from_iter(0i32..i32::try_from(MAX_ROWS_PER_CHUNK)?), diff --git a/vortex-layout/src/segments/test.rs b/vortex-layout/src/segments/test.rs index 74f227d92bb..d880d15cc1a 100644 --- a/vortex-layout/src/segments/test.rs +++ b/vortex-layout/src/segments/test.rs @@ -31,7 +31,7 @@ impl SegmentSource for TestSegments { async move { buffer .map(BufferHandle::new_host) - .ok_or_else(|| vortex_err!(NotFound: "Segment not found")) + .ok_or_else(|| vortex_err!("Segment not found")) } .boxed() } diff --git a/vortex-layout/src/serde.rs b/vortex-layout/src/serde.rs index 6b8eb2edda7..0c67f7dd681 100644 --- a/vortex-layout/src/serde.rs +++ b/vortex-layout/src/serde.rs @@ -67,17 +67,16 @@ pub fn layout_from_flatbuffer_with_options( let layout_session = session.layouts(); let layouts = layout_session.registry(); let fb_layout = root_with_opts::(&LAYOUT_VERIFIER, &flatbuffer)?; - let encoding_id = layout_ctx.resolve(fb_layout.encoding()).ok_or_else( - || vortex_err!(InvalidArgument: "Invalid encoding ID: {}", fb_layout.encoding()), - )?; + let encoding_id = layout_ctx + .resolve(fb_layout.encoding()) + .ok_or_else(|| vortex_err!("Invalid encoding ID: {}", fb_layout.encoding()))?; let encoding = layouts.get(&encoding_id); if encoding.is_none() && allow_unknown { return foreign_layout_from_fb(fb_layout, dtype, layout_ctx); } - let encoding = encoding.ok_or_else( - || vortex_err!(InvalidArgument: "Invalid encoding ID: {}", fb_layout.encoding()), - )?; + let encoding = + encoding.ok_or_else(|| vortex_err!("Invalid encoding ID: {}", fb_layout.encoding()))?; // SAFETY: we validate the flatbuffer above in the `root` call, and extract a loc. let viewed_children = unsafe { @@ -121,9 +120,9 @@ fn foreign_layout_from_fb( dtype: &DType, layout_ctx: &ReadContext, ) -> VortexResult { - let encoding_id = layout_ctx.resolve(fb_layout.encoding()).ok_or_else( - || vortex_err!(InvalidArgument: "Invalid encoding ID: {}", fb_layout.encoding()), - )?; + let encoding_id = layout_ctx + .resolve(fb_layout.encoding()) + .ok_or_else(|| vortex_err!("Invalid encoding ID: {}", fb_layout.encoding()))?; let children = fb_layout .children() @@ -204,7 +203,7 @@ impl WriteFlatBuffer for LayoutFlatBufferWriter<'_> { // Dictionary-encode the layout ID let encoding = self.ctx.intern(&self.layout.encoding_id()).ok_or_else(|| { vortex_err!( - Serde: "Layout encoding {} not permitted by ctx", + "Layout encoding {} not permitted by ctx", self.layout.encoding_id() ) })?; diff --git a/vortex-layout/src/test.rs b/vortex-layout/src/test.rs index 7cdbe21f54f..29eeb8c3eba 100644 --- a/vortex-layout/src/test.rs +++ b/vortex-layout/src/test.rs @@ -35,6 +35,6 @@ impl crate::LayoutStrategy for FailingStrategy { _eof: crate::sequence::SequencePointer, _session: &VortexSession, ) -> vortex_error::VortexResult { - vortex_error::vortex_bail!(InvalidArgument: "{}", Self::MESSAGE) + vortex_error::vortex_bail!("{}", Self::MESSAGE) } } diff --git a/vortex-mask/src/bitops.rs b/vortex-mask/src/bitops.rs index 7c7b822eed3..e795c57204f 100644 --- a/vortex-mask/src/bitops.rs +++ b/vortex-mask/src/bitops.rs @@ -15,7 +15,7 @@ impl BitAnd for &Mask { fn bitand(self, rhs: Self) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!(InvalidArgument: "Masks must have the same length"); + vortex_panic!("Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -34,7 +34,7 @@ impl BitAnd<&Mask> for Mask { /// Owned-left AND: can reuse the left buffer in-place when possible. fn bitand(self, rhs: &Mask) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!(InvalidArgument: "Masks must have the same length"); + vortex_panic!("Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -53,7 +53,7 @@ impl BitOr for &Mask { fn bitor(self, rhs: Self) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!(InvalidArgument: "Masks must have the same length"); + vortex_panic!("Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -72,7 +72,7 @@ impl BitOr<&Mask> for Mask { /// Owned-left OR: can reuse the left buffer in-place when possible. fn bitor(self, rhs: &Mask) -> Self::Output { if self.len() != rhs.len() { - vortex_panic!(InvalidArgument: "Masks must have the same length"); + vortex_panic!("Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { @@ -90,7 +90,7 @@ impl Mask { /// Computes `self & !rhs` (AND NOT), equivalent to set difference. pub fn bitand_not(self, rhs: &Mask) -> Mask { if self.len() != rhs.len() { - vortex_panic!(InvalidArgument: "Masks must have the same length"); + vortex_panic!("Masks must have the same length"); } match (self.bit_buffer(), rhs.bit_buffer()) { (AllOr::None, _) | (_, AllOr::All) => Mask::new_false(self.len()), diff --git a/vortex-mask/src/lib.rs b/vortex-mask/src/lib.rs index eebacb30ee7..14dc417e5bc 100644 --- a/vortex-mask/src/lib.rs +++ b/vortex-mask/src/lib.rs @@ -534,7 +534,7 @@ impl Mask { pub fn rank(&self, n: usize) -> usize { if n >= self.true_count() { vortex_panic!( - OutOfBounds: "Rank {n} out of bounds for mask with true count {}", + "Rank {n} out of bounds for mask with true count {}", self.true_count() ); } @@ -548,7 +548,7 @@ impl Mask { values.buffer.select(n).unwrap_or_else(|| { vortex_panic!( - OutOfBounds: "Rank {} out of bounds for mask with true count {}", + "Rank {} out of bounds for mask with true count {}", values.true_count - 1, values.true_count ) diff --git a/vortex-python-cuda/src/lib.rs b/vortex-python-cuda/src/lib.rs index 655176a39c0..61bda67cd7d 100644 --- a/vortex-python-cuda/src/lib.rs +++ b/vortex-python-cuda/src/lib.rs @@ -218,19 +218,17 @@ impl ArrayChildren for MetadataChildren { .0 .as_slice() .get(index) - .ok_or_else( - || vortex_err!(OutOfBounds: "array metadata child index {index} out of bounds"), - )? + .ok_or_else(|| vortex_err!("array metadata child index {index} out of bounds"))? .clone(); vortex_ensure_eq!( child.dtype(), dtype, - MismatchedTypes: "array metadata child {index} dtype mismatch" + "array metadata child {index} dtype mismatch" ); vortex_ensure_eq!( child.len(), len, - InvalidArgument: "array metadata child {index} length mismatch" + "array metadata child {index} length mismatch" ); Ok(child) } @@ -299,10 +297,11 @@ fn deserialize_metadata_tree( let children = MetadataChildren(children); #[expect(clippy::disallowed_methods, reason = "interning a dynamic id")] let encoding_id = ArrayId::new(&metadata.encoding_id); - let plugin = - session.arrays().registry().get(&encoding_id).ok_or_else( - || vortex_err!(NotFound: "Unknown array encoding: {}", metadata.encoding_id), - )?; + let plugin = session + .arrays() + .registry() + .get(&encoding_id) + .ok_or_else(|| vortex_err!("Unknown array encoding: {}", metadata.encoding_id))?; let decoded = plugin.deserialize( ArrayDeserialization::new( encoding_id, @@ -317,18 +316,18 @@ fn deserialize_metadata_tree( vortex_ensure_eq!( decoded.len(), metadata.len, - InvalidArgument: "Array decoded from {} has incorrect length", + "Array decoded from {} has incorrect length", metadata.encoding_id ); vortex_ensure_eq!( decoded.dtype(), &dtype, - MismatchedTypes: "Array decoded from {} has incorrect dtype", + "Array decoded from {} has incorrect dtype", metadata.encoding_id ); vortex_ensure!( plugin.is_supported_encoding(&decoded.encoding_id()), - MismatchedTypes: "Array decoded from {} has incorrect encoding {}", + "Array decoded from {} has incorrect encoding {}", metadata.encoding_id, decoded.encoding_id() ); diff --git a/vortex-python/src/arrays/py/vtable.rs b/vortex-python/src/arrays/py/vtable.rs index 37d975cdc0c..686390fdddf 100644 --- a/vortex-python/src/arrays/py/vtable.rs +++ b/vortex-python/src/arrays/py/vtable.rs @@ -66,9 +66,9 @@ impl VTable for PythonVTable { len: usize, _slots: &[Option], ) -> VortexResult<()> { - vortex_ensure_eq!(data.vtable.id, self.id, MismatchedTypes: "PythonArray vtable id mismatch"); - vortex_ensure_eq!(&data.dtype, dtype, MismatchedTypes: "PythonArray dtype mismatch"); - vortex_ensure_eq!(data.len, len, InvalidArgument: "PythonArray len mismatch"); + vortex_ensure_eq!(data.vtable.id, self.id, "PythonArray vtable id mismatch"); + vortex_ensure_eq!(&data.dtype, dtype, "PythonArray dtype mismatch"); + vortex_ensure_eq!(data.len, len, "PythonArray len mismatch"); Ok(()) } @@ -77,7 +77,7 @@ impl VTable for PythonVTable { } fn buffer(_array: ArrayView<'_, Self>, idx: usize) -> BufferHandle { - vortex_panic!(OutOfBounds: "PythonArray buffer index {idx} out of bounds") + vortex_panic!("PythonArray buffer index {idx} out of bounds") } fn buffer_name(_array: ArrayView<'_, Self>, _idx: usize) -> Option { @@ -109,15 +109,15 @@ impl VTable for PythonVTable { _session: &VortexSession, ) -> VortexResult> { _ = bytes; - vortex_bail!(Serde: "PythonArray deserialization is not supported"); + vortex_bail!("PythonArray deserialization is not supported"); } fn slot_name(_array: ArrayView<'_, Self>, _idx: usize) -> String { - vortex_panic!(OutOfBounds: "PythonArray has no slots") + vortex_panic!("PythonArray has no slots") } fn execute(_array: Array, _ctx: &mut ExecutionCtx) -> VortexResult { - vortex_bail!(NotImplemented: "PythonArray execution is not supported"); + vortex_bail!("PythonArray execution is not supported"); } } @@ -129,12 +129,12 @@ impl OperationsVTable for PythonVTable { _index: usize, _ctx: &mut ExecutionCtx, ) -> VortexResult { - vortex_bail!(NotImplemented: "PythonArray scalar_at is not supported"); + vortex_bail!("PythonArray scalar_at is not supported"); } } impl ValidityVTable for PythonVTable { fn validity(_array: ArrayView<'_, PythonVTable>) -> VortexResult { - vortex_bail!(NotImplemented: "PythonArray validity is not supported"); + vortex_bail!("PythonArray validity is not supported"); } } diff --git a/vortex-python/src/arrays/range_to_sequence.rs b/vortex-python/src/arrays/range_to_sequence.rs index 8ab88a749e2..c8804c565a4 100644 --- a/vortex-python/src/arrays/range_to_sequence.rs +++ b/vortex-python/src/arrays/range_to_sequence.rs @@ -23,7 +23,7 @@ pub fn sequence_array_from_range + Into> dtype: DType, ) -> VortexResult { if step == 0 { - vortex_bail!(InvalidArgument: "Step must not be zero"); + vortex_bail!("Step must not be zero"); } // A `Sequence` holds at least one element, so an empty range returns a primitive array @@ -39,13 +39,13 @@ pub fn sequence_array_from_range + Into> } let Ok(start) = T::try_from(start) else { vortex_bail!( - Overflow: "Start, {}, does not fit in requested dtype: {}", + "Start, {}, does not fit in requested dtype: {}", start, dtype ); }; let Ok(step) = T::try_from(step) else { - vortex_bail!(Overflow: "Step, {}, does not fit in requested dtype: {}", step, dtype); + vortex_bail!("Step, {}, does not fit in requested dtype: {}", step, dtype); }; Ok(Sequence::try_new_typed::(start, step, dtype.nullability(), len)?.into_array()) diff --git a/vortex-python/src/dtype/decimal.rs b/vortex-python/src/dtype/decimal.rs index ec89db8db13..9e249c4c8e4 100644 --- a/vortex-python/src/dtype/decimal.rs +++ b/vortex-python/src/dtype/decimal.rs @@ -22,7 +22,7 @@ impl PyDecimalDType { #[getter] fn precision(slf: PyRef) -> PyResult { let DType::Decimal(decimal_dtype, _) = slf.as_ref().deref() else { - vortex_panic!(MismatchedTypes: "Not a decimal DType"); + vortex_panic!("Not a decimal DType"); }; Ok(decimal_dtype.precision()) } @@ -32,7 +32,7 @@ impl PyDecimalDType { #[getter] fn scale(slf: PyRef) -> PyResult { let DType::Decimal(decimal_dtype, _) = slf.as_ref().deref() else { - vortex_panic!(MismatchedTypes: "Not a decimal DType"); + vortex_panic!("Not a decimal DType"); }; Ok(decimal_dtype.scale()) } diff --git a/vortex-python/src/dtype/primitive.rs b/vortex-python/src/dtype/primitive.rs index 922761c2431..e6c4625d2e3 100644 --- a/vortex-python/src/dtype/primitive.rs +++ b/vortex-python/src/dtype/primitive.rs @@ -20,7 +20,7 @@ impl PyPrimitiveDType { #[getter] fn ptype(slf: PyRef) -> PyPType { let DType::Primitive(ptype, _) = slf.as_ref().deref() else { - vortex_panic!(MismatchedTypes: "Not a primitive DType"); + vortex_panic!("Not a primitive DType"); }; PyPType::from(*ptype) } diff --git a/vortex-python/src/dtype/struct_.rs b/vortex-python/src/dtype/struct_.rs index 3dd2140d41c..709147ee96b 100644 --- a/vortex-python/src/dtype/struct_.rs +++ b/vortex-python/src/dtype/struct_.rs @@ -18,7 +18,7 @@ impl PyStructDType { /// Returns the names of the struct fields. pub fn names(self_: PyRef<'_, Self>) -> PyResult> { let DType::Struct(dtype, _) = self_.as_ref().deref() else { - vortex_panic!(MismatchedTypes: "Not a struct DType"); + vortex_panic!("Not a struct DType"); }; Ok(dtype.names().iter().map(|name| name.to_string()).collect()) @@ -27,7 +27,7 @@ impl PyStructDType { /// Returns the field DTypes of the struct. pub fn fields(self_: PyRef<'_, Self>) -> PyResult>> { let DType::Struct(dtype, _) = self_.as_ref().deref() else { - vortex_panic!(MismatchedTypes: "Not a struct DType"); + vortex_panic!("Not a struct DType"); }; let mut fields = Vec::with_capacity(dtype.names().len()); diff --git a/vortex-python/src/error.rs b/vortex-python/src/error.rs index f7957259203..d419892d047 100644 --- a/vortex-python/src/error.rs +++ b/vortex-python/src/error.rs @@ -3,17 +3,8 @@ use pyo3::CastError; use pyo3::PyErr; -use pyo3::exceptions::PyAssertionError; -use pyo3::exceptions::PyIndexError; -use pyo3::exceptions::PyKeyError; -use pyo3::exceptions::PyNotImplementedError; -use pyo3::exceptions::PyOSError; -use pyo3::exceptions::PyOverflowError; use pyo3::exceptions::PyRuntimeError; -use pyo3::exceptions::PyTypeError; -use pyo3::exceptions::PyValueError; use vortex::error::VortexError; -use vortex::error::VortexErrorKind; /// Error type to merge [`VortexError`] and [`PyErr`]. pub enum PyVortexError { @@ -46,24 +37,7 @@ impl From for PyErr { fn from(value: PyVortexError) -> Self { match value { PyVortexError::Py(py) => py, - PyVortexError::Vortex(vx) => vortex_to_py_err(vx), + PyVortexError::Vortex(vx) => PyRuntimeError::new_err(vx.to_string()), } } } - -/// Raises a [`VortexError`] as the Python exception its kind is the analogue of. -fn vortex_to_py_err(error: VortexError) -> PyErr { - let message = error.to_string(); - match error.kind() { - VortexErrorKind::OutOfBounds => PyIndexError::new_err(message), - VortexErrorKind::NotFound => PyKeyError::new_err(message), - VortexErrorKind::Overflow => PyOverflowError::new_err(message), - VortexErrorKind::InvalidArgument | VortexErrorKind::Serde => PyValueError::new_err(message), - VortexErrorKind::NotImplemented => PyNotImplementedError::new_err(message), - VortexErrorKind::MismatchedTypes => PyTypeError::new_err(message), - VortexErrorKind::AssertionFailed => PyAssertionError::new_err(message), - VortexErrorKind::Io => PyOSError::new_err(message), - // `Other`, and any kind added after this binding was written. - _ => PyRuntimeError::new_err(message), - } -} diff --git a/vortex-python/src/iter/python.rs b/vortex-python/src/iter/python.rs index 2f99ad49883..10d061ff0b8 100644 --- a/vortex-python/src/iter/python.rs +++ b/vortex-python/src/iter/python.rs @@ -52,7 +52,7 @@ impl Iterator for PythonArrayIterator { Ok(array) } }) - .map_err(|pyerr| vortex_err!(Other: "{}", pyerr)) + .map_err(|pyerr| vortex_err!("{}", pyerr)) }) }) } diff --git a/vortex-python/src/object_store/resolve.rs b/vortex-python/src/object_store/resolve.rs index f45e2281b1e..ab392c1a038 100644 --- a/vortex-python/src/object_store/resolve.rs +++ b/vortex-python/src/object_store/resolve.rs @@ -37,9 +37,9 @@ pub(crate) fn resolve_store( None => { match Url::parse(url_or_path) { Ok(url) if url.scheme() == "file" => { - let path = url.to_file_path().map_err( - |_| vortex_err!(InvalidArgument: "invalid file URL: {url_or_path}"), - )?; + let path = url + .to_file_path() + .map_err(|_| vortex_err!("invalid file URL: {url_or_path}"))?; Ok(ResolvedStore::Path(path)) } // `Url::parse` accepts a Windows absolute path like `C:\data` as a URL whose diff --git a/vortex-python/src/python_repr.rs b/vortex-python/src/python_repr.rs index 5fcbba58f19..ebddf6f3f89 100644 --- a/vortex-python/src/python_repr.rs +++ b/vortex-python/src/python_repr.rs @@ -92,7 +92,7 @@ impl Display for DTypePythonRepr<'_> { .join(", "), n.python_repr() ), - DType::Union(..) => vortex_panic!(NotImplemented: "TODO(connor)[Union]: unimplemented"), + DType::Union(..) => vortex_panic!("TODO(connor)[Union]: unimplemented"), DType::Variant(_) => write!(f, "variant()"), DType::Extension(ext) => { write!( diff --git a/vortex-python/src/readable.rs b/vortex-python/src/readable.rs index f6dbbf187fe..e8d78e54c1c 100644 --- a/vortex-python/src/readable.rs +++ b/vortex-python/src/readable.rs @@ -202,9 +202,9 @@ impl VortexReadAt for PyReadable { // Reject an invalid range before it waits for a permit or occupies a blocking thread. let end = offset .checked_add(length as u64) - .ok_or_else(|| vortex_err!(Overflow: "read {offset}+{length} overflows u64"))?; + .ok_or_else(|| vortex_err!("read {offset}+{length} overflows u64"))?; if end > len { - vortex_bail!(OutOfBounds: "read {offset}..{end} out of bounds for file of length {len}"); + vortex_bail!("read {offset}..{end} out of bounds for file of length {len}"); } // Take a permit before occupying a blocking thread. For file objects the single permit @@ -228,7 +228,7 @@ impl VortexReadAt for PyReadable { read_fully(py, obj, protocol, offset, buffer).map(|b| b.freeze()) } } - .map_err(|err| vortex_err!(Io: "Python read of {offset}..{end} failed: {err}")) + .map_err(|err| vortex_err!("Python read of {offset}..{end} failed: {err}")) })?; Ok(BufferHandle::new_host(buffer)) }) diff --git a/vortex-python/src/scalar/into_py.rs b/vortex-python/src/scalar/into_py.rs index 489c0da9913..5c98dd9e022 100644 --- a/vortex-python/src/scalar/into_py.rs +++ b/vortex-python/src/scalar/into_py.rs @@ -129,7 +129,7 @@ impl<'py> IntoPyObject<'py> for PyVortex> { let dict = PyDict::new(py); for (child, name) in fields.zip(self.0.names().iter()) { dict.set_item(name.to_string(), PyVortex(&child).into_pyobject(py)?) - .map_err(|e| vortex_err!(Other: "Failed to set item in dictionary {}", e)) + .map_err(|e| vortex_err!("Failed to set item in dictionary {}", e)) .vortex_expect("Failed to set item in dictionary"); } Ok(dict.into_pyobject(py)?.into_any()) diff --git a/vortex-python/src/scalar/struct_.rs b/vortex-python/src/scalar/struct_.rs index 7ddd83227e8..bdcfd65ecb9 100644 --- a/vortex-python/src/scalar/struct_.rs +++ b/vortex-python/src/scalar/struct_.rs @@ -31,7 +31,7 @@ impl PyStructScalar { let scalar = self_.as_scalar_ref(); let child = scalar .field(name) - .ok_or_else(|| vortex_err!(NotFound: "No field {name}"))?; + .ok_or_else(|| vortex_err!("No field {name}"))?; Ok(PyVortex(&child) .into_pyobject(self_.py()) .map(|v| v.into())?) diff --git a/vortex-python/test/test_file_arrow_indices.py b/vortex-python/test/test_file_arrow_indices.py index c9e2222e134..d911c2e6933 100644 --- a/vortex-python/test/test_file_arrow_indices.py +++ b/vortex-python/test/test_file_arrow_indices.py @@ -75,7 +75,7 @@ def test_arrow_indices_apply_filter_then_limit(indexed_file): def test_arrow_indices_use_scan_validation(indexed_file, indices): file, _ = indexed_file indices = vx.array(pa.array(indices, type=pa.uint64())) - with pytest.raises(ValueError): + with pytest.raises(RuntimeError): file.to_arrow(indices=indices) diff --git a/vortex-row/src/codec.rs b/vortex-row/src/codec.rs index 9b2e2cc8bc1..9b621200d48 100644 --- a/vortex-row/src/codec.rs +++ b/vortex-row/src/codec.rs @@ -241,12 +241,12 @@ pub(crate) fn row_width_for_dtype(dtype: &DType) -> VortexResult { // FSL is fixed iff its element type is fixed. Add a sentinel byte for the FSL // itself, then `n` copies of the element width. RowWidth::Fixed(w) => { - let body = w.checked_mul(*n).ok_or_else( - || vortex_error::vortex_err!(Overflow: "FSL row width overflows u32"), - )?; - let total = body.checked_add(1).ok_or_else( - || vortex_error::vortex_err!(Overflow: "FSL row width overflows u32"), - )?; + let body = w + .checked_mul(*n) + .ok_or_else(|| vortex_error::vortex_err!("FSL row width overflows u32"))?; + let total = body + .checked_add(1) + .ok_or_else(|| vortex_error::vortex_err!("FSL row width overflows u32"))?; Ok(RowWidth::Fixed(total)) } RowWidth::Variable => Ok(RowWidth::Variable), @@ -258,7 +258,7 @@ pub(crate) fn row_width_for_dtype(dtype: &DType) -> VortexResult { match row_width_for_dtype(&field_dtype)? { RowWidth::Fixed(w) => { total = total.checked_add(w).ok_or_else(|| { - vortex_error::vortex_err!(Overflow: "Struct row width overflows u32") + vortex_error::vortex_err!("Struct row width overflows u32") })?; } RowWidth::Variable => return Ok(RowWidth::Variable), @@ -271,12 +271,12 @@ pub(crate) fn row_width_for_dtype(dtype: &DType) -> VortexResult { Ok(RowWidth::Variable) } DType::Variant(_) => { - vortex_bail!(InvalidArgument: "row encoding does not support Variant arrays (no well-defined ordering)") + vortex_bail!("row encoding does not support Variant arrays (no well-defined ordering)") } DType::Union(..) => { - vortex_bail!(InvalidArgument: "row encoding does not support Union arrays") + vortex_bail!("row encoding does not support Union arrays") } - dtype => vortex_bail!(InvalidArgument: "row encoding does not support dtype: {dtype:?}"), + dtype => vortex_bail!("row encoding does not support dtype: {dtype:?}"), } } @@ -305,11 +305,11 @@ pub(crate) fn field_size( Canonical::List(arr) => add_size_list(arr, field, sizes, ctx)?, Canonical::Map(arr) => add_size_map(arr, field, sizes, ctx)?, Canonical::Variant(_) => { - vortex_bail!(InvalidArgument: "row encoding does not support Variant arrays (no well-defined ordering)") + vortex_bail!("row encoding does not support Variant arrays (no well-defined ordering)") } unsupported => { vortex_bail!( - InvalidArgument: "row encoding does not support canonical array: {:?}", + "row encoding does not support canonical array: {:?}", unsupported.dtype() ) } @@ -416,11 +416,11 @@ pub(crate) fn field_encode( Canonical::List(arr) => encode_list(arr, field, offsets, cursors, out, ctx)?, Canonical::Map(arr) => encode_map(arr, field, offsets, cursors, out, ctx)?, Canonical::Variant(_) => { - vortex_bail!(InvalidArgument: "row encoding does not support Variant arrays (no well-defined ordering)") + vortex_bail!("row encoding does not support Variant arrays (no well-defined ordering)") } unsupported => { vortex_bail!( - InvalidArgument: "row encoding does not support canonical array: {:?}", + "row encoding does not support canonical array: {:?}", unsupported.dtype() ) } @@ -524,9 +524,9 @@ fn prepare_list( let mut total = 0u32; for &size in &element_sizes { element_offsets.push(total); - total = total.checked_add(size).ok_or_else( - || vortex_error::vortex_err!(Overflow: "list element bytes overflow u32"), - )?; + total = total + .checked_add(size) + .ok_or_else(|| vortex_error::vortex_err!("list element bytes overflow u32"))?; } Ok(PreparedList { mask, @@ -547,18 +547,17 @@ fn add_size_prepared_list(prepared: &PreparedList, sizes: &mut [u32]) -> VortexR let body = prepared.element_sizes[offset..offset + len] .iter() .try_fold(0u32, |sum, &size| sum.checked_add(size)) - .ok_or_else( - || vortex_error::vortex_err!(Overflow: "list element sizes overflow u32"), - )?; - body.checked_add(u32::try_from(len).map_err( - |_| vortex_error::vortex_err!(Overflow: "list element count overflows u32"), - )?) + .ok_or_else(|| vortex_error::vortex_err!("list element sizes overflow u32"))?; + body.checked_add( + u32::try_from(len) + .map_err(|_| vortex_error::vortex_err!("list element count overflows u32"))?, + ) .and_then(|size| size.checked_add(2)) - .ok_or_else(|| vortex_error::vortex_err!(Overflow: "list row size overflows u32"))? + .ok_or_else(|| vortex_error::vortex_err!("list row size overflows u32"))? }; sizes[i] = sizes[i] .checked_add(contribution) - .ok_or_else(|| vortex_error::vortex_err!(Overflow: "per-row size overflow"))?; + .ok_or_else(|| vortex_error::vortex_err!("per-row size overflow"))?; } Ok(()) } diff --git a/vortex-row/src/encode.rs b/vortex-row/src/encode.rs index 9bcf48eb287..c88f164c10a 100644 --- a/vortex-row/src/encode.rs +++ b/vortex-row/src/encode.rs @@ -106,7 +106,7 @@ fn execute_row_encode( ) -> VortexResult { let nrows = args.row_count(); if u32::try_from(nrows).is_err() { - vortex_bail!(Overflow: "row-encoded input has {} rows, exceeds u32::MAX", nrows); + vortex_bail!("row-encoded input has {} rows, exceeds u32::MAX", nrows); } // ===== Phase 1: classify + size pass ===== @@ -126,10 +126,10 @@ fn execute_row_encode( .checked_mul(u64::from(fixed_per_row)) .and_then(|t| t.checked_add(var_total)) .ok_or_else(|| { - vortex_error::vortex_err!(Overflow: "row-encoded total bytes overflow u64 (nrows * fixed + var)") + vortex_error::vortex_err!("row-encoded total bytes overflow u64 (nrows * fixed + var)") })?; if total > u32::MAX as u64 { - vortex_bail!(Overflow: "row-encoded output size {} bytes exceeds u32::MAX", total); + vortex_bail!("row-encoded output size {} bytes exceeds u32::MAX", total); } let total_len = usize::try_from(total).vortex_expect("validated row-encoded output size must fit usize"); diff --git a/vortex-row/src/encoder.rs b/vortex-row/src/encoder.rs index 1f24526d091..1346d8ffc7e 100644 --- a/vortex-row/src/encoder.rs +++ b/vortex-row/src/encoder.rs @@ -93,13 +93,13 @@ impl RowEncoder { /// [`encode`](Self::encode) and [`row_sizes`](Self::row_sizes). fn prepare(&self, cols: &[ArrayRef]) -> VortexResult<(RowEncodingOptions, VecExecutionArgs)> { if cols.is_empty() { - vortex_bail!(InvalidArgument: "RowEncoder: at least one column is required"); + vortex_bail!("RowEncoder: at least one column is required"); } let options = match &self.options { Some(options) => { if options.len() != cols.len() { vortex_bail!( - InvalidArgument: "RowEncoder: options describe {} columns but {} were provided", + "RowEncoder: options describe {} columns but {} were provided", options.len(), cols.len() ); @@ -113,7 +113,7 @@ impl RowEncoder { reject_extension_dtype(col.dtype())?; if col.len() != nrows { vortex_bail!( - InvalidArgument: "RowEncoder: column {} has length {} but expected {}", + "RowEncoder: column {} has length {} but expected {}", i, col.len(), nrows @@ -128,7 +128,7 @@ fn reject_extension_dtype(dtype: &DType) -> VortexResult<()> { match dtype { DType::Extension(ext_dtype) => { vortex_bail!( - InvalidArgument: "row encoding does not support Extension arrays yet: {}", + "row encoding does not support Extension arrays yet: {}", ext_dtype.id() ) } diff --git a/vortex-row/src/options.rs b/vortex-row/src/options.rs index eaf744c2c2a..380c9a3827f 100644 --- a/vortex-row/src/options.rs +++ b/vortex-row/src/options.rs @@ -168,14 +168,14 @@ pub(crate) fn deserialize_row_encoding_options( ) -> vortex_error::VortexResult { if bytes.len() < 4 { vortex_error::vortex_bail!( - Serde: "RowEncodingOptions metadata must contain a 4-byte length prefix" + "RowEncodingOptions metadata must contain a 4-byte length prefix" ); } let n = u32::from_le_bytes([bytes[0], bytes[1], bytes[2], bytes[3]]) as usize; let expected = 4 + 2 * n; if bytes.len() != expected { vortex_error::vortex_bail!( - InvalidArgument: "RowEncodingOptions metadata wrong size: got {}, expected {}", + "RowEncodingOptions metadata wrong size: got {}, expected {}", bytes.len(), expected ); diff --git a/vortex-row/src/size.rs b/vortex-row/src/size.rs index d7607821bd7..d475d3e6412 100644 --- a/vortex-row/src/size.rs +++ b/vortex-row/src/size.rs @@ -84,11 +84,11 @@ pub(crate) fn compute_sizes( ) -> VortexResult { let n_inputs = args.num_inputs(); if n_inputs == 0 { - vortex_bail!(InvalidArgument: "at least one input column is required"); + vortex_bail!("at least one input column is required"); } if options.len() != n_inputs { vortex_bail!( - MismatchedTypes: "options len ({}) does not match num_inputs ({})", + "options len ({}) does not match num_inputs ({})", options.len(), n_inputs ); @@ -106,7 +106,7 @@ pub(crate) fn compute_sizes( let col = args.get(i)?; if col.len() != nrows { vortex_bail!( - InvalidArgument: "column {} has length {} but expected {}", + "column {} has length {} but expected {}", i, col.len(), nrows @@ -121,7 +121,8 @@ pub(crate) fn compute_sizes( prefix: running_fixed_prefix, before_varlen: first_varlen_idx.is_none(), }); - let overflow = || vortex_error::vortex_err!(Overflow: "per-row fixed width overflows u32 at column {i}"); + let overflow = + || vortex_error::vortex_err!("per-row fixed width overflows u32 at column {i}"); fixed_per_row = fixed_per_row.checked_add(w).ok_or_else(overflow)?; running_fixed_prefix = running_fixed_prefix.checked_add(w).ok_or_else(overflow)?; columns.push(PreparedField::Canonical(canonical)); diff --git a/vortex-scan/src/lib.rs b/vortex-scan/src/lib.rs index 1e9bb1dd57c..a15b49d4a67 100644 --- a/vortex-scan/src/lib.rs +++ b/vortex-scan/src/lib.rs @@ -113,7 +113,7 @@ pub trait DataSource: 'static + Send + Sync { session: &VortexSession, ) -> VortexResult { let _ = (data, session); - vortex_bail!(Serde: "DataSource does not support deserialization") + vortex_bail!("DataSource does not support deserialization") } /// Returns a scan over the source. diff --git a/vortex-scan/src/planning/driver/mod.rs b/vortex-scan/src/planning/driver/mod.rs index 620f4494178..8cb78099272 100644 --- a/vortex-scan/src/planning/driver/mod.rs +++ b/vortex-scan/src/planning/driver/mod.rs @@ -131,12 +131,12 @@ impl Work { fn deliver(&mut self, request: IoRequestId, result: IoResult) -> VortexResult<()> { let Some(target) = self.outstanding.remove(&request) else { vortex_bail!( - AssertionFailed: "completion for {request:?} of {:?}, which is not outstanding", + "completion for {request:?} of {:?}, which is not outstanding", self.id ); }; if !result.matches(&target) { - vortex_bail!(AssertionFailed: "IO source answered {target:?} with {}", result.kind()); + vortex_bail!("IO source answered {target:?} with {}", result.kind()); } self.consumer().set_io_result(request, result); Ok(()) @@ -279,7 +279,7 @@ impl Run { if let Some(limit) = self.step_limit && self.steps > limit { - vortex_bail!(AssertionFailed: "driver exceeded its step limit of {limit}"); + vortex_bail!("driver exceeded its step limit of {limit}"); } self.visit(work)?; } @@ -302,7 +302,7 @@ impl Run { self.queue.insert(work); } else if work.outstanding.is_empty() { vortex_bail!( - AssertionFailed: "work for scope {:?} waits with no outstanding fetch", + "work for scope {:?} waits with no outstanding fetch", work.scope ); } @@ -310,7 +310,7 @@ impl Run { } // An item that published fetches and had CPU work left is still in the run queue. let Some(work) = self.queue.work.get_mut(&owner) else { - vortex_bail!(AssertionFailed: "completion for unknown work {owner:?}"); + vortex_bail!("completion for unknown work {owner:?}"); }; work.deliver(request, result) } @@ -327,7 +327,7 @@ impl Run { .collect(); if sources.is_empty() { return Poll::Ready(Err(vortex_err!( - AssertionFailed: "the run is waiting for IO with no live root" + "the run is waiting for IO with no live root" ))); } let mut delivered = false; @@ -410,7 +410,7 @@ impl Run { fn park(&mut self, work: Box) -> VortexResult<()> { if work.outstanding.is_empty() { vortex_bail!( - AssertionFailed: "work for scope {:?} waits with no outstanding fetch", + "work for scope {:?} waits with no outstanding fetch", work.scope ); } @@ -464,7 +464,7 @@ impl Run { } Output::Morsel(MorselOutput::Batch(array)) => { if array.is_empty() { - vortex_bail!(AssertionFailed: "morsel for scope {:?} returned an empty batch", work.scope); + vortex_bail!("morsel for scope {:?} returned an empty batch", work.scope); } self.events.push_back(Progress::Batch(Batch { root: work.root, @@ -480,7 +480,7 @@ impl Run { /// Registers the requests an item published with its root's session. fn submit(&mut self, work: &mut Work, batch: IoBatch) -> VortexResult<()> { if batch.is_empty() { - vortex_bail!(AssertionFailed: "compute() published an empty batch"); + vortex_bail!("compute() published an empty batch"); } for request in &batch { if request.intent == IoIntent::Fetch @@ -490,14 +490,14 @@ impl Run { .is_some() { vortex_bail!( - AssertionFailed: "fetch {:?} of {:?} was published while it is outstanding", + "fetch {:?} of {:?} was published while it is outstanding", request.request, work.id ); } } let Some(root) = self.roots.get(&work.root) else { - vortex_bail!(AssertionFailed: "work {:?} outlived its root {:?}", work.id, work.root); + vortex_bail!("work {:?} outlived its root {:?}", work.id, work.root); }; root.io.submit(work.id, batch) } diff --git a/vortex-scan/src/planning/next.rs b/vortex-scan/src/planning/next.rs index 119aef7fc81..49d500593ad 100644 --- a/vortex-scan/src/planning/next.rs +++ b/vortex-scan/src/planning/next.rs @@ -62,7 +62,7 @@ mod tests { #[test] fn next_fn_reports_constructor_errors() { let next: Next = next_fn(|input: u32| -> VortexResult { - vortex_bail!(InvalidArgument: "constructor rejected {input}") + vortex_bail!("constructor rejected {input}") }); let err = next(7).err().map(|e| e.to_string()); assert!( diff --git a/vortex-scan/src/planning/tests/scripted.rs b/vortex-scan/src/planning/tests/scripted.rs index 083db3c0385..5573dafa7df 100644 --- a/vortex-scan/src/planning/tests/scripted.rs +++ b/vortex-scan/src/planning/tests/scripted.rs @@ -361,10 +361,8 @@ impl IoSource for RecordingIoSource { Ok(IoResult::Bytes(BufferHandle::new_host(bytes.clone()))) } Some(Canned::Size(size)) => Ok(IoResult::Size(*size)), - Some(Canned::Fail(message)) => Err(vortex_err!(Io: "{message}")), - None => { - Err(vortex_err!(AssertionFailed: "no canned answer for {:?}", request.target)) - } + Some(Canned::Fail(message)) => Err(vortex_err!("{message}")), + None => Err(vortex_err!("no canned answer for {:?}", request.target)), }; self.ready.lock().push(Completion { owner: work, @@ -401,9 +399,7 @@ impl IoSource for RecordingIoSource { Order::Fifo => None, Order::Lifo => ready.pop(), }; - completion.ok_or_else( - || vortex_err!(AssertionFailed: "RecordingIoSource: wait with nothing outstanding"), - ) + completion.ok_or_else(|| vortex_err!("RecordingIoSource: wait with nothing outstanding")) } } diff --git a/vortex-scan/src/selection.rs b/vortex-scan/src/selection.rs index f830fc8841a..3df51aaccab 100644 --- a/vortex-scan/src/selection.rs +++ b/vortex-scan/src/selection.rs @@ -147,7 +147,7 @@ fn relativize(range: &Range, idx: u64) -> usize { .and_then(|relative| usize::try_from(relative).ok()) .unwrap_or_else(|| { vortex_panic!( - Overflow: "index {:?} is not a usize offset into range {:?}", + "index {:?} is not a usize offset into range {:?}", idx, range ) diff --git a/vortex-scan/src/strict_sorted_buffer.rs b/vortex-scan/src/strict_sorted_buffer.rs index f4da7eac651..d508345cdd8 100644 --- a/vortex-scan/src/strict_sorted_buffer.rs +++ b/vortex-scan/src/strict_sorted_buffer.rs @@ -40,7 +40,7 @@ impl StrictSortedBuffer { for (idx, window) in buffer.windows(2).enumerate() { if window[0] >= window[1] { vortex_bail!( - InvalidArgument: "buffer values must be strictly increasing at positions {} and {}", + "buffer values must be strictly increasing at positions {} and {}", idx, idx + 1 ); diff --git a/vortex-session/src/session.rs b/vortex-session/src/session.rs index 572035cecd0..0103a95eb52 100644 --- a/vortex-session/src/session.rs +++ b/vortex-session/src/session.rs @@ -222,7 +222,7 @@ impl VortexSession { pub fn with_some(self, var: V) -> Self { if self.get_opt::().is_some() { vortex_panic!( - InvalidArgument: "Session variable of type {} already exists", + "Session variable of type {} already exists", type_name::() ); } diff --git a/vortex-spatial/src/aggregate_fn/aabb.rs b/vortex-spatial/src/aggregate_fn/aabb.rs index d767f64e820..3ef24a619a7 100644 --- a/vortex-spatial/src/aggregate_fn/aabb.rs +++ b/vortex-spatial/src/aggregate_fn/aabb.rs @@ -97,7 +97,7 @@ fn rect_from_storage(scalar: &Scalar) -> VortexResult>> f64::try_from( &fields .field(name) - .ok_or_else(|| vortex_err!(NotFound: "AABB missing {name}"))?, + .ok_or_else(|| vortex_err!("AABB missing {name}"))?, ) }; Ok(Some(SpatialRect::new( diff --git a/vortex-spatial/src/extension/coordinate.rs b/vortex-spatial/src/extension/coordinate.rs index 71a093be803..fd20e3bb619 100644 --- a/vortex-spatial/src/extension/coordinate.rs +++ b/vortex-spatial/src/extension/coordinate.rs @@ -49,7 +49,7 @@ impl Dimension { let mut strs = [""; 4]; vortex_ensure!( names.len() <= strs.len(), - InvalidArgument: "not a valid GeoArrow coordinate dimension: {names:?}" + "not a valid GeoArrow coordinate dimension: {names:?}" ); for (slot, name) in strs.iter_mut().zip(names.iter()) { *slot = name.as_ref(); @@ -60,7 +60,7 @@ impl Dimension { ["x", "y", "m"] => Dimension::Xym, ["x", "y", "z", "m"] => Dimension::Xyzm, _ => { - vortex_bail!(InvalidArgument: "not a valid GeoArrow coordinate dimension: {names:?}") + vortex_bail!("not a valid GeoArrow coordinate dimension: {names:?}") } }) } @@ -156,7 +156,7 @@ impl Display for Coordinate { /// [`Dimension`]. Any of the four GeoArrow dimensions validates. pub(crate) fn coordinate_dimension(dtype: &DType) -> VortexResult { let DType::Struct(fields, _) = dtype else { - vortex_bail!(MismatchedTypes: "coordinate storage must be a Struct, was {dtype}"); + vortex_bail!("coordinate storage must be a Struct, was {dtype}"); }; for (name, field) in fields.names().iter().zip(fields.fields()) { vortex_ensure!( @@ -164,7 +164,7 @@ pub(crate) fn coordinate_dimension(dtype: &DType) -> VortexResult { field, DType::Primitive(PType::F64, Nullability::NonNullable) ), - MismatchedTypes: "coordinate field {name} must be non-nullable f64, was {field}" + "coordinate field {name} must be non-nullable f64, was {field}" ); } Dimension::from_field_names(fields.names()) @@ -193,7 +193,7 @@ pub(crate) fn coordinate_from_struct(scalar: &Scalar) -> VortexResult VortexResult> { diff --git a/vortex-spatial/src/extension/linestring.rs b/vortex-spatial/src/extension/linestring.rs index 9a744d11b2f..0fcd508a63d 100644 --- a/vortex-spatial/src/extension/linestring.rs +++ b/vortex-spatial/src/extension/linestring.rs @@ -107,7 +107,7 @@ pub(crate) fn linestring_storage_dtype(dim: Dimension, nullability: Nullability) /// Validate `dtype` is `List` and return its [`Dimension`]. pub(crate) fn linestring_dimension(dtype: &DType) -> VortexResult { let DType::List(coords, _) = dtype else { - vortex_bail!(MismatchedTypes: "linestring storage must be a List of coordinates, was {dtype}"); + vortex_bail!("linestring storage must be a List of coordinates, was {dtype}"); }; coordinate_dimension(coords) } @@ -136,15 +136,15 @@ pub(crate) fn linestring_array_from_point_pairs( vortex_ensure_eq!( len, ends.len(), - InvalidArgument: "spatial: line string point columns must have equal lengths" + "spatial: line string point columns must have equal lengths" ); let vertex_count = len .checked_mul(2) - .ok_or_else(|| vortex_err!(Overflow: "spatial: two-vertex line string length overflow"))?; + .ok_or_else(|| vortex_err!("spatial: two-vertex line string length overflow"))?; let last_offset = i32::try_from(vertex_count) - .map_err(|_| vortex_err!(Overflow: "spatial: two-vertex line string offset overflow"))?; + .map_err(|_| vortex_err!("spatial: two-vertex line string offset overflow"))?; let row_count = u32::try_from(len) - .map_err(|_| vortex_err!(Overflow: "spatial: two-vertex line string row count overflow"))?; + .map_err(|_| vortex_err!("spatial: two-vertex line string row count overflow"))?; let dimension = linestring_dimension(ext_dtype.storage_dtype())?; let start_dimension = coordinate_dimension(starts.dtype())?; let end_dimension = coordinate_dimension(ends.dtype())?; @@ -202,10 +202,8 @@ pub(crate) fn linestring_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else( - || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), - )? - .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? + .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? + .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -220,7 +218,7 @@ fn linestring_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult< let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; LineStringArray::try_from((arrow.as_ref(), linestring_type)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct LineStringArray: {e}")) + .map_err(|e| vortex_err!("failed to construct LineStringArray: {e}")) } /// A validated `LineString` array (`try_from` checks the extension type). @@ -232,7 +230,7 @@ impl TryFrom for LineStringData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - MismatchedTypes: "expected a LineString extension array" + "expected a LineString extension array" ); Ok(LineStringData(ext)) } @@ -313,9 +311,7 @@ impl ArrowExportVTable for LineString { // Round-trip through GeoArrow's line-string array; `into_arrow` is concrete, so wrap in `Arc`. let linestrings = LineStringArray::try_from((arrow_storage.as_ref(), linestring_meta)) - .map_err( - |e| vortex_err!(InvalidArgument: "failed to construct LineStringArray: {e}"), - )?; + .map_err(|e| vortex_err!("failed to construct LineStringArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new(linestrings.into_arrow()))) } @@ -335,37 +331,36 @@ impl ArrowImportVTable for LineString { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = if let Ok(linestring_meta) = - field.try_extension_type::() - { - vortex_ensure!( - linestring_meta.coord_type() == CoordType::Separated, - NotImplemented: "geoarrow.linestring with interleaved coordinates is not supported; \ + let (dimension, metadata) = + if let Ok(linestring_meta) = field.try_extension_type::() { + vortex_ensure!( + linestring_meta.coord_type() == CoordType::Separated, + "geoarrow.linestring with interleaved coordinates is not supported; \ re-encode with separated (struct) coordinates" - ); - ( - linestring_meta.dimension().into(), - spatial_metadata_from_arrow(linestring_meta.metadata()), - ) - } else { - // Literal: peel the `List` layer to the coordinate struct and read its dimension from - // the field names (the canonical check rejects nullable coordinates). - if field.extension_type_name() != Some(LineStringType::NAME) { - return Ok(None); - } - let Ok(DType::List(coords, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); + ); + ( + linestring_meta.dimension().into(), + spatial_metadata_from_arrow(linestring_meta.metadata()), + ) + } else { + // Literal: peel the `List` layer to the coordinate struct and read its dimension from + // the field names (the canonical check rejects nullable coordinates). + if field.extension_type_name() != Some(LineStringType::NAME) { + return Ok(None); + } + let Ok(DType::List(coords, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) - }; let storage_dtype = linestring_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/mod.rs b/vortex-spatial/src/extension/mod.rs index 8227dd80d3c..047109bcec8 100644 --- a/vortex-spatial/src/extension/mod.rs +++ b/vortex-spatial/src/extension/mod.rs @@ -88,7 +88,7 @@ pub(crate) fn flatten_coordinates( ) -> VortexResult { if !is_native_geometry(array.dtype()) { vortex_bail!( - MismatchedTypes: "spatial: operand is not a native geometry extension type, was {}", + "spatial: operand is not a native geometry extension type, was {}", array.dtype() ); } @@ -139,7 +139,7 @@ pub(crate) fn flatten_row_offsets( .execute::>(ctx)?; for row_offset in &mut row_offsets { *row_offset = usize::try_from(offsets[*row_offset]) - .map_err(|_| vortex_err!(Overflow: "spatial: list offset exceeds usize"))?; + .map_err(|_| vortex_err!("spatial: list offset exceeds usize"))?; } level = list.elements().clone(); } @@ -153,7 +153,7 @@ pub(crate) fn geometries( ) -> VortexResult>> { let Some(ext) = array.dtype().as_extension_opt() else { vortex_bail!( - MismatchedTypes: "spatial: operand is not a geometry extension type, was {}", + "spatial: operand is not a geometry extension type, was {}", array.dtype() ); }; @@ -177,7 +177,7 @@ pub(crate) fn geometries( } else if ext.is::() { rect_geometries(&storage, ctx) } else { - vortex_bail!(InvalidArgument: "spatial: unsupported geometry extension {}", array.dtype()) + vortex_bail!("spatial: unsupported geometry extension {}", array.dtype()) } } @@ -188,9 +188,9 @@ pub(crate) fn single_geometry( ctx: &mut ExecutionCtx, ) -> VortexResult> { let array = ConstantArray::new(scalar.clone(), 1).into_array(); - geometries(&array, ctx)?.pop().ok_or_else( - || vortex_err!(AssertionFailed: "spatial: constant operand decoded to no geometry"), - ) + geometries(&array, ctx)? + .pop() + .ok_or_else(|| vortex_err!("spatial: constant operand decoded to no geometry")) } /// Decode a WKB geometry literal (DuckDB's wire form for `GEOMETRY` constants) to its native @@ -205,12 +205,12 @@ pub fn native_geometry_scalar_from_wkb( &binary as &dyn arrow_array::Array, WkbType::new(Arc::clone(&metadata)), )) - .map_err(|e| vortex_err!(Io: "failed to read WKB literal: {e}"))?; + .map_err(|e| vortex_err!("failed to read WKB literal: {e}"))?; // Cast the WKB value to `target`, import its native storage as a Vortex array. let to_storage = |target: &GeoArrowType| -> VortexResult { - let native = cast(&wkb, target) - .map_err(|e| vortex_err!(Serde: "failed to cast WKB literal: {e}"))?; + let native = + cast(&wkb, target).map_err(|e| vortex_err!("failed to cast WKB literal: {e}"))?; session .arrow() .from_arrow_array(native.to_array_ref(), false) @@ -315,7 +315,7 @@ pub(crate) fn geoarrow_to_wkb( let wkb_type = GeoArrowType::WkbView(WkbType::new(geoarrow_metadata(&SpatialMetadata::default()))); let wkb = cast(geoarrow_array, &wkb_type) - .map_err(|e| vortex_err!(Serde: "failed to cast geometry to WKB: {e}"))?; + .map_err(|e| vortex_err!("failed to cast geometry to WKB: {e}"))?; session.from_arrow_array(wkb.to_array_ref(), false) } @@ -404,7 +404,7 @@ mod tests { let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&3u32.to_le_bytes()); // geometry type: polygon wkb.extend_from_slice(&1u32.to_le_bytes()); // one ring - let ring_len = u32::try_from(ring.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; + let ring_len = u32::try_from(ring.len()).map_err(|e| vortex_err!("{e}"))?; wkb.extend_from_slice(&ring_len.to_le_bytes()); for (x, y) in ring { wkb.extend_from_slice(&f64::to_le_bytes(x)); @@ -438,7 +438,7 @@ mod tests { let points = [(0.0, 0.0), (1.0, 1.0)]; let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&2u32.to_le_bytes()); // geometry type: linestring - let len = u32::try_from(points.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; + let len = u32::try_from(points.len()).map_err(|e| vortex_err!("{e}"))?; wkb.extend_from_slice(&len.to_le_bytes()); for (x, y) in points { wkb.extend_from_slice(&f64::to_le_bytes(x)); @@ -467,7 +467,7 @@ mod tests { let points = [(0.0, 0.0), (1.0, 1.0)]; let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&4u32.to_le_bytes()); // geometry type: multipoint - let len = u32::try_from(points.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; + let len = u32::try_from(points.len()).map_err(|e| vortex_err!("{e}"))?; wkb.extend_from_slice(&len.to_le_bytes()); for (x, y) in points { // each member is a full WKB point @@ -499,13 +499,13 @@ mod tests { let lines = [[(0.0, 0.0), (1.0, 1.0)], [(2.0, 2.0), (3.0, 3.0)]]; let mut wkb = vec![1u8]; // little-endian byte order wkb.extend_from_slice(&5u32.to_le_bytes()); // geometry type: multilinestring - let num_lines = u32::try_from(lines.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; + let num_lines = u32::try_from(lines.len()).map_err(|e| vortex_err!("{e}"))?; wkb.extend_from_slice(&num_lines.to_le_bytes()); for line in lines { // each member is a full WKB linestring wkb.push(1u8); wkb.extend_from_slice(&2u32.to_le_bytes()); - let len = u32::try_from(line.len()).map_err(|e| vortex_err!(Overflow: "{e}"))?; + let len = u32::try_from(line.len()).map_err(|e| vortex_err!("{e}"))?; wkb.extend_from_slice(&len.to_le_bytes()); for (x, y) in line { wkb.extend_from_slice(&f64::to_le_bytes(x)); diff --git a/vortex-spatial/src/extension/multilinestring.rs b/vortex-spatial/src/extension/multilinestring.rs index c74fdcb5f4e..0443f615211 100644 --- a/vortex-spatial/src/extension/multilinestring.rs +++ b/vortex-spatial/src/extension/multilinestring.rs @@ -100,10 +100,10 @@ pub(crate) fn multilinestring_storage_dtype(dim: Dimension, nullability: Nullabi /// Validate `dtype` is `List>` and return its [`Dimension`]. pub(crate) fn multilinestring_dimension(dtype: &DType) -> VortexResult { let DType::List(line, _) = dtype else { - vortex_bail!(MismatchedTypes: "multilinestring storage must be a List of line strings, was {dtype}"); + vortex_bail!("multilinestring storage must be a List of line strings, was {dtype}"); }; let DType::List(coords, _) = line.as_ref() else { - vortex_bail!(MismatchedTypes: "multilinestring line storage must be a List of coordinates, was {line}"); + vortex_bail!("multilinestring line storage must be a List of coordinates, was {line}"); }; coordinate_dimension(coords) } @@ -127,10 +127,8 @@ pub(crate) fn multilinestring_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else( - || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), - )? - .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? + .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? + .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -148,7 +146,7 @@ fn multilinestring_array( let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; MultiLineStringArray::try_from((arrow.as_ref(), multilinestring_type)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct MultiLineStringArray: {e}")) + .map_err(|e| vortex_err!("failed to construct MultiLineStringArray: {e}")) } /// A validated `MultiLineString` array (`try_from` checks the extension type). @@ -160,7 +158,7 @@ impl TryFrom for MultiLineStringData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - MismatchedTypes: "expected a MultiLineString extension array" + "expected a MultiLineString extension array" ); Ok(MultiLineStringData(ext)) } @@ -239,13 +237,9 @@ impl ArrowExportVTable for MultiLineString { .exporter(options) .execute_arrow(storage, Some(&storage_field), ctx)?; - let multilinestrings = MultiLineStringArray::try_from(( - arrow_storage.as_ref(), - multilinestring_meta, - )) - .map_err( - |e| vortex_err!(InvalidArgument: "failed to construct MultiLineStringArray: {e}"), - )?; + let multilinestrings = + MultiLineStringArray::try_from((arrow_storage.as_ref(), multilinestring_meta)) + .map_err(|e| vortex_err!("failed to construct MultiLineStringArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new( multilinestrings.into_arrow(), @@ -265,40 +259,39 @@ impl ArrowImportVTable for MultiLineString { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = if let Ok(multilinestring_meta) = - field.try_extension_type::() - { - vortex_ensure!( - multilinestring_meta.coord_type() == CoordType::Separated, - NotImplemented: "geoarrow.multilinestring with interleaved coordinates is not supported; \ + let (dimension, metadata) = + if let Ok(multilinestring_meta) = field.try_extension_type::() { + vortex_ensure!( + multilinestring_meta.coord_type() == CoordType::Separated, + "geoarrow.multilinestring with interleaved coordinates is not supported; \ re-encode with separated (struct) coordinates" - ); - ( - multilinestring_meta.dimension().into(), - spatial_metadata_from_arrow(multilinestring_meta.metadata()), - ) - } else { - // Literal: peel the two `List` layers to the coordinate struct and read its dimension - // from the field names (the canonical check rejects nullable coordinates). - if field.extension_type_name() != Some(MultiLineStringType::NAME) { - return Ok(None); - } - let Ok(DType::List(line, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::List(coords, _) = line.as_ref() else { - return Ok(None); + ); + ( + multilinestring_meta.dimension().into(), + spatial_metadata_from_arrow(multilinestring_meta.metadata()), + ) + } else { + // Literal: peel the two `List` layers to the coordinate struct and read its dimension + // from the field names (the canonical check rejects nullable coordinates). + if field.extension_type_name() != Some(MultiLineStringType::NAME) { + return Ok(None); + } + let Ok(DType::List(line, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::List(coords, _) = line.as_ref() else { + return Ok(None); + }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) - }; let storage_dtype = multilinestring_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/multipoint.rs b/vortex-spatial/src/extension/multipoint.rs index 37aa5b51c2c..2f3f04662e4 100644 --- a/vortex-spatial/src/extension/multipoint.rs +++ b/vortex-spatial/src/extension/multipoint.rs @@ -97,7 +97,7 @@ pub(crate) fn multipoint_storage_dtype(dim: Dimension, nullability: Nullability) /// Validate `dtype` is `List` and return its [`Dimension`]. pub(crate) fn multipoint_dimension(dtype: &DType) -> VortexResult { let DType::List(coords, _) = dtype else { - vortex_bail!(MismatchedTypes: "multipoint storage must be a List of coordinates, was {dtype}"); + vortex_bail!("multipoint storage must be a List of coordinates, was {dtype}"); }; coordinate_dimension(coords) } @@ -118,10 +118,8 @@ pub(crate) fn multipoint_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else( - || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), - )? - .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? + .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? + .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -136,7 +134,7 @@ fn multipoint_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult< let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; MultiPointArray::try_from((arrow.as_ref(), multipoint_type)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct MultiPointArray: {e}")) + .map_err(|e| vortex_err!("failed to construct MultiPointArray: {e}")) } /// A validated `MultiPoint` array (`try_from` checks the extension type). @@ -148,7 +146,7 @@ impl TryFrom for MultiPointData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - MismatchedTypes: "expected a MultiPoint extension array" + "expected a MultiPoint extension array" ); Ok(MultiPointData(ext)) } @@ -229,9 +227,7 @@ impl ArrowExportVTable for MultiPoint { // Round-trip through GeoArrow's multipoint array; `into_arrow` is concrete, so wrap in `Arc`. let multipoints = MultiPointArray::try_from((arrow_storage.as_ref(), multipoint_meta)) - .map_err( - |e| vortex_err!(InvalidArgument: "failed to construct MultiPointArray: {e}"), - )?; + .map_err(|e| vortex_err!("failed to construct MultiPointArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new(multipoints.into_arrow()))) } @@ -250,35 +246,34 @@ impl ArrowImportVTable for MultiPoint { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = if let Ok(multipoint_meta) = - field.try_extension_type::() - { - vortex_ensure!( - multipoint_meta.coord_type() == CoordType::Separated, - NotImplemented: "geoarrow.multipoint with interleaved coordinates is not supported; \ + let (dimension, metadata) = + if let Ok(multipoint_meta) = field.try_extension_type::() { + vortex_ensure!( + multipoint_meta.coord_type() == CoordType::Separated, + "geoarrow.multipoint with interleaved coordinates is not supported; \ re-encode with separated (struct) coordinates" - ); - ( - multipoint_meta.dimension().into(), - spatial_metadata_from_arrow(multipoint_meta.metadata()), - ) - } else { - if field.extension_type_name() != Some(MultiPointType::NAME) { - return Ok(None); - } - let Ok(DType::List(coords, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); + ); + ( + multipoint_meta.dimension().into(), + spatial_metadata_from_arrow(multipoint_meta.metadata()), + ) + } else { + if field.extension_type_name() != Some(MultiPointType::NAME) { + return Ok(None); + } + let Ok(DType::List(coords, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) - }; let storage_dtype = multipoint_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/multipolygon.rs b/vortex-spatial/src/extension/multipolygon.rs index 909c9581410..c7e88c4b71b 100644 --- a/vortex-spatial/src/extension/multipolygon.rs +++ b/vortex-spatial/src/extension/multipolygon.rs @@ -98,13 +98,13 @@ pub(crate) fn multipolygon_storage_dtype(dim: Dimension, nullability: Nullabilit /// Validate `dtype` is `List>>` and return its [`Dimension`]. pub(crate) fn multipolygon_dimension(dtype: &DType) -> VortexResult { let DType::List(polygon, _) = dtype else { - vortex_bail!(MismatchedTypes: "multipolygon storage must be a List of polygons, was {dtype}"); + vortex_bail!("multipolygon storage must be a List of polygons, was {dtype}"); }; let DType::List(ring, _) = polygon.as_ref() else { - vortex_bail!(MismatchedTypes: "multipolygon polygon storage must be a List of rings, was {polygon}"); + vortex_bail!("multipolygon polygon storage must be a List of rings, was {polygon}"); }; let DType::List(coords, _) = ring.as_ref() else { - vortex_bail!(MismatchedTypes: "multipolygon ring storage must be a List of coordinates, was {ring}"); + vortex_bail!("multipolygon ring storage must be a List of coordinates, was {ring}"); }; coordinate_dimension(coords) } @@ -125,10 +125,8 @@ pub(crate) fn multipolygon_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else( - || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), - )? - .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? + .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? + .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -146,7 +144,7 @@ fn multipolygon_array( let session = ctx.session().clone(); let arrow = session.arrow().execute_arrow(storage.clone(), None, ctx)?; MultiPolygonArray::try_from((arrow.as_ref(), multipolygon_type)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct MultiPolygonArray: {e}")) + .map_err(|e| vortex_err!("failed to construct MultiPolygonArray: {e}")) } /// A validated `MultiPolygon` array (`try_from` checks the extension type). @@ -158,7 +156,7 @@ impl TryFrom for MultiPolygonData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - MismatchedTypes: "expected a MultiPolygon extension array" + "expected a MultiPolygon extension array" ); Ok(MultiPolygonData(ext)) } @@ -238,9 +236,8 @@ impl ArrowExportVTable for MultiPolygon { .execute_arrow(storage, Some(&storage_field), ctx)?; let multipolygons = - MultiPolygonArray::try_from((arrow_storage.as_ref(), multipolygon_meta)).map_err( - |e| vortex_err!(InvalidArgument: "failed to construct MultiPolygonArray: {e}"), - )?; + MultiPolygonArray::try_from((arrow_storage.as_ref(), multipolygon_meta)) + .map_err(|e| vortex_err!("failed to construct MultiPolygonArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new(multipolygons.into_arrow()))) } @@ -258,43 +255,42 @@ impl ArrowImportVTable for MultiPolygon { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = if let Ok(multipolygon_meta) = - field.try_extension_type::() - { - vortex_ensure!( - multipolygon_meta.coord_type() == CoordType::Separated, - NotImplemented: "geoarrow.multipolygon with interleaved coordinates is not supported; \ + let (dimension, metadata) = + if let Ok(multipolygon_meta) = field.try_extension_type::() { + vortex_ensure!( + multipolygon_meta.coord_type() == CoordType::Separated, + "geoarrow.multipolygon with interleaved coordinates is not supported; \ re-encode with separated (struct) coordinates" - ); - ( - multipolygon_meta.dimension().into(), - spatial_metadata_from_arrow(multipolygon_meta.metadata()), - ) - } else { - // Literal: peel the three `List` layers to the coordinate struct and read its - // dimension from the field names (the canonical check rejects nullable coordinates). - if field.extension_type_name() != Some(MultiPolygonType::NAME) { - return Ok(None); - } - let Ok(DType::List(polygon, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::List(ring, _) = polygon.as_ref() else { - return Ok(None); - }; - let DType::List(coords, _) = ring.as_ref() else { - return Ok(None); + ); + ( + multipolygon_meta.dimension().into(), + spatial_metadata_from_arrow(multipolygon_meta.metadata()), + ) + } else { + // Literal: peel the three `List` layers to the coordinate struct and read its + // dimension from the field names (the canonical check rejects nullable coordinates). + if field.extension_type_name() != Some(MultiPolygonType::NAME) { + return Ok(None); + } + let Ok(DType::List(polygon, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::List(ring, _) = polygon.as_ref() else { + return Ok(None); + }; + let DType::List(coords, _) = ring.as_ref() else { + return Ok(None); + }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) - }; let storage_dtype = multipolygon_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/point.rs b/vortex-spatial/src/extension/point.rs index 5cd7821aefb..9de00619d8a 100644 --- a/vortex-spatial/src/extension/point.rs +++ b/vortex-spatial/src/extension/point.rs @@ -106,7 +106,7 @@ impl TryFrom for PointData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - MismatchedTypes: "expected a Point extension array" + "expected a Point extension array" ); Ok(PointData(ext)) } @@ -132,7 +132,7 @@ fn point_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult VortexResult> { Ok(geometry - .ok_or_else( - || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), - )? - .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? + .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? + .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -219,7 +217,7 @@ impl ArrowExportVTable for Point { // Round-trip through the GeoArrow point array type: this validates that the storage is // the separated-coordinate struct layout expected for a `PointType` extension field. let points = PointArray::try_from((arrow_storage.as_ref(), point_meta)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct PointArray: {e}"))?; + .map_err(|e| vortex_err!("failed to construct PointArray: {e}"))?; Ok(ArrowExport::Exported(points.into_arrow())) } @@ -243,7 +241,7 @@ impl ArrowImportVTable for Point { { vortex_ensure!( point_meta.coord_type() == CoordType::Separated, - NotImplemented: "geoarrow.point with interleaved coordinates is not supported; \ + "geoarrow.point with interleaved coordinates is not supported; \ re-encode with separated (struct) coordinates" ); ( diff --git a/vortex-spatial/src/extension/polygon.rs b/vortex-spatial/src/extension/polygon.rs index 9e278540f23..4d2f632c521 100644 --- a/vortex-spatial/src/extension/polygon.rs +++ b/vortex-spatial/src/extension/polygon.rs @@ -103,10 +103,10 @@ pub(crate) fn polygon_storage_dtype(dim: Dimension, nullability: Nullability) -> /// Validate `dtype` is `List>` and return its [`Dimension`]. pub(crate) fn polygon_dimension(dtype: &DType) -> VortexResult { let DType::List(ring, _) = dtype else { - vortex_bail!(MismatchedTypes: "polygon storage must be a List of rings, was {dtype}"); + vortex_bail!("polygon storage must be a List of rings, was {dtype}"); }; let DType::List(coords, _) = ring.as_ref() else { - vortex_bail!(MismatchedTypes: "polygon ring storage must be a List of coordinates, was {ring}"); + vortex_bail!("polygon ring storage must be a List of coordinates, was {ring}"); }; coordinate_dimension(coords) } @@ -136,13 +136,14 @@ pub(crate) fn build_polygon_storage( for ring in exterior.into_iter().chain(polygon.interiors()) { xs.extend(ring.0.iter().map(|coord| coord.x)); ys.extend(ring.0.iter().map(|coord| coord.y)); - ring_offsets.push(u64::try_from(xs.len()).map_err( - |_| vortex_err!(Overflow: "spatial: polygon coordinate count exceeds u64"), - )?); + ring_offsets.push( + u64::try_from(xs.len()) + .map_err(|_| vortex_err!("spatial: polygon coordinate count exceeds u64"))?, + ); } polygon_offsets.push( u64::try_from(ring_offsets.len() - 1) - .map_err(|_| vortex_err!(Overflow: "spatial: polygon ring count exceeds u64"))?, + .map_err(|_| vortex_err!("spatial: polygon ring count exceeds u64"))?, ); } @@ -189,10 +190,8 @@ pub(crate) fn polygon_geometries( .iter() .map(|geometry| -> VortexResult> { Ok(geometry - .ok_or_else( - || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), - )? - .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? + .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? + .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -207,7 +206,7 @@ fn polygon_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult for PolygonData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - MismatchedTypes: "expected a Polygon extension array" + "expected a Polygon extension array" ); Ok(PolygonData(ext)) } @@ -300,7 +299,7 @@ impl ArrowExportVTable for Polygon { // Round-trip through GeoArrow's polygon array; `into_arrow` is concrete, so wrap in `Arc`. let polygons = PolygonArray::try_from((arrow_storage.as_ref(), polygon_meta)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct PolygonArray: {e}"))?; + .map_err(|e| vortex_err!("failed to construct PolygonArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new(polygons.into_arrow()))) } @@ -320,41 +319,40 @@ impl ArrowImportVTable for Polygon { field: &Field, session: &ArrowSession, ) -> VortexResult> { - let (dimension, metadata) = if let Ok(polygon_meta) = - field.try_extension_type::() - { - vortex_ensure!( - polygon_meta.coord_type() == CoordType::Separated, - NotImplemented: "geoarrow.polygon with interleaved coordinates is not supported; \ + let (dimension, metadata) = + if let Ok(polygon_meta) = field.try_extension_type::() { + vortex_ensure!( + polygon_meta.coord_type() == CoordType::Separated, + "geoarrow.polygon with interleaved coordinates is not supported; \ re-encode with separated (struct) coordinates" - ); - ( - polygon_meta.dimension().into(), - spatial_metadata_from_arrow(polygon_meta.metadata()), - ) - } else { - // Infer the dimension from the field names, not the canonical storage check: a literal's - // coordinate fields may be nullable, which that check rejects. Peel the two `List` layers - // (polygon → rings → coordinates) to reach the struct. - if field.extension_type_name() != Some(PolygonType::NAME) { - return Ok(None); - } - let Ok(DType::List(ring, _)) = - session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) - else { - return Ok(None); - }; - let DType::List(coords, _) = ring.as_ref() else { - return Ok(None); + ); + ( + polygon_meta.dimension().into(), + spatial_metadata_from_arrow(polygon_meta.metadata()), + ) + } else { + // Infer the dimension from the field names, not the canonical storage check: a literal's + // coordinate fields may be nullable, which that check rejects. Peel the two `List` layers + // (polygon → rings → coordinates) to reach the struct. + if field.extension_type_name() != Some(PolygonType::NAME) { + return Ok(None); + } + let Ok(DType::List(ring, _)) = + session.from_arrow_datatype(field.data_type(), field.is_nullable().into()) + else { + return Ok(None); + }; + let DType::List(coords, _) = ring.as_ref() else { + return Ok(None); + }; + let DType::Struct(fields, _) = coords.as_ref() else { + return Ok(None); + }; + let Ok(dimension) = Dimension::from_field_names(fields.names()) else { + return Ok(None); + }; + (dimension, SpatialMetadata::default()) }; - let DType::Struct(fields, _) = coords.as_ref() else { - return Ok(None); - }; - let Ok(dimension) = Dimension::from_field_names(fields.names()) else { - return Ok(None); - }; - (dimension, SpatialMetadata::default()) - }; let storage_dtype = polygon_storage_dtype(dimension, field.is_nullable().into()); Ok(Some(DType::Extension( diff --git a/vortex-spatial/src/extension/rect.rs b/vortex-spatial/src/extension/rect.rs index f89f177762a..162071e29a6 100644 --- a/vortex-spatial/src/extension/rect.rs +++ b/vortex-spatial/src/extension/rect.rs @@ -141,7 +141,7 @@ pub(crate) fn box_storage_dtype(dim: Dimension, nullability: Nullability) -> DTy /// [`Dimension`]. pub(crate) fn box_dimension(dtype: &DType) -> VortexResult { let DType::Struct(fields, _) = dtype else { - vortex_bail!(MismatchedTypes: "box storage must be a Struct, was {dtype}"); + vortex_bail!("box storage must be a Struct, was {dtype}"); }; for (name, field) in fields.names().iter().zip(fields.fields()) { vortex_ensure!( @@ -149,12 +149,11 @@ pub(crate) fn box_dimension(dtype: &DType) -> VortexResult { field, DType::Primitive(PType::F64, Nullability::NonNullable) ), - MismatchedTypes: "box field {name} must be non-nullable f64, was {field}" + "box field {name} must be non-nullable f64, was {field}" ); } - box_dimension_from_names(fields.names()).ok_or_else( - || vortex_err!(InvalidArgument: "not a valid geoarrow.box dimension: {:?}", fields.names()), - ) + box_dimension_from_names(fields.names()) + .ok_or_else(|| vortex_err!("not a valid geoarrow.box dimension: {:?}", fields.names())) } /// Build a native [`Rect`] array from canonical min/max ordinate columns. @@ -188,7 +187,7 @@ fn rect_array(storage: &ArrayRef, ctx: &mut ExecutionCtx) -> VortexResult VortexResult> { Ok(geometry - .ok_or_else( - || vortex_err!(InvalidArgument: "spatial: null geometry is not supported"), - )? - .map_err(|e| vortex_err!(Serde: "spatial: geometry access failed: {e}"))? + .ok_or_else(|| vortex_err!("spatial: null geometry is not supported"))? + .map_err(|e| vortex_err!("spatial: geometry access failed: {e}"))? .to_geometry()) }) .collect() @@ -271,7 +268,7 @@ impl ArrowExportVTable for Rect { // Round-trip through GeoArrow's rect array; `into_arrow` is concrete, so wrap in `Arc`. let rects = RectArray::try_from((arrow_storage.as_ref(), box_meta)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct RectArray: {e}"))?; + .map_err(|e| vortex_err!("failed to construct RectArray: {e}"))?; Ok(ArrowExport::Exported(Arc::new(rects.into_arrow()))) } diff --git a/vortex-spatial/src/extension/wkb.rs b/vortex-spatial/src/extension/wkb.rs index 783a5b499e5..8b0b42fb97b 100644 --- a/vortex-spatial/src/extension/wkb.rs +++ b/vortex-spatial/src/extension/wkb.rs @@ -72,7 +72,7 @@ impl TryFrom for WellKnownBinaryData { fn try_from(ext: ExtensionArray) -> Result { vortex_ensure!( ext.ext_dtype().is::(), - MismatchedTypes: "array extension dtype {} is not a WKB", + "array extension dtype {} is not a WKB", ext.ext_dtype() ); @@ -100,7 +100,7 @@ impl<'a> Wkb<'a> { /// validation on the structure of the WKB. pub fn try_from_bytes(bytes: &'a [u8]) -> VortexResult { wkb::reader::Wkb::try_new(bytes) - .map_err(|e| vortex_err!(Serde: "failed parsing WKB: {e}")) + .map_err(|e| vortex_err!("failed parsing WKB: {e}")) .map(Wkb) } } @@ -151,7 +151,7 @@ impl ExtVTable for WellKnownBinary { fn validate_dtype(ext_dtype: &ExtDType) -> VortexResult<()> { vortex_ensure!( ext_dtype.storage_dtype().is_binary(), - MismatchedTypes: "vortex.st.wkb must have binary storage type, was {}", + "vortex.st.wkb must have binary storage type, was {}", ext_dtype.storage_dtype() ); @@ -233,21 +233,17 @@ impl ArrowExportVTable for WellKnownBinary { let arrow_ref: ArrowArrayRef = match target.data_type() { DataType::Binary => Arc::new( GenericWkbArray::::try_from((arrow_storage.as_ref(), wkb_meta)) - .map_err(|e| vortex_err!(InvalidArgument: "failed to construct WkbArray: {e}"))? + .map_err(|e| vortex_err!("failed to construct WkbArray: {e}"))? .into_arrow(), ), DataType::LargeBinary => Arc::new( GenericWkbArray::::try_from((arrow_storage.as_ref(), wkb_meta)) - .map_err( - |e| vortex_err!(InvalidArgument: "failed to construct LargeWkbArray: {e}"), - )? + .map_err(|e| vortex_err!("failed to construct LargeWkbArray: {e}"))? .into_arrow(), ), DataType::BinaryView => Arc::new( WkbViewArray::try_from((arrow_storage.as_ref(), wkb_meta)) - .map_err( - |e| vortex_err!(InvalidArgument: "failed to construct WkbViewArray: {e}"), - )? + .map_err(|e| vortex_err!("failed to construct WkbViewArray: {e}"))? .into_arrow(), ), _ => unreachable!("target data type was validated above"), diff --git a/vortex-spatial/src/scalar_fn/collect.rs b/vortex-spatial/src/scalar_fn/collect.rs index fe1ada7b7f4..ce52bd8fda8 100644 --- a/vortex-spatial/src/scalar_fn/collect.rs +++ b/vortex-spatial/src/scalar_fn/collect.rs @@ -61,10 +61,10 @@ fn collect_dtype(dtypes: &[DType]) -> VortexResult { vortex_ensure_eq!( dtypes.len(), 1, - InvalidArgument: "spatial: collect requires exactly one list operand" + "spatial: collect requires exactly one list operand" ); let DType::List(element_dtype, nullability) = &dtypes[0] else { - vortex_bail!(MismatchedTypes: "spatial: collect operand {} is not a list", dtypes[0]); + vortex_bail!("spatial: collect operand {} is not a list", dtypes[0]); }; // Execution ignores null list elements, so the result's element storage is non-nullable. let multi_storage = |element: &ExtDTypeRef| { @@ -90,7 +90,7 @@ fn collect_dtype(dtypes: &[DType]) -> VortexResult { )? .erased()), _ => vortex_bail!( - MismatchedTypes: "spatial: collect list element {element_dtype} is not a native Point, LineString, \ + "spatial: collect list element {element_dtype} is not a native Point, LineString, \ or Polygon" ), } @@ -131,13 +131,12 @@ fn compact_row_views( .filter(|end| *end <= element_mask.len()) .ok_or_else(|| { vortex_err!( - OutOfBounds: "spatial: collect row at element {start} exceeds the {} list elements", + "spatial: collect row at element {start} exceeds the {} list elements", element_mask.len() ) })?; - let valid = u64::try_from(count_valid(element_mask, start, end)).map_err( - |_| vortex_err!(Overflow: "spatial: collect valid element count exceeds u64"), - )?; + let valid = u64::try_from(count_valid(element_mask, start, end)) + .map_err(|_| vortex_err!("spatial: collect valid element count exceeds u64"))?; compact_offsets.push(offset); compact_sizes.push(valid); offset += valid; @@ -517,7 +516,7 @@ mod tests { let result = SpatialCollect::try_new(input)?.into_array(); let Columnar::Constant(constant) = result.clone().execute::(&mut ctx)? else { return Err(vortex_err!( - AssertionFailed: "collect of a constant list should remain constant" + "collect of a constant list should remain constant" )); }; assert_eq!(constant.len(), 3); diff --git a/vortex-spatial/src/scalar_fn/contains.rs b/vortex-spatial/src/scalar_fn/contains.rs index 1bce23d103c..34864cfaa5a 100644 --- a/vortex-spatial/src/scalar_fn/contains.rs +++ b/vortex-spatial/src/scalar_fn/contains.rs @@ -120,10 +120,10 @@ mod tests { fn geometry_constant(geometry: &Geometry, len: usize) -> VortexResult { let mut buf = Vec::new(); wkb::writer::write_geometry(&mut buf, geometry, &WriteOptions::default()) - .map_err(|e| vortex_err!(Serde: "writing WKB failed: {e}"))?; + .map_err(|e| vortex_err!("writing WKB failed: {e}"))?; let session = VortexSession::empty(); let scalar = crate::extension::native_geometry_scalar_from_wkb(&buf, &session)? - .ok_or_else(|| vortex_err!(InvalidArgument: "unsupported geometry type"))?; + .ok_or_else(|| vortex_err!("unsupported geometry type"))?; Ok(ConstantArray::new(scalar, len).into_array()) } diff --git a/vortex-spatial/src/scalar_fn/convex_hull.rs b/vortex-spatial/src/scalar_fn/convex_hull.rs index 4bdadc9c4ab..244dae0f5d2 100644 --- a/vortex-spatial/src/scalar_fn/convex_hull.rs +++ b/vortex-spatial/src/scalar_fn/convex_hull.rs @@ -34,17 +34,17 @@ fn convex_hull_dtype(dtypes: &[DType]) -> VortexResult { vortex_ensure_eq!( dtypes.len(), 1, - InvalidArgument: "spatial: convex_hull requires exactly one MultiPoint operand" + "spatial: convex_hull requires exactly one MultiPoint operand" ); let Some(input) = dtypes[0].as_extension_opt() else { vortex_bail!( - MismatchedTypes: "spatial: convex_hull operand {} is not a native MultiPoint", + "spatial: convex_hull operand {} is not a native MultiPoint", dtypes[0] ); }; vortex_ensure!( input.is::(), - MismatchedTypes: "spatial: convex_hull operand {} is not a native MultiPoint", + "spatial: convex_hull operand {} is not a native MultiPoint", dtypes[0] ); @@ -216,7 +216,7 @@ mod tests { let result = SpatialConvexHull::try_new(input)?.into_array(); let Columnar::Constant(constant) = result.clone().execute::(&mut ctx)? else { return Err(vortex_err!( - AssertionFailed: "convex_hull of a constant should remain constant" + "convex_hull of a constant should remain constant" )); }; assert_eq!(constant.len(), 3); diff --git a/vortex-spatial/src/scalar_fn/envelope.rs b/vortex-spatial/src/scalar_fn/envelope.rs index c3d98257aaa..37c99f4b1b9 100644 --- a/vortex-spatial/src/scalar_fn/envelope.rs +++ b/vortex-spatial/src/scalar_fn/envelope.rs @@ -58,11 +58,11 @@ fn validate_envelope_operands(dtypes: &[DType]) -> VortexResult<()> { vortex_ensure_eq!( dtypes.len(), 1, - InvalidArgument: "spatial: envelope requires exactly one geometry operand" + "spatial: envelope requires exactly one geometry operand" ); vortex_ensure!( is_native_geometry(&dtypes[0]), - MismatchedTypes: "spatial: envelope operand {} is not a native geometry type", + "spatial: envelope operand {} is not a native geometry type", dtypes[0] ); Ok(()) @@ -151,7 +151,7 @@ fn envelope_array( let is_rect = array .dtype() .as_extension_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "spatial: envelope operand is not a geometry extension type"))? + .ok_or_else(|| vortex_err!("spatial: envelope operand is not a geometry extension type"))? .is::(); let storage = array .execute::(ctx)? @@ -562,9 +562,7 @@ mod tests { let points = ConstantArray::new(scalar, 3).into_array(); let result = boxes(points)?.execute::(&mut ctx)?; let Columnar::Constant(boxes) = result else { - return Err( - vortex_err!(AssertionFailed: "envelope of a constant should remain constant"), - ); + return Err(vortex_err!("envelope of a constant should remain constant")); }; assert_eq!(boxes.len(), 3); diff --git a/vortex-spatial/src/scalar_fn/intersects.rs b/vortex-spatial/src/scalar_fn/intersects.rs index addf97f32b3..81cc1ca0522 100644 --- a/vortex-spatial/src/scalar_fn/intersects.rs +++ b/vortex-spatial/src/scalar_fn/intersects.rs @@ -141,10 +141,10 @@ mod tests { fn geometry_constant(geometry: &Geometry, len: usize) -> VortexResult { let mut buf = Vec::new(); wkb::writer::write_geometry(&mut buf, geometry, &WriteOptions::default()) - .map_err(|e| vortex_err!(Serde: "writing WKB failed: {e}"))?; + .map_err(|e| vortex_err!("writing WKB failed: {e}"))?; let session = VortexSession::empty(); let scalar = crate::extension::native_geometry_scalar_from_wkb(&buf, &session)? - .ok_or_else(|| vortex_err!(InvalidArgument: "unsupported geometry type"))?; + .ok_or_else(|| vortex_err!("unsupported geometry type"))?; Ok(ConstantArray::new(scalar, len).into_array()) } diff --git a/vortex-spatial/src/scalar_fn/length.rs b/vortex-spatial/src/scalar_fn/length.rs index b21ffa9c03f..9512008e2c4 100644 --- a/vortex-spatial/src/scalar_fn/length.rs +++ b/vortex-spatial/src/scalar_fn/length.rs @@ -49,13 +49,13 @@ fn validate_length_operands(dtypes: &[DType]) -> VortexResult<()> { vortex_ensure_eq!( dtypes.len(), 1, - InvalidArgument: "spatial: length requires exactly one lineal operand" + "spatial: length requires exactly one lineal operand" ); vortex_ensure!( dtypes[0].as_extension_opt().is_some_and(|extension| { extension.is::() || extension.is::() }), - MismatchedTypes: "spatial: length operand {} is not a native LineString or MultiLineString", + "spatial: length operand {} is not a native LineString or MultiLineString", dtypes[0] ); Ok(()) @@ -68,8 +68,7 @@ fn list_offsets(list: &ListArray, ctx: &mut ExecutionCtx) -> VortexResult>(ctx)? .iter() .map(|&offset| { - usize::try_from(offset) - .map_err(|_| vortex_err!(Overflow: "spatial: list offset exceeds usize")) + usize::try_from(offset).map_err(|_| vortex_err!("spatial: list offset exceeds usize")) }) .collect() } @@ -324,9 +323,7 @@ mod tests { .into_array() .execute::(&mut ctx)?; let Columnar::Constant(lengths) = result else { - return Err( - vortex_err!(AssertionFailed: "length of a constant should remain constant"), - ); + return Err(vortex_err!("length of a constant should remain constant")); }; assert_eq!(lengths.len(), 3); assert_eq!(f64::try_from(lengths.scalar())?, 9.0); @@ -344,7 +341,7 @@ mod tests { .execute::(&mut ctx)?; let Columnar::Constant(lengths) = result else { return Err(vortex_err!( - AssertionFailed: "length of a null constant should remain constant" + "length of a null constant should remain constant" )); }; assert_eq!(lengths.len(), 2); diff --git a/vortex-spatial/src/scalar_fn/make_line.rs b/vortex-spatial/src/scalar_fn/make_line.rs index 8730be2a3f1..406b05e6dc1 100644 --- a/vortex-spatial/src/scalar_fn/make_line.rs +++ b/vortex-spatial/src/scalar_fn/make_line.rs @@ -44,14 +44,14 @@ fn validate_make_line_operands(dtypes: &[DType]) -> VortexResult<()> { vortex_ensure_eq!( dtypes.len(), 2, - InvalidArgument: "spatial: make_line requires exactly two point operands" + "spatial: make_line requires exactly two point operands" ); for dtype in dtypes { vortex_ensure!( dtype .as_extension_opt() .is_some_and(|extension| extension.is::()), - MismatchedTypes: "spatial: make_line operand {dtype} is not a native point" + "spatial: make_line operand {dtype} is not a native point" ); } Ok(()) @@ -67,7 +67,7 @@ fn make_line_metadata( vortex_ensure_eq!( left_crs, right_crs, - InvalidArgument: "spatial: make_line operands have different coordinate reference systems" + "spatial: make_line operands have different coordinate reference systems" ); Ok(left.clone()) } @@ -107,9 +107,7 @@ fn point_coordinates( fields .field(name) .map(|value| ConstantArray::new(value, len).into_array()) - .ok_or_else( - || vortex_err!(NotFound: "spatial: point coordinate missing {name}"), - ) + .ok_or_else(|| vortex_err!("spatial: point coordinate missing {name}")) }) .collect::>>()?; StructArray::try_new(names, arrays, len, Validity::NonNullable) @@ -342,7 +340,7 @@ mod tests { .execute::(&mut ctx)?; let Columnar::Constant(lines) = result else { return Err(vortex_err!( - AssertionFailed: "make_line of two constants should remain constant" + "make_line of two constants should remain constant" )); }; assert_eq!(lines.len(), 3); @@ -402,7 +400,7 @@ mod tests { .execute::(&mut ctx)?; let Columnar::Constant(lines) = result else { return Err(vortex_err!( - AssertionFailed: "make_line with a null constant should remain constant" + "make_line with a null constant should remain constant" )); }; assert_eq!(lines.len(), 2); diff --git a/vortex-spatial/src/scalar_fn/row.rs b/vortex-spatial/src/scalar_fn/row.rs index b305fe6268a..4d3c1fe5977 100644 --- a/vortex-spatial/src/scalar_fn/row.rs +++ b/vortex-spatial/src/scalar_fn/row.rs @@ -84,7 +84,7 @@ unsafe impl InputElement for GeometryRow { fn validate(dtype: &DType) -> VortexResult<()> { vortex_ensure!( is_native_geometry(dtype), - MismatchedTypes: "spatial: operand {dtype} is not a native geometry type" + "spatial: operand {dtype} is not a native geometry type" ); Ok(()) } @@ -98,7 +98,7 @@ unsafe impl InputElement for GeometryRow { vortex_ensure_eq!( geometries.len(), 1, - AssertionFailed: "a geometry batch constant must decode to one value", + "a geometry batch constant must decode to one value", ); Ok(geometries diff --git a/vortex-spatial/src/test_harness.rs b/vortex-spatial/src/test_harness.rs index 9c28c9bb317..d6f30d51162 100644 --- a/vortex-spatial/src/test_harness.rs +++ b/vortex-spatial/src/test_harness.rs @@ -64,7 +64,7 @@ fn xy_struct(xs: Vec, ys: Vec) -> VortexResult { /// A list offset as `i32`. fn offset(n: usize) -> VortexResult { - i32::try_from(n).map_err(|_| vortex_err!(Overflow: "geometry offset overflow")) + i32::try_from(n).map_err(|_| vortex_err!("geometry offset overflow")) } /// Wrap `elements` — built from `rows` flattened one level — in a non-nullable `List` with one diff --git a/vortex-spatial/src/tests/point.rs b/vortex-spatial/src/tests/point.rs index e06a53b2e69..aec2e91bcbf 100644 --- a/vortex-spatial/src/tests/point.rs +++ b/vortex-spatial/src/tests/point.rs @@ -92,7 +92,7 @@ fn exports_to_struct() -> VortexResult<()> { let ordinates = |name: &str| -> VortexResult> { Ok(points .column_by_name(name) - .ok_or_else(|| vortex_err!(NotFound: "missing {name} column"))? + .ok_or_else(|| vortex_err!("missing {name} column"))? .as_primitive::() .values() .to_vec()) @@ -176,7 +176,7 @@ fn roundtrips_through_arrow() -> VortexResult<()> { let ext = reimported .dtype() .as_extension_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Extension dtype"))?; + .ok_or_else(|| vortex_err!("expected Extension dtype"))?; assert_eq!(ext.metadata::().crs.as_deref(), Some("EPSG:4326")); assert_eq!( diff --git a/vortex-spatial/src/tests/rect.rs b/vortex-spatial/src/tests/rect.rs index 6e616272795..9639e5ba400 100644 --- a/vortex-spatial/src/tests/rect.rs +++ b/vortex-spatial/src/tests/rect.rs @@ -86,7 +86,7 @@ fn roundtrips_through_arrow() -> VortexResult<()> { let ext = reimported .dtype() .as_extension_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected Extension dtype"))?; + .ok_or_else(|| vortex_err!("expected Extension dtype"))?; assert!(ext.is::()); assert_eq!(ext.metadata::().crs.as_deref(), Some("EPSG:4326")); @@ -94,13 +94,13 @@ fn roundtrips_through_arrow() -> VortexResult<()> { let scalar = reimported.execute_scalar(row, &mut ctx)?; let storage = scalar .as_extension_opt() - .ok_or_else(|| vortex_err!(MismatchedTypes: "expected extension scalar"))? + .ok_or_else(|| vortex_err!("expected extension scalar"))? .to_storage_scalar(); f64::try_from( &storage .as_struct() .field(name) - .ok_or_else(|| vortex_err!(NotFound: "missing {name}"))?, + .ok_or_else(|| vortex_err!("missing {name}"))?, ) }; assert_eq!(corner(0, "xmin")?, 0.0); diff --git a/vortex-spatial/src/tests/wkb.rs b/vortex-spatial/src/tests/wkb.rs index 558d0956ac3..05b14ad1942 100644 --- a/vortex-spatial/src/tests/wkb.rs +++ b/vortex-spatial/src/tests/wkb.rs @@ -62,7 +62,7 @@ fn wkb_extension_array() -> VortexResult<(Vec, vortex_array::ArrayRef)> { let mut buf = Vec::new(); // We should always prefer to write little-endian, which is the default option. wkb::writer::write_geometry(&mut buf, &test_polygon(), &WriteOptions::default()) - .map_err(|e| vortex_err!(Serde: "writing WKB failed: {e}"))?; + .map_err(|e| vortex_err!("writing WKB failed: {e}"))?; let mut builder = VarBinBuilder::::with_capacity_in( DType::Binary(Nullability::NonNullable), diff --git a/vortex-tensor/src/scalar_fns/l2_norm.rs b/vortex-tensor/src/scalar_fns/l2_norm.rs index 3cdb7ee998e..0d4ffc03447 100644 --- a/vortex-tensor/src/scalar_fns/l2_norm.rs +++ b/vortex-tensor/src/scalar_fns/l2_norm.rs @@ -128,11 +128,11 @@ impl ScalarFnArrayVTable for L2Norm { session: &VortexSession, ) -> VortexResult> { let metadata = L2NormMetadata::decode(metadata) - .map_err(|error| vortex_err!(Serde: "failed to decode L2Norm metadata: {error}"))?; + .map_err(|error| vortex_err!("failed to decode L2Norm metadata: {error}"))?; let input_pb = metadata .input_dtype .as_ref() - .ok_or_else(|| vortex_err!(Serde: "L2Norm metadata must contain input_dtype"))?; + .ok_or_else(|| vortex_err!("L2Norm metadata must contain input_dtype"))?; let input_dtype = DType::from_proto(input_pb, session)?; let child = children.get(0, &input_dtype, len)?; Ok(ScalarFnArrayParts { diff --git a/vortex-tensor/src/scalar_fns/l2_normalize.rs b/vortex-tensor/src/scalar_fns/l2_normalize.rs index fbe967b0ab6..ff3d068529d 100644 --- a/vortex-tensor/src/scalar_fns/l2_normalize.rs +++ b/vortex-tensor/src/scalar_fns/l2_normalize.rs @@ -213,13 +213,12 @@ impl ScalarFnArrayVTable for L2Normalize { children: &dyn ArrayChildren, session: &VortexSession, ) -> VortexResult> { - let metadata = L2NormalizeMetadata::decode(metadata).map_err( - |error| vortex_err!(Serde: "failed to decode L2Normalize metadata: {error}"), - )?; + let metadata = L2NormalizeMetadata::decode(metadata) + .map_err(|error| vortex_err!("failed to decode L2Normalize metadata: {error}"))?; let input_dtype = metadata .input_dtype .as_ref() - .ok_or_else(|| vortex_err!(Serde: "L2Normalize metadata must contain input_dtype"))?; + .ok_or_else(|| vortex_err!("L2Normalize metadata must contain input_dtype"))?; let input_dtype = DType::from_proto(input_dtype, session)?; l2_normalize_dtype(&input_dtype)?; let child = children.get(0, &input_dtype, len)?; diff --git a/vortex-tensor/src/scalar_fns/row.rs b/vortex-tensor/src/scalar_fns/row.rs index c6d6df75259..cc079c21445 100644 --- a/vortex-tensor/src/scalar_fns/row.rs +++ b/vortex-tensor/src/scalar_fns/row.rs @@ -37,14 +37,14 @@ use crate::utils::validate_tensor_float_input; /// Returns the common float element type of tensor row-function arguments. pub fn tensor_element_ptype(args: &[DType]) -> VortexResult { - let (first, rest) = args.split_first().ok_or_else( - || vortex_err!(InvalidArgument: "tensor row function requires at least one input"), - )?; + let (first, rest) = args + .split_first() + .ok_or_else(|| vortex_err!("tensor row function requires at least one input"))?; for argument in rest { vortex_ensure!( first.eq_ignore_nullability(argument), - MismatchedTypes: "tensor row-function inputs must have the same dtype, got {first} and {argument}", + "tensor row-function inputs must have the same dtype, got {first} and {argument}", ); } @@ -85,16 +85,16 @@ fn decode_tensor_storage( vortex_ensure_eq!( stride, row_width, - InvalidArgument: "per-row tensor stride must equal its width", + "per-row tensor stride must equal its width", ); let Some(expected_elements) = row_count.checked_mul(stride) else { vortex_bail!( - Overflow: "tensor row storage length must fit usize, got {row_count} rows of width {stride}", + "tensor row storage length must fit usize, got {row_count} rows of width {stride}", ); }; expected_elements }; - vortex_ensure_eq!(elements.len(), expected_elements, InvalidArgument); + vortex_ensure_eq!(elements.len(), expected_elements); Ok(TensorRows { elements, @@ -121,7 +121,7 @@ unsafe impl InputElement for TensorRow { vortex_ensure_eq!( tensor_match.element_ptype(), expected_element_ptype, - MismatchedTypes: "tensor row input {dtype} has the wrong element type", + "tensor row input {dtype} has the wrong element type", ); Ok(()) @@ -149,14 +149,14 @@ unsafe impl InputElement for TensorRow { extension.storage_array().clone() } else { vortex_bail!( - MismatchedTypes: "a tensor batch constant must use the Constant encoding or constant extension \ + "a tensor batch constant must use the Constant encoding or constant extension \ storage, got {}", array.encoding_id() ); }; let decoded = decode_tensor_storage::(&storage, 1, row_width, ctx)?; - vortex_ensure_eq!(decoded.elements.len(), row_width, InvalidArgument); + vortex_ensure_eq!(decoded.elements.len(), row_width); Ok(decoded.elements) } diff --git a/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs b/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs index 9e35b984ad4..e4e460c21a2 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/matcher.rs @@ -48,7 +48,7 @@ impl Matcher for AnyFixedShapeTensor { let DType::FixedSizeList(element_dtype, list_size, _) = ext_dtype.storage_dtype() else { vortex_panic!( - AssertionFailed: "`FixedShapeTensor` type somehow did not have a `FixedSizeList` storage type" + "`FixedShapeTensor` type somehow did not have a `FixedSizeList` storage type" ) }; diff --git a/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs b/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs index c935a507855..ed174c93d95 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/metadata.rs @@ -54,7 +54,7 @@ impl FixedShapeTensorMetadata { /// The number of names must match the number of logical dimensions. pub fn with_dim_names(mut self, names: Vec) -> VortexResult { if !names.is_empty() { - vortex_ensure_eq!(names.len(), self.logical_shape.len(), InvalidArgument); + vortex_ensure_eq!(names.len(), self.logical_shape.len()); self.dim_names = Some(names); } @@ -68,17 +68,17 @@ impl FixedShapeTensorMetadata { /// number of logical dimensions. pub fn with_permutation(mut self, permutation: Vec) -> VortexResult { if !permutation.is_empty() { - vortex_ensure_eq!(permutation.len(), self.logical_shape.len(), InvalidArgument); + vortex_ensure_eq!(permutation.len(), self.logical_shape.len()); // Verify this is actually a permutation of [0..N). let mut seen = vec![false; permutation.len()]; for &p in &permutation { vortex_ensure!( p < permutation.len(), - OutOfBounds: "permutation index {p} is out of range for {} dimensions", + "permutation index {p} is out of range for {} dimensions", permutation.len() ); - vortex_ensure!(!seen[p], InvalidArgument: "permutation contains duplicate index {p}"); + vortex_ensure!(!seen[p], "permutation contains duplicate index {p}"); seen[p] = true; } diff --git a/vortex-tensor/src/types/fixed_shape_tensor/proto.rs b/vortex-tensor/src/types/fixed_shape_tensor/proto.rs index 52f6a37a41a..2bd608d717d 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/proto.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/proto.rs @@ -67,8 +67,7 @@ pub(crate) fn serialize(metadata: &FixedShapeTensorMetadata) -> Vec { /// For 0-dimensional tensors, all three repeated fields are empty, which correctly produces a /// metadata with an empty shape and no names or permutation. pub(crate) fn deserialize(bytes: &[u8]) -> VortexResult { - let proto = - FixedShapeTensorMetadataProto::decode(bytes).map_err(|e| vortex_err!(Serde: "{e}"))?; + let proto = FixedShapeTensorMetadataProto::decode(bytes).map_err(|e| vortex_err!("{e}"))?; let logical_shape = proto .logical_shape diff --git a/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs b/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs index 590808a8753..b98e3dd0acf 100644 --- a/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs +++ b/vortex-tensor/src/types/fixed_shape_tensor/vtable.rs @@ -39,26 +39,26 @@ impl ExtVTable for FixedShapeTensor { let storage_dtype = ext_dtype.storage_dtype(); let DType::FixedSizeList(element_dtype, list_size, _nullability) = storage_dtype else { vortex_bail!( - InvalidArgument: "FixedShapeTensor storage dtype must be a FixedSizeList, got {storage_dtype}" + "FixedShapeTensor storage dtype must be a FixedSizeList, got {storage_dtype}" ); }; // Note that these constraints may be relaxed in the future. vortex_ensure!( element_dtype.is_primitive(), - MismatchedTypes: "FixedShapeTensor element dtype must be primitive, got {element_dtype} \ + "FixedShapeTensor element dtype must be primitive, got {element_dtype} \ (may change in the future)" ); vortex_ensure!( !element_dtype.is_nullable(), - InvalidArgument: "FixedShapeTensor element dtype must be non-nullable (may change in the future)" + "FixedShapeTensor element dtype must be non-nullable (may change in the future)" ); let element_count: usize = ext_dtype.metadata().logical_shape().iter().product(); vortex_ensure_eq!( element_count, *list_size as usize, - InvalidArgument: "FixedShapeTensor logical shape product must match FixedSizeList size" + "FixedShapeTensor logical shape product must match FixedSizeList size" ); Ok(()) diff --git a/vortex-tensor/src/types/vector/matcher.rs b/vortex-tensor/src/types/vector/matcher.rs index 66fed38ceb8..9f5b0037029 100644 --- a/vortex-tensor/src/types/vector/matcher.rs +++ b/vortex-tensor/src/types/vector/matcher.rs @@ -44,7 +44,7 @@ impl Matcher for AnyVector { } let DType::FixedSizeList(element_dtype, list_size, _) = ext_dtype.storage_dtype() else { - vortex_panic!(AssertionFailed: "`Vector` type somehow did not have a `FixedSizeList` storage type") + vortex_panic!("`Vector` type somehow did not have a `FixedSizeList` storage type") }; let dimensions = *list_size; diff --git a/vortex-tensor/src/types/vector/mod.rs b/vortex-tensor/src/types/vector/mod.rs index 441e23c1b73..af424b9cc41 100644 --- a/vortex-tensor/src/types/vector/mod.rs +++ b/vortex-tensor/src/types/vector/mod.rs @@ -23,16 +23,16 @@ use vortex_error::vortex_ensure; /// elements. The outer nullability is not constrained. pub(crate) fn validate_vector_storage_dtype(storage: &DType) -> VortexResult<()> { let DType::FixedSizeList(element_dtype, _list_size, _nullability) = storage else { - vortex_bail!(InvalidArgument: "Vector storage dtype must be a FixedSizeList, got {storage}"); + vortex_bail!("Vector storage dtype must be a FixedSizeList, got {storage}"); }; vortex_ensure!( element_dtype.is_float(), - MismatchedTypes: "Vector element dtype must be a float, got {element_dtype}" + "Vector element dtype must be a float, got {element_dtype}" ); vortex_ensure!( !element_dtype.is_nullable(), - InvalidArgument: "Vector element dtype must be non-nullable" + "Vector element dtype must be non-nullable" ); Ok(()) diff --git a/vortex-tensor/src/utils.rs b/vortex-tensor/src/utils.rs index cf3eefb0cae..69ef4378648 100644 --- a/vortex-tensor/src/utils.rs +++ b/vortex-tensor/src/utils.rs @@ -29,18 +29,18 @@ use crate::matcher::TensorMatch; /// Validates that `input_dtype` is a float-valued tensor-like extension dtype. pub fn validate_tensor_float_input(input_dtype: &DType) -> VortexResult> { - let ext = input_dtype.as_extension_opt().ok_or_else( - || vortex_err!(MismatchedTypes: "expected an extension type, got {input_dtype}"), - )?; + let ext = input_dtype + .as_extension_opt() + .ok_or_else(|| vortex_err!("expected an extension type, got {input_dtype}"))?; - let tensor_match = ext.metadata_opt::().ok_or_else( - || vortex_err!(MismatchedTypes: "expected an `AnyTensor`, got {input_dtype}"), - )?; + let tensor_match = ext + .metadata_opt::() + .ok_or_else(|| vortex_err!("expected an `AnyTensor`, got {input_dtype}"))?; let ptype = tensor_match.element_ptype(); vortex_ensure!( ptype.is_float(), - MismatchedTypes: "expected a float element dtype, got {ptype}", + "expected a float element dtype, got {ptype}", ); Ok(tensor_match) @@ -54,7 +54,7 @@ pub fn validate_binary_tensor_float_inputs<'a>( ) -> VortexResult> { vortex_ensure!( lhs.eq_ignore_nullability(rhs), - MismatchedTypes: "binary tensor expression expects inputs to have the same dtype, got {lhs} and {rhs}" + "binary tensor expression expects inputs to have the same dtype, got {lhs} and {rhs}" ); validate_tensor_float_input(lhs) } @@ -123,7 +123,7 @@ pub fn extract_flat_elements( let elems: PrimitiveArray = fsl.elements().clone().execute(ctx)?; vortex_ensure!( !elems.nullability().is_nullable(), - InvalidArgument: "tensor storage elements must be non-nullable, got {}", + "tensor storage elements must be non-nullable, got {}", elems.dtype(), ); Ok(FlatElements { @@ -172,15 +172,15 @@ impl BinaryTensorOpMetadata { session: &VortexSession, ) -> VortexResult> { let metadata = Self::decode(metadata) - .map_err(|e| vortex_err!(Serde: "Failed to decode BinaryTensorOpMetadata: {e}"))?; + .map_err(|e| vortex_err!("Failed to decode BinaryTensorOpMetadata: {e}"))?; let lhs_pb = metadata .lhs_dtype .as_ref() - .ok_or_else(|| vortex_err!(Serde: "metadata missing lhs_dtype"))?; + .ok_or_else(|| vortex_err!("metadata missing lhs_dtype"))?; let rhs_pb = metadata .rhs_dtype .as_ref() - .ok_or_else(|| vortex_err!(Serde: "metadata missing rhs_dtype"))?; + .ok_or_else(|| vortex_err!("metadata missing rhs_dtype"))?; let lhs_dtype = DType::from_proto(lhs_pb, session)?; let rhs_dtype = DType::from_proto(rhs_pb, session)?; diff --git a/vortex-test/compat-gen/src/adapter.rs b/vortex-test/compat-gen/src/adapter.rs index aed22317db6..f1c518a1186 100644 --- a/vortex-test/compat-gen/src/adapter.rs +++ b/vortex-test/compat-gen/src/adapter.rs @@ -31,7 +31,7 @@ use vortex_error::vortex_err; use vortex_session::VortexSession; fn runtime() -> VortexResult { - Runtime::new().map_err(|e| vortex_err!(Io: "failed to create tokio runtime: {e}")) + Runtime::new().map_err(|e| vortex_err!("failed to create tokio runtime: {e}")) } /// Compute all statistics on every node in the array tree. @@ -76,7 +76,7 @@ pub fn write_compressed( let session = VortexSession::default().with_tokio(); let mut file = tokio::fs::File::create(path) .await - .map_err(|e| vortex_err!(Io: "failed to create {}: {e}", path.display()))?; + .map_err(|e| vortex_err!("failed to create {}: {e}", path.display()))?; let _summary = session .write_options() .with_strategy(strategy) @@ -155,8 +155,8 @@ pub fn read_layout_tree(bytes: ByteBuffer) -> VortexResult<()> { &session, &Default::default(), )?; - let len = usize::try_from(row_count) - .map_err(|e| vortex_err!(Overflow: "row count overflow: {e}"))?; + let len = + usize::try_from(row_count).map_err(|e| vortex_err!("row count overflow: {e}"))?; let expr = root().bind(reader.dtype())?; reader .projection_evaluation(&(0..row_count), &expr, MaskFuture::new_true(len))? diff --git a/vortex-test/compat-gen/src/check.rs b/vortex-test/compat-gen/src/check.rs index 7295c5cd93a..a2834fa733b 100644 --- a/vortex-test/compat-gen/src/check.rs +++ b/vortex-test/compat-gen/src/check.rs @@ -63,8 +63,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { } // Generate fresh fixtures into a temp directory. - let tmp_dir = - tempfile::tempdir().map_err(|e| vortex_err!(Io: "failed to create temp dir: {e}"))?; + let tmp_dir = tempfile::tempdir().map_err(|e| vortex_err!("failed to create temp dir: {e}"))?; eprintln!("generating fresh fixtures for comparison..."); for fixture in &fixtures { @@ -73,7 +72,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { // Collect .vortex files in the check directory. let dir_files: Vec = std::fs::read_dir(dir) - .map_err(|e| vortex_err!(Io: "failed to read dir {}: {e}", dir.display()))? + .map_err(|e| vortex_err!("failed to read dir {}: {e}", dir.display()))? .filter_map(|entry| { let entry = entry.ok()?; let name = entry.file_name().to_string_lossy().to_string(); @@ -83,7 +82,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { // Collect all fixture names (each fixture may produce multiple files). let fresh_files: Vec = std::fs::read_dir(tmp_dir.path()) - .map_err(|e| vortex_err!(Io: "failed to read tmp dir: {e}"))? + .map_err(|e| vortex_err!("failed to read tmp dir: {e}"))? .filter_map(|entry| { let entry = entry.ok()?; let name = entry.file_name().to_string_lossy().to_string(); @@ -200,7 +199,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { // Print JSON result to stdout. let json = serde_json::to_string_pretty(&result) - .map_err(|e| vortex_err!(Serde: "failed to serialize result: {e}"))?; + .map_err(|e| vortex_err!("failed to serialize result: {e}"))?; println!("{json}"); // Summary to stderr. @@ -215,7 +214,7 @@ pub fn check(dir: &Path, mode: Mode, exclude: &[String]) -> VortexResult<()> { for f in &result.failed { eprintln!(" FAIL {}: {}", f.name, f.error); } - vortex_bail!(AssertionFailed: "{} fixture(s) failed", result.failed.len()); + vortex_bail!("{} fixture(s) failed", result.failed.len()); } Ok(()) diff --git a/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs b/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs index 13f94358acd..ba24c20dc82 100644 --- a/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs +++ b/vortex-test/compat-gen/src/fixtures/arrays/datasets/clickbench.rs @@ -39,7 +39,7 @@ fn cached_clickbench_parquet() -> VortexResult { return Ok(dest); } - fs::create_dir_all(&data_dir).map_err(|e| vortex_err!(Io: "failed to create data dir: {e}"))?; + fs::create_dir_all(&data_dir).map_err(|e| vortex_err!("failed to create data dir: {e}"))?; // Download full partition 0 to a temp file. let source_bytes = download_with_retries(CLICKBENCH_URL)?; @@ -54,18 +54,18 @@ fn download_with_retries(url: &str) -> VortexResult { let client = reqwest::blocking::Client::builder() .timeout(std::time::Duration::from_secs(300)) .build() - .map_err(|e| vortex_err!(Io: "failed to build HTTP client: {e}"))?; + .map_err(|e| vortex_err!("failed to build HTTP client: {e}"))?; for attempt in 1..=MAX_RETRIES { match client.get(url).send() { Ok(response) if response.status().is_success() => { return response .bytes() - .map_err(|e| vortex_err!(Io: "failed to read response body: {e}")); + .map_err(|e| vortex_err!("failed to read response body: {e}")); } Ok(response) if response.status().is_client_error() => { return Err(vortex_err!( - Io: "HTTP {}: failed to download {url}", + "HTTP {}: failed to download {url}", response.status() )); } @@ -87,7 +87,7 @@ fn download_with_retries(url: &str) -> VortexResult { } Err(vortex_err!( - Io: "failed to download {url} after {MAX_RETRIES} attempts" + "failed to download {url} after {MAX_RETRIES} attempts" )) } @@ -95,7 +95,7 @@ fn download_with_retries(url: &str) -> VortexResult { fn sample_and_write(source_bytes: &[u8], dest: &std::path::Path) -> VortexResult<()> { let source_bytes = Bytes::copy_from_slice(source_bytes); let builder = ParquetRecordBatchReaderBuilder::try_new(source_bytes.clone()) - .map_err(|e| vortex_err!(Io: "failed to open source parquet: {e}"))?; + .map_err(|e| vortex_err!("failed to open source parquet: {e}"))?; let metadata = Arc::clone(builder.metadata()); let total_rows: usize = metadata @@ -135,35 +135,35 @@ fn sample_and_write(source_bytes: &[u8], dest: &std::path::Path) -> VortexResult let mut sampled_batches: Vec = Vec::new(); for &(rg_idx, local_offset, count) in &ranges { let reader = ParquetRecordBatchReaderBuilder::try_new(source_bytes.clone()) - .map_err(|e| vortex_err!(Io: "failed to open parquet for sampling: {e}"))? + .map_err(|e| vortex_err!("failed to open parquet for sampling: {e}"))? .with_row_groups(vec![rg_idx]) .with_offset(local_offset) .with_limit(count) .with_batch_size(count) .build() - .map_err(|e| vortex_err!(Serde: "failed to build parquet reader: {e}"))?; + .map_err(|e| vortex_err!("failed to build parquet reader: {e}"))?; for batch in reader { sampled_batches - .push(batch.map_err(|e| vortex_err!(Io: "failed to read parquet batch: {e}"))?); + .push(batch.map_err(|e| vortex_err!("failed to read parquet batch: {e}"))?); } } // Write sampled batches to a parquet file. let schema = sampled_batches[0].schema(); let combined = arrow_select::concat::concat_batches(&schema, &sampled_batches) - .map_err(|e| vortex_err!(InvalidArgument: "failed to concat batches: {e}"))?; + .map_err(|e| vortex_err!("failed to concat batches: {e}"))?; - let file = fs::File::create(dest) - .map_err(|e| vortex_err!(Io: "failed to create output parquet: {e}"))?; + let file = + fs::File::create(dest).map_err(|e| vortex_err!("failed to create output parquet: {e}"))?; let mut writer = parquet::arrow::ArrowWriter::try_new(file, schema, None) - .map_err(|e| vortex_err!(Serde: "failed to create parquet writer: {e}"))?; + .map_err(|e| vortex_err!("failed to create parquet writer: {e}"))?; writer .write(&combined) - .map_err(|e| vortex_err!(Io: "failed to write parquet: {e}"))?; + .map_err(|e| vortex_err!("failed to write parquet: {e}"))?; writer .close() - .map_err(|e| vortex_err!(Io: "failed to close parquet writer: {e}"))?; + .map_err(|e| vortex_err!("failed to close parquet writer: {e}"))?; Ok(()) } @@ -181,20 +181,19 @@ impl DatasetFixture for ClickBenchHits5kFixture { fn build(&self, arrow: &ArrowSession) -> VortexResult { let path = cached_clickbench_parquet()?; - let file_bytes = fs::read(&path).map_err( - |e| vortex_err!(Io: "failed to read cached parquet at {}: {e}", path.display()), - )?; + let file_bytes = fs::read(&path) + .map_err(|e| vortex_err!("failed to read cached parquet at {}: {e}", path.display()))?; let bytes = Bytes::from(file_bytes); let reader = ParquetRecordBatchReaderBuilder::try_new(bytes) - .map_err(|e| vortex_err!(Io: "failed to open parquet: {e}"))? + .map_err(|e| vortex_err!("failed to open parquet: {e}"))? .with_batch_size(1000) .build() - .map_err(|e| vortex_err!(Serde: "failed to build parquet reader: {e}"))?; + .map_err(|e| vortex_err!("failed to build parquet reader: {e}"))?; let batches: Vec = reader .collect::, _>>() - .map_err(|e| vortex_err!(Io: "failed to read parquet batches: {e}"))?; + .map_err(|e| vortex_err!("failed to read parquet batches: {e}"))?; Ok(ChunkedArray::from_iter( batches diff --git a/vortex-test/compat-gen/src/fixtures/mod.rs b/vortex-test/compat-gen/src/fixtures/mod.rs index 3f1e0d34437..3749a1f1483 100644 --- a/vortex-test/compat-gen/src/fixtures/mod.rs +++ b/vortex-test/compat-gen/src/fixtures/mod.rs @@ -184,7 +184,7 @@ pub fn check_expected_encodings( if !missing.is_empty() { vortex_bail!( - InvalidArgument: "fixture '{}' is missing expected encodings: {:?} (found: {:?})", + "fixture '{}' is missing expected encodings: {:?} (found: {:?})", fixture.name(), missing, found, diff --git a/vortex-test/compat-gen/src/generate.rs b/vortex-test/compat-gen/src/generate.rs index e4a066afc9a..a888a41bb5c 100644 --- a/vortex-test/compat-gen/src/generate.rs +++ b/vortex-test/compat-gen/src/generate.rs @@ -47,7 +47,7 @@ pub fn write_fixtures( } std::fs::create_dir_all(output_dir) - .map_err(|e| vortex_err!(Io: "failed to create output dir: {e}"))?; + .map_err(|e| vortex_err!("failed to create output dir: {e}"))?; eprintln!("generating {} fixtures...", fixtures.len()); @@ -57,7 +57,7 @@ pub fn write_fixtures( for entry in entries { let path = output_dir.join(&entry.name); let file_bytes = std::fs::read(&path) - .map_err(|e| vortex_err!(Io: "failed to read back {}: {e}", path.display()))?; + .map_err(|e| vortex_err!("failed to read back {}: {e}", path.display()))?; let sha256 = format!("{:x}", HexDisplay(&Sha256::digest(&file_bytes))); eprintln!(" wrote {}", entry.name); infos.push(FixtureInfo { @@ -75,9 +75,9 @@ pub fn write_fixtures( pub fn write_manifest(output_dir: &Path, infos: Vec) -> VortexResult<()> { let fixtures_json = FixturesJson { fixtures: infos }; let json = serde_json::to_string_pretty(&fixtures_json) - .map_err(|e| vortex_err!(Serde: "failed to serialize fixtures.json: {e}"))?; + .map_err(|e| vortex_err!("failed to serialize fixtures.json: {e}"))?; std::fs::write(output_dir.join("fixtures.json"), format!("{json}\n")) - .map_err(|e| vortex_err!(Io: "failed to write fixtures.json: {e}"))?; + .map_err(|e| vortex_err!("failed to write fixtures.json: {e}"))?; eprintln!(" wrote fixtures.json"); eprintln!( diff --git a/vortex-tui/src/browse/ui/segments.rs b/vortex-tui/src/browse/ui/segments.rs index 922af882821..a271b1195b1 100644 --- a/vortex-tui/src/browse/ui/segments.rs +++ b/vortex-tui/src/browse/ui/segments.rs @@ -119,7 +119,7 @@ pub fn segments_ui(app_state: &mut AppState, area: Rect, buf: &mut Buffer) { ); app_state.segment_grid_state.segment_tree = Some( to_display_segment_tree(segment_tree) - .map_err(|e| vortex_err!(Other: "Fail to compute segment tree {e}")) + .map_err(|e| vortex_err!("Fail to compute segment tree {e}")) .vortex_expect("operation should succeed in TUI"), ); } @@ -134,7 +134,7 @@ pub fn segments_ui(app_state: &mut AppState, area: Rect, buf: &mut Buffer) { height: AvailableSpace::Definite(area.height as f32), }; tree.compute_layout(*root_node, viewport_size) - .map_err(|e| vortex_err!(Other: "Fail to compute layout {e}")) + .map_err(|e| vortex_err!("Fail to compute layout {e}")) .vortex_expect("operation should succeed in TUI"); app_state.frame_size = area.as_size(); diff --git a/vortex-tui/src/inspect.rs b/vortex-tui/src/inspect.rs index ae7c4984300..038d57e4559 100644 --- a/vortex-tui/src/inspect.rs +++ b/vortex-tui/src/inspect.rs @@ -343,12 +343,12 @@ struct VortexInspector<'a> { impl<'a> VortexInspector<'a> { fn new(session: &'a VortexSession, path: PathBuf) -> VortexResult { - let mut file = File::open(&path) - .map_err(|e| vortex_err!(Io: "Failed to open file {:?}: {}", path, e))?; + let mut file = + File::open(&path).map_err(|e| vortex_err!("Failed to open file {:?}: {}", path, e))?; let file_size = file .seek(SeekFrom::End(0)) - .map_err(|e| vortex_err!(Io: "Failed to get file size: {}", e))?; + .map_err(|e| vortex_err!("Failed to get file size: {}", e))?; Ok(Self { session, @@ -361,7 +361,7 @@ impl<'a> VortexInspector<'a> { fn read_eof(&mut self) -> VortexResult { if self.file_size < EOF_SIZE as u64 { vortex_bail!( - InvalidArgument: "File too small ({} bytes) to contain EOF marker (requires {} bytes)", + "File too small ({} bytes) to contain EOF marker (requires {} bytes)", self.file_size, EOF_SIZE ); @@ -370,10 +370,10 @@ impl<'a> VortexInspector<'a> { let mut eof_bytes = [0u8; EOF_SIZE]; self.file .seek(SeekFrom::End(-(EOF_SIZE as i64))) - .map_err(|e| vortex_err!(Io: "Failed to seek to EOF: {}", e))?; + .map_err(|e| vortex_err!("Failed to seek to EOF: {}", e))?; self.file .read_exact(&mut eof_bytes) - .map_err(|e| vortex_err!(Io: "Failed to read EOF bytes: {}", e))?; + .map_err(|e| vortex_err!("Failed to read EOF bytes: {}", e))?; let version = u16::from_le_bytes([eof_bytes[0], eof_bytes[1]]); let postscript_size = u16::from_le_bytes([eof_bytes[2], eof_bytes[3]]); @@ -393,14 +393,14 @@ impl<'a> VortexInspector<'a> { let mut postscript_bytes = vec![0u8; postscript_size as usize]; self.file .seek(SeekFrom::Start(postscript_offset)) - .map_err(|e| vortex_err!(Io: "Failed to seek to postscript: {}", e))?; + .map_err(|e| vortex_err!("Failed to seek to postscript: {}", e))?; self.file .read_exact(&mut postscript_bytes) - .map_err(|e| vortex_err!(Io: "Failed to read postscript: {}", e))?; + .map_err(|e| vortex_err!("Failed to read postscript: {}", e))?; let postscript_buffer = ByteBuffer::from(postscript_bytes); let fb_postscript = root::(&postscript_buffer) - .map_err(|e| vortex_err!(Serde: "Failed to parse postscript flatbuffer: {}", e))?; + .map_err(|e| vortex_err!("Failed to parse postscript flatbuffer: {}", e))?; let segment_info = |s: fb::PostscriptSegment<'_>| -> VortexResult { Ok(SegmentInfo { @@ -416,7 +416,7 @@ impl<'a> VortexInspector<'a> { .layout() .map(segment_info) .transpose()? - .ok_or_else(|| vortex_err!(NotFound: "Postscript missing layout segment"))?; + .ok_or_else(|| vortex_err!("Postscript missing layout segment"))?; let statistics = fb_postscript.statistics().map(segment_info).transpose()?; @@ -424,7 +424,7 @@ impl<'a> VortexInspector<'a> { .footer() .map(segment_info) .transpose()? - .ok_or_else(|| vortex_err!(Serde: "Postscript missing footer segment"))?; + .ok_or_else(|| vortex_err!("Postscript missing footer segment"))?; Ok(PostscriptInfo { dtype, diff --git a/vortex-tui/src/query.rs b/vortex-tui/src/query.rs index 05ed4b1706f..fa789bef4dc 100644 --- a/vortex-tui/src/query.rs +++ b/vortex-tui/src/query.rs @@ -54,11 +54,11 @@ pub async fn exec_query(session: &VortexSession, args: QueryArgs) -> VortexResul let file_path = args .file .to_str() - .ok_or_else(|| vortex_err!(InvalidArgument: "Path is not valid UTF-8"))?; + .ok_or_else(|| vortex_err!("Path is not valid UTF-8"))?; let batches: Vec = execute_vortex_query(session, file_path, &args.sql) .await - .map_err(|e| vortex_err!(InvalidArgument: "{e}"))?; + .map_err(|e| vortex_err!("{e}"))?; // Build schema info from the result let schema = if let Some(batch) = batches.first() { @@ -82,7 +82,7 @@ pub async fn exec_query(session: &VortexSession, args: QueryArgs) -> VortexResul }; let json_output = serde_json::to_string_pretty(&output) - .map_err(|e| vortex_err!(Serde: "Failed to serialize JSON: {e}"))?; + .map_err(|e| vortex_err!("Failed to serialize JSON: {e}"))?; println!("{json_output}"); Ok(()) diff --git a/vortex-tui/src/segments.rs b/vortex-tui/src/segments.rs index 4baace28356..e8ca3d94ab7 100644 --- a/vortex-tui/src/segments.rs +++ b/vortex-tui/src/segments.rs @@ -106,7 +106,7 @@ pub async fn exec_segments(session: &VortexSession, args: SegmentsArgs) -> Vorte let output = SegmentsOutput { columns }; let json_output = serde_json::to_string_pretty(&output) - .map_err(|e| vortex::error::vortex_err!(Serde: "Failed to serialize JSON: {e}"))?; + .map_err(|e| vortex::error::vortex_err!("Failed to serialize JSON: {e}"))?; println!("{json_output}"); Ok(()) diff --git a/vortex-tui/src/tree.rs b/vortex-tui/src/tree.rs index 06e991d5b7f..64d0af2552a 100644 --- a/vortex-tui/src/tree.rs +++ b/vortex-tui/src/tree.rs @@ -115,7 +115,7 @@ async fn exec_layout_tree( if json { let tree = layout_to_json(Arc::clone(footer.layout()))?; let json_output = serde_json::to_string_pretty(&tree) - .map_err(|e| vortex::error::vortex_err!(Serde: "Failed to serialize JSON: {e}"))?; + .map_err(|e| vortex::error::vortex_err!("Failed to serialize JSON: {e}"))?; println!("{json_output}"); } else if verbose { // In verbose mode, fetch segments to display buffer sizes. diff --git a/vortex/benches/common_encoding_tree_throughput.rs b/vortex/benches/common_encoding_tree_throughput.rs index 559bb1bc628..e2bfcabfd4c 100644 --- a/vortex/benches/common_encoding_tree_throughput.rs +++ b/vortex/benches/common_encoding_tree_throughput.rs @@ -111,7 +111,7 @@ mod setup { match array.references() { FoRReferences::Global(reference) => reference.clone(), FoRReferences::Blocked(_) => { - vortex_panic!(AssertionFailed: "FoR::encode uses a global reference") + vortex_panic!("FoR::encode uses a global reference") } } } diff --git a/vortex/benches/pipeline.rs b/vortex/benches/pipeline.rs index 35be3862dd8..a53dba2e430 100644 --- a/vortex/benches/pipeline.rs +++ b/vortex/benches/pipeline.rs @@ -783,7 +783,7 @@ fn compare_outputs(function_name: &str, expected: &[f32], actual: &[f32], expect ); } vortex_panic!( - AssertionFailed: "{}: Output mismatch at index {}: expected={}, actual={}", + "{}: Output mismatch at index {}: expected={}, actual={}", function_name, i, expected_slice[i], diff --git a/vortex/src/editions/tests.rs b/vortex/src/editions/tests.rs index b4b37483429..c116f73796f 100644 --- a/vortex/src/editions/tests.rs +++ b/vortex/src/editions/tests.rs @@ -413,7 +413,7 @@ async fn disabling_editions_allows_uneditioned_components() -> VortexResult<()> .await .err() .ok_or_else(|| { - vortex_err!(AssertionFailed: "writer with no enabled editions accepted an extension dtype") + vortex_err!("writer with no enabled editions accepted an extension dtype") })?; assert!( error @@ -556,9 +556,10 @@ async fn writer_restricts_layouts_to_the_enabled_editions() -> VortexResult<()> // Dropping one of them fails the write at the layout it may not emit. let session = session_declaring(&members[1..])?; - let error = write_with(&session, array).await.err().ok_or_else( - || vortex_err!(AssertionFailed: "write emitted layout {} outside its edition", written[0]), - )?; + let error = write_with(&session, array) + .await + .err() + .ok_or_else(|| vortex_err!("write emitted layout {} outside its edition", written[0]))?; assert!( error.to_string().contains(&format!( "Layout encoding {} not permitted by ctx", @@ -651,7 +652,7 @@ async fn explicit_btrblocks_strategy_is_not_reconfigured() -> VortexResult<()> { ) .await .err() - .ok_or_else(|| vortex_err!(AssertionFailed: "explicit BtrBlocks strategy was unexpectedly reconfigured"))?; + .ok_or_else(|| vortex_err!("explicit BtrBlocks strategy was unexpectedly reconfigured"))?; assert!( error .to_string() @@ -682,9 +683,7 @@ async fn serialization_context_rejects_unsupported_compressor_output() -> Vortex ) .await .err() - .ok_or_else( - || vortex_err!(AssertionFailed: "Sequence unexpectedly had a permitted wire variant"), - )?; + .ok_or_else(|| vortex_err!("Sequence unexpectedly had a permitted wire variant"))?; assert!( error .to_string()