{"record":{"id":"e33169b4c2d2008a","repo":"shwenzhang/AndResGuard","slug":"keystorefile-contains-multiple-key-entries-ks-key-alias","errorCode":null,"errorMessage":"<keystoreFile> contains multiple key entries. --ks-key-alias option must be used to specify which entry to use.","messagePattern":"<keystoreFile> contains multiple key entries\\. --ks-key-alias option must be used to specify which entry to use\\.","errorType":"validation","errorClass":"ParameterException","httpStatus":null,"severity":"error","filePath":"AndResGuard-core/src/main/java/apksigner/ApkSignerTool.java","lineNumber":705,"sourceCode":"        keystorePasswords = passwordRetriever.getPasswords(keystorePasswordSpec, \"Keystore password for \" + name);\n        loadKeyStoreFromFile(ks, keystoreFile, keystorePasswords);\n      }\n\n      // 3. Load the PrivateKey and cert chain from KeyStore\n      String keyAlias = null;\n      PrivateKey key = null;\n      try {\n        if (keystoreKeyAlias == null) {\n          // Private key entry alias not specified. Find the key entry contained in this\n          // KeyStore. If the KeyStore contains multiple key entries, return an error.\n          Enumeration<String> aliases = ks.aliases();\n          if (aliases != null) {\n            while (aliases.hasMoreElements()) {\n              String entryAlias = aliases.nextElement();\n              if (ks.isKeyEntry(entryAlias)) {\n                keyAlias = entryAlias;\n                if (keystoreKeyAlias != null) {\n                  throw new ParameterException(keystoreFile\n                                               + \" contains multiple key entries\"\n                                               + \". --ks-key-alias option must be used to specify\"\n                                               + \" which entry to use.\");\n                }\n                keystoreKeyAlias = keyAlias;\n              }\n            }\n          }\n          if (keystoreKeyAlias == null) {\n            throw new ParameterException(keystoreFile + \" does not contain key entries\");\n          }\n        }\n\n        // Private key entry alias known. Load that entry's private key.\n        keyAlias = keystoreKeyAlias;\n        if (!ks.isKeyEntry(keyAlias)) {\n          throw new ParameterException(keystoreFile + \" entry \\\"\" + keyAlias + \"\\\" does not contain a key\");\n        }","sourceCodeStart":687,"sourceCodeEnd":723,"githubUrl":"https://github.com/shwenzhang/AndResGuard/blob/e4df245d82f27d9a2d0dd108260a3510cbaba849/AndResGuard-core/src/main/java/apksigner/ApkSignerTool.java#L687-L723","documentation":"apksigner's keystore loader iterates all aliases in the keystore and picks the first key entry as the signing key. When a second key entry is found while --ks-key-alias was not given, the ambiguity is unrecoverable, so a ParameterException is thrown telling the user to explicitly name which alias to sign with.","triggerScenarios":"Running apksigner sign (or loadPrivateKeyAndCerts via loadPrivateKeyAndCertsFromKeyStore) with a --ks file that contains two or more KeyEntry aliases (multiple private keys) while omitting the --ks-key-alias option.","commonSituations":"Developers reuse a debug keystore that accumulated several generated keys over time; CI pipelines migrated from a single-key keystore to a multi-key one; teams share one keystore holding release and debug signing keys; Android Studio-generated keystores later merged with another keystore.","solutions":["Pass the desired alias explicitly: apksigner sign --ks my.keystore --ks-key-alias <alias> ...","List the keystore entries first with keytool -list -keystore my.keystore to see available aliases and pick the right one.","If the extra entries are obsolete, delete them or create a keystore containing only the signing key.","In calling code, resolve/verify the alias before invoking (KeyStore.aliases() + isKeyEntry) and pass it to the signer."],"exampleFix":"// before\napksigner sign --ks release.keystore --ks-key-pass ... --out app.apk app-unsigned.apk\n// after\napksigner sign --ks release.keystore --ks-key-alias release --ks-key-pass ... --out app.apk app-unsigned.apk","handlingStrategy":"validation","validationCode":"KeyStore ks = KeyStore.getInstance(\"PKCS12\");\ntry (FileInputStream in = new FileInputStream(ksFile)) { ks.load(in, storePassword); }\njava.util.List<String> keyAliases = new java.util.ArrayList<>();\njava.util.Enumeration<String> a = ks.aliases();\nwhile (a.hasMoreElements()) { String al = a.nextElement(); if (ks.isKeyEntry(al)) keyAliases.add(al); }\nif (keyAliases.size() > 1 && keyAliasArg == null)\n    throw new IllegalArgumentException(\"Keystore has multiple key entries; pass --ks-key-alias. Found: \" + keyAliases);","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Always pass --ks-key-alias in build scripts so behavior is explicit","Run keytool -list -keystore ... in CI before signing to confirm the alias exists","Keep one signing key per keystore file","Pin the exact keystore file + alias pair in Gradle/CI config"],"tags":["keystore","apksigner","android-signing","cli"],"backgroundTag":"missing-required-option","analyzedSha":"e4df245d82f27d9a2d0dd108260a3510cbaba849","analyzedAt":"2026-09-12T17:49:07.798Z","contentChangedAt":"2026-09-12T17:49:07.798Z","schemaVersion":2},"datasetVersion":"2026-09-16T09:17:16.951Z"}