apache/cassandra · error · InvalidRequestException

Invalid unset map key for column

Error message

Invalid unset map key for column %s

What it means

Thrown by SimpleRestriction.addToRowFilter when the map key of a map-column restriction is the UNSET sentinel byte buffer. Cassandra treats UNSET as 'do not apply this binding', which is meaningless for a map key inside a row filter, so it is rejected.

Solutions

  1. Bind a concrete non-null key value to the map key parameter instead of unset.
  2. Rebuild the statement without the map-key restriction when the key is unknown, rather than leaving it unset.
  3. Treat unset as a client-side error: validate all bound key positions are set before executing.
  4. Avoid unset semantics for map keys; only the restriction's value parameter can safely be omitted logic-wise.

Example fix

// before
boundStatement.setToUnset(i); // key left unset
// after
if (key == null) throw new IllegalArgumentException("map key required");
boundStatement.setByteBuffer(i, key);
Defensive patterns

Strategy: validation

Validate before calling

if (mapKey == null || isUnset(mapKey)) throw new IllegalArgumentException("map key must be bound to a concrete value");

Type guard

boolean isSet(ByteBuffer b) { return b != null && b != ByteBufferUtil.UNSET_BYTE_BUFFER; }

Try / catch

try { session.execute(stmt); } catch (InvalidRequestException e) { if (e.getMessage().contains("unset map key")) rebuildQueryWithoutMapRestriction(); else throw e; }

Prevention

When it happens

Trigger: Executing `WHERE m[?] = ?` where the driver binds the key parameter as unset (e.g. unsetByteBuffer() / omitted named parameter), so columnsExpression.element(context) returns ByteBufferUtil.UNSET_BYTE_BUFFER.

Common situations: Drivers using named/unset parameter semantics (Java driver setToUnset) where callers skip a parameter assuming it is ignored; batch templates with optional map-key lookups left unset.

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


AI-assisted analysis of apache/cassandra@88fd0f6a0e (2026-09-10). Data as JSON: /api/errors/a677721918bbdf40. Report an issue: GitHub.

Appendix: source

Thrown at src/java/org/apache/cassandra/cql3/restrictions/SimpleRestriction.java:458

                    // either directly or via filtering. If not, throw an error.
                    if (column.type.isFrozenCollection())
                    {
                        for (Index index : indexRegistry.listIndexes())
                        {
                            if (index.dependsOn(column)
                                && !index.supportsMapElementExpression()
                                && !index.supportsFilteringOnMapElementExpression())
                            {
                                throw invalidRequest(Relation.FROZEN_MAP_ENTRY_PREDICATES_NOT_SUPPORTED, column.name);
                            }
                        }
                    }

                    ByteBuffer key = columnsExpression.element(context);
                    if (key == null)
                        throw invalidRequest("Invalid null map key for column %s", column.name.toCQLString());
                    if (key == ByteBufferUtil.UNSET_BYTE_BUFFER)
                        throw invalidRequest("Invalid unset map key for column %s", column.name.toCQLString());
                    List<ByteBuffer> values = bindAndGet(context);
                    filter.addMapEquality(column, key, operator, values.get(0));
                }
                break;
            default: throw new UnsupportedOperationException();
        }
    }

    private static ByteBuffer multiInputOperatorValues(ColumnMetadata column, List<ByteBuffer> values)
    {
        return ListType.getInstance(column.type, false).pack(values);
    }

    @Override
    public String toString()
    {
        return operator.buildCQLString(columnsExpression, values);
    }

View on GitHub (pinned to 88fd0f6a0e)