Using TPgConnection and TPgAlerter in thread

Discussion of open issues, suggestions and bugs regarding PgDAC (PostgreSQL Data Access Components) for Delphi, C++Builder, Lazarus (and FPC)
Post Reply
chapa
Posts: 3
Joined: Fri 09 Sep 2011 16:06

Using TPgConnection and TPgAlerter in thread

Post by chapa » Fri 09 Sep 2011 16:21

Hello,

Using PgDAC 3.0 beta trial and 9.0.4 server on localhost. Delphi XE2.
Windows 7 x64

I have following case:

In thread I create one TPgConnection object and one TPgAlerter. Attaching OnEvent handler.
OnEvent is never called. Instead I get TPgSQLNotification leak for every notify message I sent from database side.

Then I add TDataModule. Pick TPgConnection and TPgAlerter VCL components. Configure them.
In this case OnEvent is fired for both OnEvent Alerter handlers (thread created and vcl).

How can I work out this behavior? I would like to use Connection and Alerter in thread.

Thanks.

AlexP
Devart Team
Posts: 5530
Joined: Tue 10 Aug 2010 11:35

Post by AlexP » Mon 12 Sep 2011 13:03

Hello,

I cannot reproduce the problem.
The following code works correctly (the event works) in RAD Studio XE2 and in x32 applications as well as in the x64 ones. Please try to execute this code, and, if it is executed successfully, modify it so that the problem can be reproduced and send it to alexp*devart*com.

Code: Select all

unit Unit2;

interface

uses
  Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants, System.Classes, Vcl.Graphics,
  Vcl.Controls, Vcl.Forms, Vcl.Dialogs, DAAlerter, PgAlerter, Data.DB, DBAccess,
  PgAccess, Vcl.StdCtrls;

type
  TAlerterThread = class(TThread)
  private
    FPgConnection: TPgConnection;
    FPgAlerter: TPgAlerter;
  public
    procedure execute; override;
    procedure FPgAlerterEvent(Sender: TObject; const EventName: string;
      PID: Integer; const EventMessage: string);
  end;

  TForm2 = class(TForm)
    Button1: TButton;
    procedure FormCreate(Sender: TObject);
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
    FAlerterThread: TAlerterThread;
    FPgConnection: TPgConnection;
    FPgAlerter: TPgAlerter;

  public
    { Public declarations }
  end;

var
  Form2: TForm2;

implementation

{$R *.dfm}

{ TAlerterThread }

procedure TAlerterThread.execute;
begin
  FPgConnection := TPgConnection.Create(nil);
  FPgConnection.Server := 'db';
  FPgConnection.Port := 5438;
  FPgConnection.Database := 'alexp';
  FPgConnection.Username := 'postgres';
  FPgConnection.Password := 'postgres';
  FPgConnection.LoginPrompt := false;
  FPgConnection.Connect;
  FPgAlerter := TPgAlerter.Create(nil);
  FPgAlerter.Connection := FPgConnection;
  FPgAlerter.Events := 'TestThread';
  FPgAlerter.OnEvent := FPgAlerterEvent;
  FPgConnection.Connect;
  FPgAlerter.Start;
  If not FPgAlerter.Active then
    ShowMessage('error');
end;

procedure TAlerterThread.FPgAlerterEvent(Sender: TObject;
  const EventName: string; PID: Integer; const EventMessage: string);
begin
  ShowMessage(EventName + '; PID: ' + IntToStr(PID));
end;

procedure TForm2.Button1Click(Sender: TObject);
begin
    FPgAlerter.SendEvent('TestThread');
end;

procedure TForm2.FormCreate(Sender: TObject);
begin
  FPgConnection := TPgConnection.Create(nil);
  FPgConnection.Server := 'db';
  FPgConnection.Port := 5438;
  FPgConnection.Database := 'alexp';
  FPgConnection.Username := 'postgres';
  FPgConnection.Password := 'postgres';
  FPgConnection.LoginPrompt := false;
  FPgConnection.Connect;
  FPgAlerter := TPgAlerter.Create(nil);
  FPgAlerter.Connection := FPgConnection;
  FPgAlerter.Events := 'TestThread';
  FPgConnection.Connect;
  FPgAlerter.Start;

  FAlerterThread:= TAlerterThread.Create(true);
  FAlerterThread.resume;
end;

end.

chapa
Posts: 3
Joined: Fri 09 Sep 2011 16:06

Post by chapa » Mon 12 Sep 2011 13:22

Hi AlexP,

The catch is as I said, you MUST have no visual components connected.

Try to trigger the event (SendEvent) from thread's PgAlerter with removed (or not connected) visual components.
Run two instances of the application.
No one will fire.

If you connect the visuals, thread event will fire.

Thanks.

AlexP
Devart Team
Posts: 5530
Joined: Tue 10 Aug 2010 11:35

Post by AlexP » Wed 14 Sep 2011 10:43

Hello,

Thank you for the information.
We've reproduced the problem with TPgAlerter in threads when visual components are not used.
We will notify you as soon as we have any results.

Post Reply