MuntashirAkon/AppManager · error · BackupException
Destination doesn't contain any backup.
Error message
Destination doesn't contain any backup.
What it means
OABConverter parses an OAndBackup-style log file to rebuild backup metadata. The log's "backupMode" field is read with jsonObject.optInt("backupMode", MODE_UNSET); if the key is absent or unreadable, backupMode stays MODE_UNSET and the converter refuses to continue because it cannot tell whether the source backup contains APKs, data, or both. This is a hard precondition: without a known backup mode the conversion would produce an incomplete or wrong App Manager backup.
Source
Thrown at app/src/main/java/io/github/muntashirakon/AppManager/backup/convert/OABConverter.java:209
JSONObject jsonObject = new JSONObject(jsonString);
metadataV2.label = jsonObject.getString("label");
metadataV2.packageName = jsonObject.getString("packageName");
metadataV2.versionName = jsonObject.getString("versionName");
metadataV2.versionCode = jsonObject.getInt("versionCode");
metadataV2.isSystem = jsonObject.optBoolean("isSystem");
metadataV2.isSplitApk = false;
metadataV2.splitConfigs = ArrayUtils.emptyArray(String.class);
metadataV2.hasRules = false;
metadataV2.backupTime = jsonObject.getLong("lastBackupMillis");
metadataV2.crypto = jsonObject.optBoolean("isEncrypted") ? CryptoUtils.MODE_OPEN_PGP : CryptoUtils.MODE_NO_ENCRYPTION;
mSourceCryptoMode = metadataV2.crypto;
mSourceCrypto = CryptoUtils.setupCrypto(metadataV2);
metadataV2.apkName = new File(jsonObject.getString("sourceDir")).getName();
// Flags
metadataV2.flags = new BackupFlags(BackupFlags.BACKUP_MULTIPLE);
int backupMode = jsonObject.optInt("backupMode", MODE_UNSET);
if (backupMode == MODE_UNSET) {
throw new BackupException("Destination doesn't contain any backup.");
}
if (backupMode == MODE_APK || backupMode == MODE_BOTH) {
if (mBackupLocation.hasFile(CryptoUtils.getAppropriateFilename(metadataV2.apkName,
mSourceCryptoMode))) {
metadataV2.flags.addFlag(BackupFlags.BACKUP_APK_FILES);
} else {
throw new BackupException("Destination doesn't contain any APK files.");
}
}
if (backupMode == MODE_DATA || backupMode == MODE_BOTH) {
boolean hasBackup = false;
if (mBackupLocation.hasFile(CryptoUtils.getAppropriateFilename(mPackageName + ".zip",
mSourceCryptoMode))) {
metadataV2.flags.addFlag(BackupFlags.BACKUP_INT_DATA);
hasBackup = true;
}
if (mBackupLocation.hasFile(EXTERNAL_FILES) && mBackupLocation.findFile(EXTERNAL_FILES).hasFile(
CryptoUtils.getAppropriateFilename(mPackageName + ".zip", mSourceCryptoMode))) {View on GitHub (pinned to 0152f468fc)
Solutions
- Check the source log file and ensure it contains a numeric "backupMode" entry (0/1/2 per OAndBackup's MODE_APK/MODE_DATA/MODE_BOTH convention).
- Re-create the backup with the original OAndBackup app so a fresh, complete log file is generated.
- If the log is hand-edited or migrated, add the missing "backupMode" key with the correct value instead of leaving it absent.
- Verify you are passing the correct log file (e.g. the per-package log, not a global index) to OABConverter.convert().
Example fix
// before: converting a log file that lacks the field
// { "packageName": "com.example", "apkName": "base.apk" }
// after: fix the source log JSON
// { "packageName": "com.example", "apkName": "base.apk", "backupMode": 2 } Defensive patterns
Strategy: validation
Validate before calling
JSONObject log = readLogJson(logFile);
if (!log.has("backupMode") || log.optInt("backupMode", MODE_UNSET) == MODE_UNSET) {
throw new IllegalArgumentException(logFile + " has no valid backupMode; cannot convert");
} Type guard
static boolean hasBackupMode(JSONObject log) {
return log.has("backupMode") && log.optInt("backupMode", Integer.MIN_VALUE) != Integer.MIN_VALUE;
} Try / catch
try {
converter.convert(...);
} catch (BackupException e) {
if (e.getMessage().contains("doesn't contain any backup")) {
Log.e(TAG, "Log file missing backupMode: inspect " + logFile, e);
}
} Prevention
- Always generate backups with a current OAndBackup version that writes backupMode into the log.
- Validate required log keys (packageName, apkName, backupMode) before invoking the converter.
- Never hand-edit backup log files; regenerate them from the source app.
When it happens
Trigger: readLogFile() (called from convert()) encounters a log JSON object where key "backupMode" is missing, or its value parses to MODE_UNSET, i.e. jsonObject.optInt("backupMode", MODE_UNSET) returns MODE_UNSET at OABConverter.java:209.
Common situations: Converting an OAndBackup log written by an older app version that did not record backupMode; a corrupted or truncated log file where the backupMode entry was lost; hand-edited log files; pointing the converter at a metadata/log file of a different format that lacks this key.
Understand the failure class
Background: "is required", "must be set", "missing required field": configuration validation errors across open-source libraries — this error's family across 36 libraries.
Related errors
- Could not retrieve metadata from backup.
- Failed to setup metadata.
- Failed to write metadata.
- Could not read backup metadata. Possibly due to a malformed
- Could not get metadata file.
AI-assisted analysis of MuntashirAkon/AppManager@0152f468fc (2026-09-12).
Data as JSON: /api/errors/c6f846bc79f9d966.
Report an issue: GitHub.