@@ -9,37 +9,37 @@ interface
99, SysUtils
1010, IdContext
1111, IdIRC
12+ , IRCLogBot.Config
13+ , IRCLogBot.Database
1214;
1315
1416type
1517{ TIRCLogBot }
1618 TIRCLogBot = class (TObject)
1719 private
1820 FIRC: TIdIRC;
19- FNickName: String;
20- FUserName: String;
21- FRealName: String;
22- FHost: String;
23- FPort: Word;
24- FChannel: String;
25-
2621 FJoinedChannel: Boolean;
2722
23+ FConfig: TBotConfig;
24+
25+ FDB: TDatabase;
26+
2827 procedure OnConnected (Sender: TObject);
2928 procedure OnDisconnected (Sender: TObject);
3029 procedure OnNotice (ASender: TIdContext; const ANickname, AHost,
3130 ATarget, ANotice: String);
31+ procedure OnServerQuit (ASender: TIdContext; const ANickname, AHost,
32+ AServer, AReason: String);
3233 procedure OnJoin (ASender: TIdContext; const ANickname, AHost,
3334 AChannel: String);
3435 procedure OnPrivateMessage (ASender: TIdContext; const ANickname, AHost,
3536 ATarget, AMessage: String);
3637
3738 procedure Help (const ATarget: String);
38- procedure Replay (const ATarget: String; Count : Integer);
39+ procedure Replay (const ATarget: String; ACount : Integer);
3940 protected
4041 public
41- constructor Create(AHost: String; APort: Word;
42- ANickName, AUserName, ARealName, AChannel: String);
42+ constructor Create(const AConfig: TBotConfig);
4343 destructor Destroy; override;
4444
4545 procedure Run ;
@@ -53,6 +53,70 @@ implementation
5353 IRCLogBot.Common
5454;
5555
56+ type
57+ { TReplayThread }
58+ TReplayThread = class (TTHread)
59+ private
60+ FIRC: TIdIRC;
61+ FTarget: String;
62+ FLines: TStringList;
63+ protected
64+ procedure Execute ; override;
65+ public
66+ constructor Create(const AIRC: TIdIRC; const ATarget: String;
67+ const ALines: TStringList);
68+ published
69+ end ;
70+
71+ { TReplayThread }
72+
73+ procedure TReplayThread.Execute ;
74+ var
75+ line: String;
76+ index: Integer = 0 ;
77+ begin
78+ if not FIRC.Connected then ;
79+ begin
80+ debug(' Exiting replay thread due not being connected.' );
81+ exit;
82+ end ;
83+ try
84+ FIRC.Say(FTarget, ' !! --> To avoid triggering flooding, for each 5 lines, I will pause for 5 seconds <-- !!' );
85+ FIRC.Say(FTarget, Format(' *** Here are the last %d lines ***' , [FLines.Count]));
86+ for line in FLines do
87+ begin
88+ if (Terminated) or (not FIRC.Connected) then
89+ begin
90+ debug(' Exiting replay thread due to termination or not being connected.' );
91+ exit;
92+ end ;
93+ debug(' Sending #%d: "%s"' , [index, line]);
94+ Inc(index);
95+ FIRC.Say(FTarget, line);
96+ if (index mod 5 ) = 0 then
97+ begin
98+ debug(' Pausing' );
99+ Sleep(5000 );
100+ end ;
101+ end ;
102+ FIRC.Say(FTarget, Format(' *** End of the last %d lines ***' , [FLines.Count]));
103+ finally
104+ FLines.Free;
105+ end ;
106+ end ;
107+
108+ constructor TReplayThread.Create(const AIRC: TIdIRC; const ATarget: String;
109+ const ALines: TStringList);
110+ begin
111+ inherited Create(True);
112+ FIRC:= AIRC;
113+ FTarget:= ATarget;
114+ FLines:= TStringList.Create;
115+ FLines.Text := ALines.Text;
116+ FreeOnTerminate:= True;
117+ Start;
118+ end ;
119+
56120{ TIRCLogBot }
57121
58122procedure TIRCLogBot.OnConnected (Sender: TObject);
@@ -68,21 +132,34 @@ procedure TIRCLogBot.OnDisconnected(Sender: TObject);
68132procedure TIRCLogBot.OnNotice (ASender: TIdContext; const ANickname, AHost,
69133 ATarget, ANotice: String);
70134begin
71- debug(' >> NOTICE: <%s> "%s"' , [
135+ debug(' >> NOTICE: <%s:%s> (%s) "%s"' , [
72136 ANickname,
137+ AHost,
138+ ATarget,
73139 ANotice
74140 ]);
75141end ;
76142
143+ procedure TIRCLogBot.OnServerQuit (ASender: TIdContext; const ANickname, AHost,
144+ AServer, AReason: String);
145+ begin
146+ debug(' >> QUIT: <%s:%s> %s "%s"' ,[
147+ ANickname,
148+ AHost,
149+ AServer,
150+ AReason
151+ ]);
152+ end ;
153+
77154procedure TIRCLogBot.OnJoin (ASender: TIdContext; const ANickname, AHost,
78155 AChannel: String);
79156begin
80- debug(' >> JOIN: <%s@ %s> %s' , [
157+ debug(' >> JOIN: <%s: %s> %s' , [
81158 ANickname,
82159 AHost,
83160 AChannel
84161 ]);
85- if (ANickname = FNickName ) and (AChannel = FChannel ) then
162+ if (ANickname = FConfig.NickName ) and (AChannel = FConfig.Channel ) then
86163 begin
87164 debug(' Successfully joined my channel' );
88165 FJoinedChannel:= True;
@@ -96,13 +173,24 @@ procedure TIRCLogBot.OnPrivateMessage(ASender: TIdContext; const ANickname,
96173 strings: TStringArray;
97174 count: Integer;
98175begin
99- debug(' >> PRIVMSG: <%s@ %s>(%s) "%s"' , [
176+ debug(' >> PRIVMSG: <%s: %s>(%s) "%s"' , [
100177 ANickname,
101178 AHost,
102179 ATarget,
103180 AMessage
104181 ]);
105- if ATarget = FNickName then
182+ if ATarget = FConfig.Channel then
183+ begin
184+ debug(' Inserting: %s, %s, %s, %s' , [
185+ ANickname,
186+ AHost,
187+ ATarget,
188+ AMessage
189+ ]);
190+ FDB.Insert(ANickname, ATarget, AMessage);
191+ exit;
192+ end ;
193+ if ATarget = FConfig.NickName then
106194 begin
107195 if Pos(' .' , AMessage) = 1 then
108196 begin
@@ -115,18 +203,23 @@ procedure TIRCLogBot.OnPrivateMessage(ASender: TIdContext; const ANickname,
115203 if Pos(' .replay' , Trim(AMessage)) = 1 then
116204 begin
117205 strings:= AMessage.Split([' ' ]);
206+ // debug('Strings: %d', [Length(strings)]);
118207 try
119208 if Length(strings) > 1 then
120209 begin
121210 count:= StrToInt(strings[1 ]);
122211 end
123212 else
124213 begin
125- count:= 0 ;
214+ count:= 10 ;
126215 end ;
216+ // debug('Count: %d', [count]);
127217 Replay(ANickname, count);
128218 except
129- FIRC.Say(ANickname, ' That <count> is not a number.' );
219+ on e:Exception do
220+ begin
221+ FIRC.Say(ANickname, ' Something went wrong: "' + e.Message + ' ". It'' s been logged. Please contact the admin if I stop working.' );
222+ end ;
130223 end ;
131224 exit;
132225 end ;
@@ -136,6 +229,7 @@ procedure TIRCLogBot.OnPrivateMessage(ASender: TIdContext; const ANickname,
136229 debug(' No command.' );
137230 FIRC.Say(ANickname, ' Not a command. Please use ".help" to see a list of commands.' );
138231 end ;
232+ exit;
139233 end ;
140234end ;
141235
@@ -147,10 +241,16 @@ procedure TIRCLogBot.Help(const ATarget: String);
147241 FIRC.Say(ATarget, ' .replay [count] - Raplays last <count> lines. Default is last 10 lines.' );
148242end ;
149243
150- procedure TIRCLogBot.Replay (const ATarget: String; Count: Integer);
244+ procedure TIRCLogBot.Replay (const ATarget: String; ACount: Integer);
245+ var
246+ replayThread: TReplayThread;
247+ lines: TStringList;
151248begin
152- debug(' Replay command.' );
153- FIRC.Say(ATarget, Format(' Not fully implemented yet: %d' ,[Count]));
249+ debug(' Replay command(%d).' , [ACount]);
250+ lines:= FDB.Get(ACount);
251+ debug(' Lines: %d' , [lines.Count]);
252+ replayThread:= TReplayThread.Create(FIRC, ATarget, lines);
253+ lines.Free;
154254end ;
155255
156256procedure TIRCLogBot.Run ;
@@ -164,9 +264,9 @@ procedure TIRCLogBot.Run;
164264 debug(' Error connecting: %s' , [e.Message]);
165265 end ;
166266 end ;
167- debug(' Joining channel: "%s"...' , [FChannel ]);
267+ debug(' Joining channel: "%s"...' , [FConfig.Channel ]);
168268 try
169- FIRC.Join(FChannel );
269+ FIRC.Join(FConfig.Channel );
170270 except
171271 on e:Exception do
172272 begin
@@ -181,7 +281,8 @@ procedure TIRCLogBot.Shutdown;
181281 begin
182282 debug(' Disconnecting...' );
183283 try
184- FIRC.Disconnect(' Need to go and have a wee nap.' );
284+ if FJoinedChannel then FIRC.Say(FConfig.Channel, ' Boss sais I need to have a wee nap. See Y'' All later...' );
285+ FIRC.Disconnect(' ZzZzZzZzZzZzZzZz...' );
185286 except
186287 on e:Exception do
187288 begin
@@ -191,33 +292,41 @@ procedure TIRCLogBot.Shutdown;
191292 end ;
192293end ;
193294
194- constructor TIRCLogBot.Create(AHost: String; APort: Word; ANickName, AUserName,
195- ARealName, AChannel: String);
295+ constructor TIRCLogBot.Create(const AConfig: TBotConfig);
196296begin
197- FNickname:= ANickname;
198- FUsername:= AUserName;
199- FRealName:= ARealName;
200- FHost:= AHost;
201- FPort:= APort;
202- FChannel:= AChannel;
297+ FJoinedChannel:= False;
298+
299+ // Config
300+ FConfig:= AConfig;
203301
302+ // Setup IRC Client
204303 FIRC:= TIdIRC.Create;
205- FIRC.Nickname:= FNickName ;
206- FIRC.Username:= FUserName ;
207- FIRC.RealName:= FRealName ;
208- FIRC.Host:= FHost ;
209- FIRC.Port:= FPort ;
304+ FIRC.Nickname:= FConfig.NickName ;
305+ FIRC.Username:= FConfig.UserName ;
306+ FIRC.RealName:= FConfig.RealName ;
307+ FIRC.Host:= FConfig.Host ;
308+ FIRC.Port:= FConfig.Port ;
210309 FIRC.OnConnected:= @OnConnected;
211310 FIRC.OnDisconnected:= @OnDisconnected;
311+ FIRC.OnServerQuit:= @OnServerQuit;
212312 FIRC.OnJoin:= @OnJoin;
213313 FIRC.OnNotice:= @OnNotice;
214314 FIRC.OnPrivateMessage:= @OnPrivateMessage;
215315
216- FJoinedChannel:= False;
316+ // Setup Database
317+ try
318+ FDB:= TDatabase.Create(FConfig.Database);
319+ except
320+ on e:Exception do
321+ begin
322+ debug(' Error creating db: ' , [e.Message]);
323+ end ;
324+ end ;
217325end ;
218326
219327destructor TIRCLogBot.Destroy;
220328begin
329+ FDB.Free;
221330 FIRC.Free;
222331 inherited Destroy;
223332end ;
0 commit comments