如何通过 Datasnap REST 服务器将 blob 存储到数据库?
How to store blob to database thru Datasnap REST server?
前言:
我们使用 Firemonkey 应用程序,然后与 DataSnap REST 服务器交互。该服务器使用 SQLite 数据库。在客户端,我们使用 FireDac Memtable 来管理数据。通常为了更新数据,我们编辑 FDMemTable,然后我们使用一个名为 ApplyUpdate 的函数(简而言之)创建一个 TFDJSONDelta,然后将其传递给服务器以应用更新。这适用于所有 "standard" 数据类型。
现在我们要在数据库中存储一个blob,就是企业的logo。
一些调查:
我们发现了一些使用 FDQuery 的 PARAMS 和 EXECUTE 函数的示例,但我们在客户端没有 FDQuery。许多示例都是针对 FDQuery 的,我们没有看到针对 FDMemTable 的示例。 FDMemtable 没有 ExecSQL 功能。
我们也看到了很多与 TBlobStream 的算法,(但除非我们错过了正确的单元声明),这个对象似乎没有在 Firemonkey 端实现。
问题:
有一种方法可以使用 FDMemTable 执行此任务,还是先将图像上传到服务器然后让服务器执行将图像添加到 blob 字段的任务更好?
我可以像这样将 blob 字段发送到 DataSnap REST 服务器:
客户端:
var
mes: TMemoryStream;
FDMemUp: TFDMemTable;
LDeltaList: TFDJSONDeltas;
begin
mes:= TMemoryStream.Create;
FDMemUp:= TFDMemTable.Create(nil);
FDMemUp.CachedUpdates:= true;
FDMemUp.FieldDefs.Add('IMAGE',ftBlob);
FDMemUp.FieldDefs.Add('ID',ftInteger);
FDMemUp.CreateDataSet;
//append one record with blob field filled from stream
FDMemUp.Append;
(FDMemUp.FieldByName('ID') as TIntegerField).AsInteger:= 106;
(FDMemUp.FieldByName('IMAGE') as TBlobField).LoadFromStream(mes);
FDMemUp.Post;
//send dataset to server
try
try
LDeltaList:= TFDJSONDeltas.Create;
TFDJSONDeltasWriter.ListAdd(LDeltaList, 'INFOLOGO', FDMemUp);
Result:= DM.ServerCoreClient.SendData(LDeltaList);
except
Result:= nil;
end;
finally
FreeAndNil(FDMemUp);
FreeAndNil(mes);
end;
然后在服务器端处理数据:
function TDMCore.SendData(const ADeltaList: TFDJSONDeltas): boolean;
var
LApply: IFDJSONDeltasApplyUpdates;
mes: TMemoryStream;
begin
LApply:= TFDJSONDeltasApplyUpdates.Create(ADeltaList);
if (LApply.Values[0].RecordCount > 0) then
begin
mes:= TMemoryStream.Create;
LApply.Values[0].First;
while not LApply.Values[0].Eof do
begin
mes.Clear;
//read stream data from blob field
(LApply.Values[0].Fields[1] as TBlobField).SaveToStream(mes);
mes.Position:= 0;
//Use stream to insert in a database or create a image or whatever the stream represent
LApply.Values[0].Next;
end;
result:= true;
end else result:= false;
end;
前言:
我们使用 Firemonkey 应用程序,然后与 DataSnap REST 服务器交互。该服务器使用 SQLite 数据库。在客户端,我们使用 FireDac Memtable 来管理数据。通常为了更新数据,我们编辑 FDMemTable,然后我们使用一个名为 ApplyUpdate 的函数(简而言之)创建一个 TFDJSONDelta,然后将其传递给服务器以应用更新。这适用于所有 "standard" 数据类型。
现在我们要在数据库中存储一个blob,就是企业的logo。
一些调查:
我们发现了一些使用 FDQuery 的 PARAMS 和 EXECUTE 函数的示例,但我们在客户端没有 FDQuery。许多示例都是针对 FDQuery 的,我们没有看到针对 FDMemTable 的示例。 FDMemtable 没有 ExecSQL 功能。
我们也看到了很多与 TBlobStream 的算法,(但除非我们错过了正确的单元声明),这个对象似乎没有在 Firemonkey 端实现。
问题:
有一种方法可以使用 FDMemTable 执行此任务,还是先将图像上传到服务器然后让服务器执行将图像添加到 blob 字段的任务更好?
我可以像这样将 blob 字段发送到 DataSnap REST 服务器:
客户端:
var
mes: TMemoryStream;
FDMemUp: TFDMemTable;
LDeltaList: TFDJSONDeltas;
begin
mes:= TMemoryStream.Create;
FDMemUp:= TFDMemTable.Create(nil);
FDMemUp.CachedUpdates:= true;
FDMemUp.FieldDefs.Add('IMAGE',ftBlob);
FDMemUp.FieldDefs.Add('ID',ftInteger);
FDMemUp.CreateDataSet;
//append one record with blob field filled from stream
FDMemUp.Append;
(FDMemUp.FieldByName('ID') as TIntegerField).AsInteger:= 106;
(FDMemUp.FieldByName('IMAGE') as TBlobField).LoadFromStream(mes);
FDMemUp.Post;
//send dataset to server
try
try
LDeltaList:= TFDJSONDeltas.Create;
TFDJSONDeltasWriter.ListAdd(LDeltaList, 'INFOLOGO', FDMemUp);
Result:= DM.ServerCoreClient.SendData(LDeltaList);
except
Result:= nil;
end;
finally
FreeAndNil(FDMemUp);
FreeAndNil(mes);
end;
然后在服务器端处理数据:
function TDMCore.SendData(const ADeltaList: TFDJSONDeltas): boolean;
var
LApply: IFDJSONDeltasApplyUpdates;
mes: TMemoryStream;
begin
LApply:= TFDJSONDeltasApplyUpdates.Create(ADeltaList);
if (LApply.Values[0].RecordCount > 0) then
begin
mes:= TMemoryStream.Create;
LApply.Values[0].First;
while not LApply.Values[0].Eof do
begin
mes.Clear;
//read stream data from blob field
(LApply.Values[0].Fields[1] as TBlobField).SaveToStream(mes);
mes.Position:= 0;
//Use stream to insert in a database or create a image or whatever the stream represent
LApply.Values[0].Next;
end;
result:= true;
end else result:= false;
end;