从COM+返回压缩后的数据集到客户端
最近在我们的项目中负责开发一个用于三层中数据交换的模块,要求实现以下功能: 1、数据从总部下发到门店(总部数据下发功能) 2、数据从门店上报到总部(总部数据导入功能) 注:此功能主要用于单据上报 3、门店数据更新与同步(门店数据导入功能) 1)、从总部下发的数据包文件中导入数据(无网络环境支持时) 2)、直接连接总部服务器同步数据(有网络环境支持时) 我想这样实现的,大部分的处理都放在应用层来完成,客户端只向应用层发出数据请求。 在COM+中我没有使用TDataSetProvider来向客户端提供数据集,而是在应用层将客户端需要 的数据取出并进行压缩处理后通过接口函数以Variant类型返回给客户端。 在实现过程中,被TMemoryStream类型与Variant类型之间的转换问题卡住了,后来在LiChaoHui大侠的帮助下解决了这个问题,他提供了以下两个函数: procedure TDataExchangeRDM.VariantToStream (const V: OLEVariant; Stream : TStream); var P : Pointer; begin Stream.Position := 0; Stream.Size := VarArrayHighBound (V, 1) - VarArrayLowBound (V, 1) + 1; P := VarArrayLock (V); Stream.Write (P^, Stream.Size); VarArrayUnlock (V); Stream.Position := 0; end; procedure TDataExchangeRDM.StreamToVariant (Stream : TStream; var V: OLEVariant); var P : Pointer; begin V := VarArrayCreate ([0, Stream.Size - 1], varByte); P := VarArrayLock (V); Stream.Position := 0; Stream.Read (P^, Stream.Size); VarArrayUnlock (V); end; 函数是很简单,可我原来就是没想到!主要是对变体类型理解不足。 在数据压缩方面,我使用的是Delphi中自带的ZLib单元,具体代码如下: function TDataExchangeRDM.GetDataEx(iClientID: Integer; const SQLText: WideString): OleVariant; var adoDataSet: TADODataSet; dsp: TDataSetProvider; M: TMemoryStream; begin Result := Null; InitByClient(iClientID); adoDataSet := TADODataSet.Create(self); dsp := TDataSetProvider.Create(self); M := TMemoryStream.Create; try adoDataSet.Connection := adoConn; adoDataSet.CommandTimeout := 600; adoDataSet.CommandText := SQLText; dsp.DataSet := adoDataSet; adoDataSet.Open; Result := dsp.Data; //取得结果集 if Result = Null then exit; VariantToStream(Result,M); //转换到流 M.Position := 0; Compression(M,clFastest); //压缩流 StreamToVariant(M,Result); //转换到变体返回值 finally dsp.Free; adoDataSet.Free; M.Free; SetAbort; end; end; 于2003-07-12晚修改。