2010-01-08 41 views
1

我想用Delphi 2007将我的应用程序从Indy 9升级到10。 现在,由于找不到DecodeToStream,因此无法编译。 代码使用粗体框架,因为有对BoldElement的引用。Indy10中的DecodeToStream

任何其他方法调用?

UPDATE(我想我简化前面的例子太多了)

原始代码:

BlobStreamStr : String; 
    MIMEDecoder : TidDecoderMIME; 

    if (BoldElement is TBATypedBlob) then 
    begin 
     BlobStreamStr := copy(ChangeValue,pos(']',ChangeValue)+1,maxint); 
     (BoldElement as TBATypedBlob).ContentType := copy(ChangeValue,2,pos(']',ChangeValue)-2); 

     MIMEDecoder := TidDecoderMIME.Create(nil); 
     try 
     MIMEDecoder.DecodeToStream(BlobStreamStr,(BoldElement as TBATypedBlob).CreateBlobStream(bmWrite)); 
     finally 
     FreeAndNil(MIMEDecoder); 
     end; 
    end 

我的变化后:

BlobStreamStr : String; 
    MIMEDecoder : TidDecoderMIME; 
    LStream  : TIdMemoryStream; 

    if (BoldElement is TBATypedBlob) then 
    begin 
     BlobStreamStr := copy(ChangeValue, pos(']', ChangeValue) + 1, maxint); 
     (BoldElement as TBATypedBlob).ContentType := copy(ChangeValue, 2, pos(']',ChangeValue)-2); 

     MIMEDecoder := TidDecoderMIME.Create(nil); 
     LStream := TIdMemoryStream.Create; 
     try 
     MIMEDecoder.DecodeBegin(LStream); 
     MIMEDecoder.Decode(BlobStreamStr, 0, Length(BlobStreamStr)); 
     LStream.Position := 0; 
     ReadTIdBytesFromStream(LStream, DecodedBytes, Length(BlobStreamStr)); 

     // Should memory for this stream be released ?? 
     (BoldElement as TBATypedBlob).CreateBlobStream(bmWrite).Write(DecodedBytes[0], Length(DecodedBytes)); 
     finally 
     MIMEDecoder.DecodeEnd; 
     FreeAndNil(LStream); 
     FreeAndNil(MIMEDecoder); 
     end; 
    end 

但我根本没有信心因为我不太了解Indy,所以我的变化。所以所有的意见都欢迎。有一件事我不明白是对CreateBlobStream的调用。我应该检查FastMM,所以它不是一个memleak。

+0

是的,对CreateBlobStream()的调用是内存泄漏。当您完成使用时,您需要释放()流。 – 2010-01-08 22:47:00

回答

2

使用TIdDecoder.DecodeBegin()是解码到TStream的正确方法。但是,您不需要中间TIdMemoryStream(其中,BTW在Indy 10中已经存在很长一段时间了 - 考虑升级到更新版本)。您可以直接传递Blob流,例如:

var 
    BlobElement : TBATypedBlob; 
    BlobStreamStr : String; 
    BlobStream  : TStream; 
    MIMEDecoder : TidDecoderMIME; 
begin 
    ... 
    if BoldElement is TBATypedBlob then 
    begin 
    BlobElement := BoldElement as TBATypedBlob; 

    BlobStreamStr := Copy(ChangeValue, Pos(']',ChangeValue)+1, Maxint); 
    BlobElement.ContentType := Copy(ChangeValue, 2, Pos(']',ChangeValue)-2); 

    BlobStream := BlobElement.CreateBlobStream(bmWrite); 
    try 
     MIMEDecoder := TidDecoderMIME.Create(nil); 
     try 
     MIMEDecoder.DecodeBegin(BlobStream); 
     try 
      MIMEDecoder.Decode(BlobStreamStr); 
     finally 
      MIMEDecoder.DecodeEnd; 
     end; 
     finally 
     FreeAndNil(MIMEDecoder); 
     end; 
    finally 
     FreeAndNil(BlobStream); 
    end; 
    end; 
    ... 
end; 
+0

Somethines我真的希望像变数这样的本地“界面”。他们会花费这么多的样板。例如BlobStream只会释放自己,当它超出范围 – Runner 2010-01-09 08:35:38

+0

感谢您的例子,现在它编译好,但我还没有验证结果呢。这可能属于另一个线程,但最终嵌套在代码中。这是常见的吗?有很多try/finally代码会出现性能问题吗? – 2010-01-10 17:46:02

2

是他们改变了9和10

之间有很多现在你有“DecodeBytes”,而不是DecodeToStream的我觉得。所以像这样的事情应该这样做:

var 
    DecodedBytes: TIdBytes; 
begin 
    MIMEDecoder := TidDecoderMIME.Create(nil); 
    try 
    DecodedBytes := MIMEDecoder.DecodeBytes(vString); 
    vStream.Write(DecodedBytes[0], Length(DecodedBytes)); 
    finally 
    FreeAndNil(MIMEDecoder); 
    end; 
end; 
+0

我没有找到DecodeBytes方法,但答案给了我灵感来改变代码,所以你得到的积分:) – 2010-01-08 21:51:22

+0

好吧,现在你的例子是有点不同是的。那么因为Remy是Indy作者之一,所以我认为听他说是明智之举) – Runner 2010-01-09 08:33:49