Delphi XE2 DataSnap-通过TStream从服务器到客户端流式传输JPEG文件



我编写了一个DataSnap服务器方法,该方法返回一个TStream对象以传输文件。客户端应用程序调用该方法并读取流以下载文件。服务器方法非常简单:

function TServerMethods.DownloadFile(sFilePath: string): TStream;
var
  strFileStream: TFileStream;
begin
  strFileStream := TFileStream.Create(sFilePath, fmOpenRead);
  Result := strFileStream;
end;

它可以很好地下载许多文件类型(PDF,GIF,BMP,ZIP,EXE),但在下载JPG文件时不起作用。在客户端,方法调用返回的流对象的大小始终为0(带有JPG)。我可以在我的电脑上成功地在本地流式传输JPG文件,所以这一定与DataSnap有关。我做了一些研究,表明DataSnap在幕后将流转换为JSON,当涉及到JPG文件时,这可能会有问题——有人能证实这一点吗?在客户端,我使用TDSRESTConnection来调用服务器方法。我意识到我可以在流媒体播放之前对JPG文件进行压缩,但我宁愿不必这样做。

我想在尝试解决这个问题时更新线程。我从未找到过使用TStream通过DataSnap传输JPEG文件的方法,但我已经通过将流转换为TJSONArray并将其传递回来来实现了这一点。所以我的服务器方法现在看起来如下:

function TServerMethods.DownloadJPEGFile(sFilePath: string): TJSONArray;
var
  strFileStream: TFileStream;
begin
  strFileStream := TFileStream.Create(sFilePath, fmOpenRead);
  Result := TDBXJSONTools.StreamToJSON(strFileStream, 0, strFileStream.Size);
end;

然后在客户端,我用转换回TStream

strFileStream := TDBXJSONTools.JSONToStream(JSONArray);

我创建了一个新的服务器方法调用,纯粹是为了下载JPEG,因为我发现使用TJSONArray而不是TStream传输文件的速度慢了4倍,所以我对所有其他文件类型都使用我的原始方法。

作为更新-经过进一步研究,我发现这与PC上使用的系统区域设置有关。我使用的是"English(United Kingdom)",但如果我将其更改为例如"Japan(Japanese)",则错误将消失,文件传输也可以正常工作。我已将此记录为Embarcadero的QC报告。

Embarcadero现在已经修复了这个问题(它也影响.DOC文件):

1.复制。。。\RAD Studio\9.0\source\data\datasnap\datasnap.DSClientRest.pas'到您的datasnap Client项目文件夹

2.将.pas文件添加到项目

3.将第1288行修改为

//  LResponseJSON := TJSONObject.ParseJSONValue(BytesOf(LResponseText.StringValue), 0);
LResponseJSON := TJSONObject.ParseJSONValue(BytesOf(UTF8String(LResponseText.StringValue)), 0);

4.重建DataSnap REST客户端项目

5.使用REST服务器运行

这解决了问题。

将此行添加到您的DownloadFile方法:

GetInvocationMetadata.ResponseContentType := 'image/jpeg';

相关内容

  • 没有找到相关文章

最新更新