Calculate differences between two manifests.
Patches are compared by UUID: if the PURL exists in both manifests but the
UUID changed, the patch is considered modified.
Get only afterHash blobs referenced by a manifest.
Used for apply operations – we only need the patched file content, not the original.
This saves disk space since beforeHash blobs are not needed for applying patches.
Read and parse a manifest from the filesystem.
Returns Ok(None) if the file does not exist.
Returns Err for I/O errors, JSON parse errors, or validation errors.