delphidelphi-10.1-berlinremobjects

RemObjects leaks detected after calling manually created service instance


I have the following code which creates an instance of an RemObjects service and makes a call to a .net server

class function TLabelPrintingServiceProxy.GetInstance: ILabelPrintingManager;
var
  LRoRemoteService: TRoRemoteService;
begin
  LRoRemoteService := TRoRemoteService.Create(nil);
  LRoRemoteService.Message := TROSOAPMessage.Create();
  LRoRemoteService.Channel := TROIndyHTTPChannel.Create(nil);
  LRoRemoteService.Channel.TargetUri := TROUri.Create(ILabelPrintingIntf.LabelPrintingManager_EndPointURI);

  Result := (LRoRemoteService as ILabelPrintingManager);
end;

call to the .net service is performed like this:

  try
        Result := BinaryArray.Create;
        LLabelPrintingManager := TLabelPrintingServiceProxy.GetInstance();
        Result.Add(LLabelPrintingManager.GetVSSLabelImage(APrintJob));
    finally 
        TLabelPrintingServiceProxy.ReleaseLabelPrintingServiceProxyInstance(LLabelPrintingManager);
    end;

After the call is made the LLabelPrintingManager interface should be released automatically by RemObjects, but it isn't and leaks the objects used.

I've tried on the ReleaseLabelPrintingServiceProxyInstance (code bellow) to release manually all the objects from the service instance, but it's still leaking

class procedure TLabelPrintingServiceProxy.ReleaseLabelPrintingServiceProxyInstance(aILabelPrintingManagerIntf: ILabelPrintingManager);
var
  lProxy: TRoProxy;
begin
  lProxy := TROProxy(aILabelPrintingManagerIntf);
  TROIndyHTTPChannel(lProxy.__TransportChannel).TargetUri.Free;
//  TROIndyHTTPChannel(lProxy.__TransportChannel).Free; this is generating an AV
  TRoMessage(lProxy.__Message).free;

  TRoRemoteService(aILabelPrintingManagerIntf).Free;

I'm missing something?


Solution

  • After discussing with guys from RemObjects, here is the solution:

    class function TLabelPrintingServiceProxy.GetRemoteServiceInstance: TRoRemoteService;
    var
      LRoRemoteService: TRoRemoteService;
    begin
      Result := TRoRemoteService.Create(nil);
      Result.Message := TROSOAPMessage.Create();
      Result.Channel := TROIndyHTTPChannel.Create(nil);
      Result.Channel.TargetUri := TROUri.Create(ILabelPrintingIntf.LabelPrintingManager_EndPointURI);
    end;
    

    call

    try
      LLabelPrintingRemoteService := TLabelPrintingServiceProxy.GetRemoteServiceInstance();
      (LLabelPrintingRemoteService as ILabelPrintingManager).PrintVSSJob(printJob);
    finally
      TLabelPrintingServiceProxy.ReleaseLabelPrintingServiceProxyInstance(LLabelPrintingRemoteService);
    end;
    

    and releasing the objects

    try
      LLabelPrintingRemoteService := TLabelPrintingServiceProxy.GetRemoteServiceInstance();
      (LLabelPrintingRemoteService as ILabelPrintingManager).PrintVSSJob(printJob);
    finally
      TLabelPrintingServiceProxy.ReleaseLabelPrintingServiceProxyInstance(LLabelPrintingRemoteService);
    end;