我正在尝试用C#压缩xml并将其编码为base64。我尝试同时使用DeflateStream和GZipStream,但我似乎得到的结果与在节点库中使用的结果不同。
我将发布节点代码和 c# 代码:
//zlib = require('zlib');
zlib.deflateRaw(xml, (function(_this) {
return function(err, deflated) {
return deflated.toString('base64');
}
}
C# DeflateStream
private static byte[] Deflate(String str)
{
using (MemoryStream output = new MemoryStream())
{
using (DeflateStream gzip =
new DeflateStream(output, CompressionMode.Compress))
{
using (StreamWriter writer =
new StreamWriter(gzip, System.Text.Encoding.UTF8))
{
writer.Write(str);
}
}
return output.ToArray();
}
}
C# GZipStream
public static byte[] Zip(string str)
{
var bytes = Encoding.UTF8.GetBytes(str);
using (var msi = new MemoryStream(bytes))
using (var mso = new MemoryStream())
{
using (var gs = new GZipStream(mso, CompressionMode.Compress))
{
//msi.CopyTo(gs);
CopyTo(msi, gs);
}
return mso.ToArray();
}
}
C# Base64 编码:
private static string Base64Encode(byte[] textBytes)
{
return System.Convert.ToBase64String(textBytes);
}
我错过了什么吗?
更新
我找到了一个有效的例子。通过使用这个,我也可以使用 Node 对其进行解码。
var bytes = Encoding.UTF8.GetBytes(stringToDeflate);
using (var output = new MemoryStream())
{
using (var zip = new DeflateStream(output, CompressionMode.Compress))
{
zip.Write(bytes, 0, bytes.Length);
}
var base64 = Convert.ToBase64String(output.ToArray());
}
更新 2(工作代码 - 供未来的搜索者使用(
private static string DeflateAndEncode(string str)
{
var bytes = Encoding.UTF8.GetBytes(str);
using (var output = new MemoryStream())
{
using (var zip = new DeflateStream(output, CompressionMode.Compress))
{
zip.Write(bytes, 0, bytes.Length);
}
var base64 = Convert.ToBase64String(output.ToArray());
return base64;
}
}
private static string DecodeAndInflate(string str)
{
var utf8 = Encoding.UTF8;
var bytes = Convert.FromBase64String(str);
using (var output = new MemoryStream())
{
using (var input = new MemoryStream(bytes))
{
using (var unzip = new DeflateStream(input, CompressionMode.Decompress))
{
unzip.CopyTo(output, bytes.Length);
unzip.Close();
}
return utf8.GetString(output.ToArray());
}
}
}
用于 base-64 编码的字符在 C# 和 Node.js 之间有所不同。
C# 使用以下内容:
从零升序排列的 64 进制数字是大写字符"A"到"Z"、小写字符"a"到"z"、数字"0"到"9"以及符号"+"和"/"。无值字符"="用于尾随填充。
Node.js 使用RFC4648第 5 节中指定的"URL 和文件名安全"基础 64 字母表":
A-Z, a-z, 0-9, - (minus), _ (underscore)
Trailing padding uses '='
所以你想做的事情是行不通的。
您可以通过分别用+
和/
替换_
和-
字符来修复它,以将 C# 编码转换为 Node.js,反之亦然,然后再对 base64 解码数据。