我一直在编写和阅读PDF文件到SQL Server 2008 FileStream几个月,没有任何重大问题(除了繁琐的用户权限)。昨天我有一个用户告诉我,他们的一些PDF在写入FileStream后被破坏了。所以,我做了一些调试,我发现了问题,但它似乎是SqlFileStream库的一个错误,它将文件写入FileStream。
这是我写入FileStream的代码:
// Byte array representing the FileStream
byte[] fsBytes = (byte[])obj;
SqlFileStream sqlFS = new SqlFileStream(path, fsBytes, FileAccess.Write);
byte[] b = new byte[4096];
int read;
stream.Seek(0, SeekOrigin.Begin);
while ((read = stream.Read(b, 0, b.Length)) > 0) {
sqlFS.Write(b, 0, read);
}
sqlFS.Close();
从我的调试开始,我确定从流中读取的最后一次迭代的读取值等于1253,这意味着最后一次读取的流在索引0到1252,的字节数组中有数据,这是正确即可。 1253年及之后的所有内容均来自上一次阅读。
所以,我的理解是 sqlFS.Write(b,0,1253)会将字节数组的索引0到1252之间的所有内容写入SqlFileStream。但是,它实际上是将字节数组中的所有写入SqlFileStream。我已经通过将PDF拉回数据库来验证这一点,即使我现在无法正常查看它,因为它现在已经损坏了,我仍然可以在文本编辑器中打开它并查看结尾处的garbal属于那里(1253位及之后的所有数据)。
我在这里做错了,或者SqlFileStream Write方法是否有像我认为的那样的错误?
奇怪的是,我上传了很多其他PDF和文本文件和图片,我从未见过这个问题。我不知道为什么会出现一些PDF而不是其他PDF ...
修改 这是我的read方法的代码。这个错误也可能在这里(感谢Remus指出这个!)。
SqlFileStream objSqlFileStream = new SqlFileStream(path, objContext, FileAccess.Read);
objSqlFileStream.Seek(0, SeekOrigin.Begin);
b = new byte[4096];
int read;
while ((read = objSqlFileStream.Read(b, 0, b.Length)) > 0) {
Response.BinaryWrite(b);
}
objSqlFileStream.Close();
编辑#2(固定代码):
SqlFileStream objSqlFileStream = new SqlFileStream(path, objContext, FileAccess.Read);
objSqlFileStream.Seek(0, SeekOrigin.Begin);
b = new byte[4096];
int read;
while ((read = objSqlFileStream.Read(b, 0, b.Length)) > 0) {
if (read < 4096) {
byte[] b2 = new byte[read];
System.Buffer.BlockCopy(b, 0, b2, 0, read);
Response.BinaryWrite(b2);
}
else
Response.BinaryWrite(b);
}
objSqlFileStream.Close();
答案 0 :(得分:2)
while ((read = objSqlFileStream.Read(b, 0, b.Length)) > 0) {
Response.BinaryWrite(b);
}
这会写入整个原始byte[]
数组b
并忽略大小read
。我知道HttpResponse没有签名.BinaryWrite(byte[], offset, size)
......在你写出来之前我恐怕你必须b.Resize(read);
。
答案 1 :(得分:0)
写入后清除字节数组是否有帮助?