databendlabs/databend · critical

internal error: entered unreachable code

Error message

internal error: entered unreachable code

What it means

This is an internal invariant panic inside Databend's lambda-function type checker. When resolving a lambda for a map function (map_filter, map_transform_keys, map_transform_values), the code assumes the map's inner type is a Tuple (key, value); any other inner type (e.g. Variant or Array left over from a JSON auto-cast) hits `unreachable!()` and panics with "entered unreachable code". It signals a type-checking gap, not a user-facing semantic error.

Solutions

  1. Inspect the actual data type of the lambda argument with SELECT typeof(col) and ensure it is a MAP whose inner type is TUPLE(key, value)
  2. If the column is Variant, first cast it explicitly to the intended shape: CAST(col AS MAP(VARCHAR, VARIANT)) or ARRAY(...) before applying the map lambda
  3. If the JSON value is an array, use array_* lambda functions (array_filter, array_transform) instead of map_*
  4. If the type is genuinely a Map but the panic still occurs, this is a planner bug — capture the full query and EXPLAIN output and report it to Databend

Example fix

// before: map_filter on a Variant holding a JSON array
SELECT map_filter(v, (k, v2) -> k = 'a') FROM t;
// after: cast to the correct type or use the array lambda
SELECT array_filter(v, x -> x['k'] = 'a') FROM t; -- if v is a JSON array
Defensive patterns

Strategy: validation

Validate before calling

-- run before the lambda query
SELECT typeof(arg_col) FROM t LIMIT 1;
-- expect MAP(VARCHAR NULL, VARIANT NULL) or similar tuple-backed Map

Type guard

fn is_map_type(ty: &str) -> bool { ty.starts_with("MAP(") }

Prevention

When it happens

Trigger: Calling a map_* lambda function (e.g. map_filter(m, (k,v) -> ...)) where the argument type was auto-cast from Variant and its inner type resolves to something other than Tuple or Null — e.g. the argument is actually an array or a bare variant that got cast to Map(NonTupleType).

Common situations: Querying JSON/Variant columns with map lambda functions when the JSON value is not an object (e.g. it is a JSON array); mismatched function/argument families such as map_* lambdas over arrays; Databend version upgrades that change auto-cast behavior for Variant arguments.

Understand the failure class

Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.

Related errors


AI-assisted analysis of databendlabs/databend@288d84d76e (2026-09-11). Data as JSON: /api/errors/403b5d22a8d4c24e. Report an issue: GitHub.

Appendix: source

Thrown at src/query/sql/src/planner/semantic/type_check/lambda.rs:323

                        .to_string(),
                )
                .set_span(span));
            }
        };

        let inner_tys = if func_name == "array_reduce" {
            let max_ty = self.transform_to_max_type(&inner_ty)?;
            vec![max_ty.clone(), max_ty.clone()]
        } else if func_name == "map_filter"
            || func_name == "map_transform_keys"
            || func_name == "map_transform_values"
        {
            match &inner_ty {
                DataType::Null => {
                    vec![DataType::Null, DataType::Null]
                }
                DataType::Tuple(t) => t.clone(),
                _ => unreachable!(),
            }
        } else {
            vec![inner_ty.clone()]
        };

        let lambda_columns = params
            .iter()
            .zip(inner_tys.iter())
            .map(|(col, ty)| (col.clone(), ty.clone()))
            .collect::<Vec<_>>();

        let mut lambda_context = self.bind_context.clone();
        let box (lambda_expr, lambda_type) = self.resolve_core_lambda_expr(
            arena,
            &mut lambda_context,
            &lambda_columns,
            lambda_expr,
        )?;

View on GitHub (pinned to 288d84d76e)