www.pudn.com > indyprelim.zip > IdIntercept.pas
{
$Project$
$Workfile$
$Revision$
$DateUTC$
$Id$
This file is part of the Indy (Internet Direct) project, and is offered
under the dual-licensing agreement described on the Indy website.
(http://www.indyproject.org/)
Copyright:
(c) 1993-2005, Chad Z. Hower and the Indy Pit Crew. All rights reserved.
}
{
$Log$
}
{
Rev 1.10 3/10/2005 12:00:46 AM JPMugaas
Minor problem Craig Peterson had noted in an E-Mail to me.
Rev 1.9 11/30/04 6:19:12 PM RLebeau
Promoted the TIdConnectionIntercept.Intercept property from protected to
published
Rev 1.8 2004.02.03 4:16:44 PM czhower
For unit name changes.
Rev 1.7 2004.01.20 10:03:24 PM czhower
InitComponent
Rev 1.6 5/12/2003 12:33:32 AM GGrieve
add Data from BlockCipher descendent
Rev 1.5 2003.10.14 1:26:48 PM czhower
Uupdates + Intercept support
Rev 1.4 2003.10.11 5:48:16 PM czhower
-VCL fixes for servers
-Chain suport for servers (Super core)
-Scheduler upgrades
-Full yarn support
Rev 1.3 10/5/2003 3:20:46 PM BGooijen
.net
Rev 1.2 2003.10.01 1:12:34 AM czhower
.Net
Rev 1.1 3/5/2003 10:59:48 PM BGooijen
Fixed (i know, the SendBuffer looks bad)
Rev 1.0 11/13/2002 08:44:42 AM JPMugaas
2002-03-01 - Andrew P.Rybin
- Nested Intercept support (ex: ->logging->compression->encryption)
2002-04-09 - Chuck Smith
- set ABuffer.Position := 0; in OnSend/OnReceive for Nested Stream send/receive
}
unit IdIntercept;
interface
{$I IdCompilerDefines.inc}
//here only to put FPC in Delphi mode
uses
IdGlobal, IdBaseComponent, IdBuffer, IdException, IdSys, IdObjs;
type
EIdInterceptCircularLink = class(EIdException);
TIdConnectionIntercept = class;
TIdInterceptNotifyEvent = procedure(ASender: TIdConnectionIntercept) of object;
TIdInterceptStreamEvent = procedure(
ASender: TIdConnectionIntercept;
var ABuffer: TIdBytes
) of object;
TIdConnectionIntercept = class(TIdBaseComponent)
protected
FConnection: TIdNativeComponent;
FIntercept: TIdConnectionIntercept;
FIsClient: Boolean;
FData: TObject;
FOnConnect: TIdInterceptNotifyEvent;
FOnDisconnect: TIdInterceptNotifyEvent;
FOnReceive: TIdInterceptStreamEvent;
FOnSend: TIdInterceptStreamEvent;
//
procedure InitComponent; override;
procedure Notification(AComponent: TIdNativeComponent; Operation: TIdOperation); override;
procedure SetIntercept(AValue: TIdConnectionIntercept);
//
public
procedure Connect(AConnection: TIdNativeComponent); virtual;
procedure Disconnect;
virtual;
procedure Receive(
var ABuffer: TIdBytes
); virtual;
procedure Send(
var ABuffer: TIdBytes
); virtual;
//
property Connection: TIdNativeComponent read FConnection;
property IsClient: Boolean read FIsClient;
property Data: TObject read FData write FData; // user can use this to keep context
published
property Intercept: TIdConnectionIntercept read FIntercept write SetIntercept;
property OnConnect: TIdInterceptNotifyEvent read FOnConnect write FOnConnect;
property OnDisconnect: TIdInterceptNotifyEvent read FOnDisconnect write FOnDisconnect;
property OnReceive: TIdInterceptStreamEvent read FOnReceive write FOnReceive;
property OnSend: TIdInterceptStreamEvent read FOnSend write FOnSend;
end;
TIdServerIntercept = class(TIdBaseComponent)
public
procedure Init; virtual; abstract;
function Accept(AConnection: TIdNativeComponent): TIdConnectionIntercept; virtual; abstract;
end;
implementation
uses
IdResourceStringsCore;
{ TIdIntercept }
procedure TIdConnectionIntercept.Disconnect;
begin
if Intercept <> nil then begin
Intercept.Disconnect;
end;
if Assigned(OnDisconnect) then begin
OnDisconnect(Self);
end;
FConnection := nil;
end;
procedure TIdConnectionIntercept.Connect(AConnection: TIdNativeComponent);
begin
FConnection := AConnection;
if Assigned(OnConnect) then begin
OnConnect(Self);
end;
if Intercept <> nil then begin
Intercept.Connect(AConnection);
end;
end;
procedure TIdConnectionIntercept.Receive(var ABuffer: TIdBytes);
begin
if Intercept <> nil then begin
Intercept.Receive(ABuffer);
end;
if Assigned(OnReceive) then begin
OnReceive(Self, ABuffer);
end;
end;
procedure TIdConnectionIntercept.Send(var ABuffer: TIdBytes);
begin
if Assigned(OnSend) then begin
OnSend(Self, ABuffer);
end;
if Intercept <> nil then begin
Intercept.Send(ABuffer);
end;
end;
procedure TIdConnectionIntercept.SetIntercept(AValue: TIdConnectionIntercept);
var
LIntercept: TIdConnectionIntercept;
Begin
LIntercept := AValue;
while Assigned(LIntercept) do begin
if LIntercept = SELF then begin //recursion
raise EIdInterceptCircularLink.Create(Sys.Format(RSInterceptCircularLink,[ClassName])); // TODO: Resource string and more english
end;
LIntercept := LIntercept.Intercept;
end;
FIntercept := AValue;
// add self to the Intercept's free notification list {Do not Localize}
if Assigned(Intercept) then begin
Intercept.FreeNotification(Self);
end;
End;
procedure TIdConnectionIntercept.Notification(AComponent: TIdNativeComponent;
Operation: TIdOperation);
begin
inherited Notification(AComponent, OPeration);
if (Operation = opRemove) and (AComponent = Intercept) then begin
FIntercept := NIL;
end;
end;
procedure TIdConnectionIntercept.InitComponent;
begin
inherited InitComponent;
FIsClient := True;
end;
end.