cocoindex-io/cocoindex · error · ValueError
Iggy does not support Kafka-style tombstones. Provide deleti
Error message
Iggy does not support Kafka-style tombstones. Provide deletion_value_fn or encode deletes in the payload.
What it means
Unlike Kafka, Iggy has no native tombstone records for deletes. When a reconciliation sees a desired state of non-existence and the connector has no deletion_value_fn configured, it raises ValueError rather than emitting an ambiguous delete.
Source
Thrown at python/cocoindex/connectors/iggy/_target.py:128
partitioning=self._partition,
messages=messages,
)
def reconcile(
self,
key: coco.StableKey,
desired_target_state: bytes | str | coco.NonExistenceType,
prev_possible_records: Collection[_MessageFingerprint],
prev_may_be_missing: bool,
/,
) -> coco.TargetReconcileOutput[_MessageAction, _MessageFingerprint] | None:
assert isinstance(key, (bytes, str))
if coco.is_non_existence(desired_target_state):
if not prev_possible_records and not prev_may_be_missing:
return None
if self._deletion_value_fn is None:
raise ValueError(
"Iggy does not support Kafka-style tombstones. "
"Provide deletion_value_fn or encode deletes in the payload."
)
deletion_value = self._deletion_value_fn(key)
return coco.TargetReconcileOutput(
action=_MessageAction(key=key, value=deletion_value),
sink=self._sink,
tracking_record=coco.NON_EXISTENCE,
)
# Upsert case
if isinstance(desired_target_state, bytes):
target_fp = fingerprint_bytes(desired_target_state)
else:
target_fp = fingerprint_str(desired_target_state)
if not prev_may_be_missing and all(
prev == target_fp for prev in prev_possible_recordsView on GitHub (pinned to e84aa99b32)
Solutions
- Provide deletion_value_fn when constructing the Iggy target so deletes can be encoded as a message value
- Encode deletes inside the normal payload (e.g. a flag in the message value) and handle them downstream
- If deletes are impossible/unnecessary, ensure prev records and prev_may_be_missing are handled so no delete action is generated
Example fix
// before target = iggy.TableTarget(client, stream="s", topic="t", ...) // after target = iggy.TableTarget(client, stream="s", topic="t", deletion_value_fn=lambda key: encode_tombstone(key), ...)
Defensive patterns
Strategy: validation
Validate before calling
if deletion_value_fn is None:
raise ValueError("Iggy target requires deletion_value_fn to handle deletes") Try / catch
try:
await app.update()
except ValueError as e:
if "tombstones" in str(e):
reconfigure_target_with_deletion_value_fn() Prevention
- Always configure deletion_value_fn for Iggy targets that can see deletions
- Model deletes explicitly in the payload schema and document downstream handling
- Test delete scenarios (source record removed) against the Iggy target before production
When it happens
Trigger: Reconcile output for a key with coco.is_non_existence(desired_target_state) (a delete) on an Iggy target constructed without deletion_value_fn — e.g. during update when a source record disappears.
Common situations: Source rows/files deleted between runs causing target deletes; switching a target from Kafka (tombstones supported) to Iggy without adapting delete handling.
Understand the failure class
Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.
Related errors
- build_node_delete requires at least one primary key field
- build_relationship_delete requires at least one primary key
- build_node_index_drop requires at least one field
- apache-iggy is required to use the Iggy connector. Please in
- Received an Iggy message for an untracked partition. Use an
AI-assisted analysis of cocoindex-io/cocoindex@e84aa99b32 (2026-09-08).
Data as JSON: /api/errors/c52aa82023b0435c.
Report an issue: GitHub.