我有一个流程,其中一些数据(如图像/视频)使用GZip进行压缩,如下所示:
await using var outputStream = new MemoryStream();
await using var compressionStream = new GZipStream(outputStream, CompressionMode.Compress);
await compressionStream.WriteAsync(payload);
await compressionStream.FlushAsync();
outputStream.Position = 0;
return outputStream.ToArray()
上面的代码不是我的团队提供的,但如果需要可以更改
如果我将输出转换为base64字符串,并使用以下简单代码对其进行测试解压缩,它将非常有效:
var bytes = Convert.FromBase64String("H4sIAAAAAAAACirOz01VKEmtKAEAAAD//w=="); // "some text"
using var ms = new MemoryStream(bytes);
using var ds = new GZipStream(ms, CompressionMode.Decompress);
using var output = new MemoryStream();
ds.CopyTo(output);
ds.Flush();
var result = output.ToArray();
但是,我的要求是在python脚本中获取压缩的负载,并在将其传递到另一个系统之前对其进行解压缩。我对python一点也不熟悉,所以我编写了一个非常简单的脚本:
import base64
import gzip
encodedBase64 = "H4sIAAAAAAAACirOz01VKEmtKAEAAAD//w=="
decodedBytes = base64.standard_b64decode(encodedBase64)
decompressedBytes = gzip.decompress(decodedBytes)
上述操作失败:EOFError: Compressed file ended before the end-of-stream marker was reached
我当然做过研究并找到了类似this Q&A的帖子,但没有任何帮助(例如,使用该答案在gzip.BadGzipFile: Not a gzipped file (b'\x00\x00')
时失败)。其他尝试产生了不同的gzip错误
在读取} (也是由} 。我想这是有道理的,因为在编码过程中
GzipStream
的输出之前,需要先释放它。Gzip有一个需要添加到流末尾的页脚,它是added by ^{Close()
)但是not by ^{Flush()
可能会被多次调用,所以在这里添加页脚是错误的我重写了您的代码,以便在适当的点上处理对象,并且还去掉了
async
,因为您处理的是纯同步操作:这将产生输出
这比您看到的输出稍长,表明它包含Python所期望的页脚。不过,至少在.NET中,它仍然解码到相同的结果
有趣的是,.NET的
GzipStream
对缺少的页脚是健壮的,但是Python
的版本不是相关问题 更多 >
编程相关推荐