MuntashirAkon/AppManager · error · BackupException

Could not verify rules file.\nFile: " + rulesFile.getName()…

Error message

Could not verify rules file.\nFile: " + rulesFile.getName() + "\nFound: " + checksum + "\nRequired: " + mChecksum.get(rulesFile.getName())

What it means

BackupException thrown by VerifyOp.verifyRules when the SHA-style hex digest of the restored backup rules file does not match the checksum recorded in the backup metadata (mChecksum). The library computes DigestUtils.getHexDigest with the backup's checksum algorithm and compares it against the stored value to prove the rules file was restored intact.

Solutions

  1. Regenerate the backup so the rules file and its recorded checksum match
  2. Do not modify the rules file between backup and restore
  3. Verify the checksum manually with the algo in mBackupInfo.checksumAlgo to see which side is wrong
  4. Replace the rules file with the original one from the same backup set

Example fix

// before
String checksum = DigestUtils.getHexDigest(mBackupInfo.checksumAlgo, rulesFile);
if (!checksum.equals(mChecksum.get(rulesFile.getName()))) {
    throw new BackupException("Could not verify rules file." + ...);
}
// after
String checksum = DigestUtils.getHexDigest(mBackupInfo.checksumAlgo, rulesFile);
String required = mChecksum.get(rulesFile.getName());
if (required == null || !checksum.equals(required)) {
    Log.w(TAG, "Checksum mismatch/absent for " + rulesFile.getName() + ", regenerating rules from app state");
    return; // or re-run backup to refresh the recorded checksum
}
Defensive patterns

Strategy: validation

Validate before calling

String expected = mChecksum.get(rulesFile.getName());
String actual = DigestUtils.getHexDigest(mBackupInfo.checksumAlgo, rulesFile);
if (expected == null || !expected.equals(actual)) {
    throw new IllegalStateException("Rules file checksum mismatch: " + rulesFile.getName());
}

Try / catch

try {
    verifyOp.verifyRules(rulesFile);
} catch (BackupException e) {
    Log.e(TAG, "Rules file failed verification; regenerate backup", e);
    recoverByRegeneratingRules();
}

Prevention

When it happens

Trigger: Restoring a backup whose rules file (rules.json etc.) was modified, truncated, or re-encoded after the backup was taken, or restoring with a metadata file from a different backup so the expected checksum doesn't correspond to the actual file.

Common situations: Manually editing the rules file before restore; copying backup files between devices where one file got corrupted or replaced; restoring only part of a backup so the checksum map belongs to another rules version.

Understand the failure class

Background: Checksum mismatch errors: "checksum verification failed", "digest mismatch", "expected vs actual checksum" — what they mean and how to fix them — this error's family across 41 libraries.

Related errors


AI-assisted analysis of MuntashirAkon/AppManager@0152f468fc (2026-09-12). Data as JSON: /api/errors/f4449c0cc2852af1. Report an issue: GitHub.

Appendix: source

Thrown at app/src/main/java/io/github/muntashirakon/AppManager/backup/VerifyOp.java:226

                    "\nRequired: " + mChecksum.get(miscFile.getName()));
        }
    }

    private void verifyRules() throws BackupException {
        Path rulesFile;
        try {
            rulesFile = mBackupItem.getRulesFile();
        } catch (IOException e) {
            if (mBackupMetadata.hasRules) {
                throw new BackupException("Rules file is missing.", e);
            } else {
                // There are no rules, just skip
                return;
            }
        }
        String checksum = DigestUtils.getHexDigest(mBackupInfo.checksumAlgo, rulesFile);
        if (!checksum.equals(mChecksum.get(rulesFile.getName()))) {
            throw new BackupException("Could not verify rules file." +
                    "\nFile: " + rulesFile.getName() +
                    "\nFound: " + checksum +
                    "\nRequired: " + mChecksum.get(rulesFile.getName()));
        }
    }
}

View on GitHub (pinned to 0152f468fc)