Windows与Linux下.NET 9计算SHA256哈希结果不一致问题
解决.NET 9下Windows本地SHA256哈希单元测试失败问题
问题根源
你的测试失败核心原因是字符串转字节的过程破坏了原始文件的字节结构,且.NET 9的平台行为差异放大了这个问题:
- 原代码通过
StreamReader.ReadToEnd()读取嵌入资源为字符串,再用Encoding.UTF8.GetBytes()转字节数组:- StreamReader默认会自动识别编码(无BOM时,Windows和Linux可能用不同默认编码),导致字节转换不一致
- StreamReader读取时会自动转换换行符(Windows的CRLF转为LF),直接修改了原始文件的字节内容
- 直接读取CDN流计算哈希用的是原始字节,所以结果和官方一致;而字符串转字节的方式改变了数据,导致哈希不符。
解决方案
方案1:直接读取嵌入资源的原始字节(推荐)
跳过字符串转换环节,直接读取资源的原始字节数组,完全避免编码和换行符干扰:
// 修改资源读取方法为返回字节数组 public static byte[] GetFileBytes(string filename) { var assembly = typeof(TestResources).GetTypeInfo().Assembly; using var resource = assembly.GetManifestResourceStream(filename)!; using var ms = new MemoryStream(); resource.CopyTo(ms); return ms.ToArray(); } // 更新测试代码 [Fact] public void Test() { const string Expected = "/JqT3SQfawRcv/BIHPThkBvs0OEvtFFmqPF/lYI/Cxo="; var fileBytes = TestResources.GetFileBytes("MyTests.Resources.jquery-3.7.1.min.js"); var sha256Hasher = SHA256.Create(); var byteResult = sha256Hasher.ComputeHash(fileBytes); var result = Convert.ToBase64String(byteResult); result.Should().Be(Expected); }
方案2:强制StreamReader使用UTF-8且禁用换行转换
如果必须读取为字符串,需明确指定编码并关闭自动换行转换:
// 修改资源读取方法 public static string GetFileContents(string filename) { var assembly = typeof(TestResources).GetTypeInfo().Assembly; using var resource = assembly.GetManifestResourceStream(filename)!; // 指定UTF-8编码,禁用BOM检测和换行符转换 using var reader = new StreamReader( resource, Encoding.UTF8, detectEncodingFromByteOrderMarks: false, leaveOpen: false, newLine: null); var result = reader.ReadToEnd(); return result; }
额外检查项
- 确认嵌入的
jquery-3.7.1.min.js和官方文件完全一致:导出本地嵌入资源,与CDN下载文件对比哈希,避免编辑器自动修改换行符或编码 - 检查项目文件的
<EmbeddedResource>配置:确保未启用TransformOnBuild等会修改资源内容的构建选项
内容的提问来源于stack exchange,提问作者Marthijn
相关产品推荐
相关产品推荐

