Grzegorz Liter created FLINK-40442:
--------------------------------------

             Summary: State Processor API re-derives a key's key-group from 
hashCode() instead of reusing the one it read the key from — breaks reading old 
state after any hashCode() change
                 Key: FLINK-40442
                 URL: https://issues.apache.org/jira/browse/FLINK-40442
             Project: Flink
          Issue Type: Improvement
          Components: API / State Processor
            Reporter: Grzegorz Liter


When reading keyed state with SavepointReader.readKeyedState(), each key is 
discovered by iterating storage per key-group — the backend already knows which 
key-group a key lives under while doing this. But KeyedStateInputFormat throws 
that away and calls setCurrentKey(key), which recomputes the key-group from 
key.hashCode() instead of reusing the one it was just found under. If 
hashCode()/equals() for that key type ever changed since the savepoint was 
written, the recomputed key-group can disagree with where the key actually 
lives, and you get:

{code}
Key group X is not in KeyGroupRange\{...}
{code}

This makes affected state permanently unreadable via the State Processor API — 
even though it's fully intact and a live streaming job restores it fine (live 
restore only computes a key-group once, when a new record first arrives; it 
never re-derives one for already-stored keys).

This is exactly the failure mode reported in AVRO-4334 (Avro's Utf8.hashCode() 
changing undocumented between 1.12.0 and 1.12.1). Fixing whatever caused a 
hashCode() to drift doesn't help with data already written under the old hash — 
this bug is what stands between that state and being repairable at all.

Proposed fix

AbstractKeyedStateBackend already has setCurrentKeyAndKeyGroup(key, 
keyGroupIndex) — sets both explicitly, no hashCode recompute (already used by 
ChangelogKeyedStateBackend today). KeyedStateInputFormat/MultiStateKeyIterator 
already have the discovered key-group in hand when iterating; passing it 
through and calling setCurrentKeyAndKeyGroup() instead of setCurrentKey() would 
make the read path immune to hashCode drift, with no change to the shared 
validation itself.

(Not proposing relaxing the check itself — it's shared with live restore and, 
for RocksDB, is the only thing stopping a wrong key-group from being written as 
a literal storage-key prefix. The fix above is scoped entirely to the State 
Processor API's own key iteration.)

Affected classes: org.apache.flink.state.api.input.KeyedStateInputFormat, 
MultiStateKeyIterator (flink-state-processing-api)



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to