apache/hadoop · error · IllegalArgumentException

KeyVersion '%s' does not belong to the key '%s'

Error message

KeyVersion '%s' does not belong to the key '%s'

What it means

The second check in verifyKeyVersionBelongsToKey (line 259): the referenced key version exists, but its key name does not equal the encryption key name carried in the EncryptedKeyVersion (the name field of the decrypt request). It throws IllegalArgumentException "KeyVersion '<v>' does not belong to the key '<k>'" (HTTP 400), catching client requests that mix a version name from one key with the name of another.

Source

Thrown at hadoop-common-project/hadoop-kms/src/main/java/org/apache/hadoop/crypto/key/kms/server/KeyAuthorizationKeyProvider.java:259

    try {
      doAccessCheck(encryptionKeyName, KeyOpType.GENERATE_EEK);
      return provider.generateEncryptedKey(encryptionKeyName);
    } finally {
      readLock.unlock();
    }
  }

  private void verifyKeyVersionBelongsToKey(EncryptedKeyVersion ekv)
      throws IOException {
    String kn = ekv.getEncryptionKeyName();
    String kvn = ekv.getEncryptionKeyVersionName();
    KeyVersion kv = provider.getKeyVersion(kvn);
    if (kv == null) {
      throw new IllegalArgumentException(String.format(
          "'%s' not found", kvn));
    }
    if (!kv.getName().equals(kn)) {
      throw new IllegalArgumentException(String.format(
          "KeyVersion '%s' does not belong to the key '%s'", kvn, kn));
    }
  }

  @Override
  public KeyVersion decryptEncryptedKey(EncryptedKeyVersion encryptedKeyVersion)
          throws IOException, GeneralSecurityException {
    readLock.lock();
    try {
      verifyKeyVersionBelongsToKey(encryptedKeyVersion);
      doAccessCheck(
          encryptedKeyVersion.getEncryptionKeyName(), KeyOpType.DECRYPT_EEK);
      return provider.decryptEncryptedKey(encryptedKeyVersion);
    } finally {
      readLock.unlock();
    }
  }

View on GitHub (pinned to 2add963021)

Solutions

  1. Send the key name that actually owns the version: both values come from the same generateEncryptedKey response (EncryptedKeyVersion.getEncryptionKeyName/VersionName)
  2. Fix client code that stores or passes key name and version name independently — keep them as one EDEK record
  3. Verify with GET /v1/keyversion/{versionName} which key the version belongs to before decrypting

Example fix

# before: version from keyB sent with name keyA
{"name":"keyA","iv":"...","material":"..."} -> /v1/keyversion/keyB@0/_eek
# after: consistent pair
{"name":"keyB","iv":"...","material":"..."} -> /v1/keyversion/keyB@0/_eek
Defensive patterns

Strategy: validation

Validate before calling

KeyVersion kv = provider.getKeyVersion(ekv.getEncryptionKeyVersionName());
if (kv != null && !kv.getName().equals(ekv.getEncryptionKeyName()))
  throw new IllegalStateException("EDEK key/version mismatch: " + ekv.getEncryptionKeyName() + " vs " + kv.getName());

Try / catch

try { provider.decryptEncryptedKey(ekv); } catch (IllegalArgumentException e) { if (e.getMessage().contains("does not belong")) { /* fix client pairing of name and version */ } else throw e; }

Prevention

When it happens

Trigger: POST /v1/keyversion/{versionName}/_eek?eek_op=decrypt where versionName belongs to key B but the JSON body's name field (and EDEK material) names key A — e.g. hand-assembled decrypt requests, or a client bug that pairs an EDEK with the wrong key name.

Common situations: Manual curl testing with mismatched name/version pairs; client code caching version names across keys; refactoring that swapped key name and version name fields; multi-key applications mixing up per-key EDEK state.

Related errors


AI-assisted analysis of apache/hadoop@2add963021 (2026-08-22). Data as JSON: /api/errors/6245ba976bf43af0. Report an issue: GitHub.