/*==============================================================*/
/* Object name: 服务器端程序 */
/* DBMS name: Delphi 7 */
/* Created on: 2006-09-13 21:00:00 */
/*==============================================================*/
procedure TfrmMain.FormCloseQuery(Sender: TObject;
var CanClose: Boolean);
begin
inherited;
ComServer.UIInteractive:=False;
if Not frmDMServer.adoConMain.Connected then
exit;
if frmDMServer.qryClientStatus.Active then
if frmDMServer.qryClientStatus.RecordCount > 0 then
begin
if (Application.MessageBox('关闭中间层系统将导致所有客户端无法连接,你确定需要关闭中间层系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDNO) then
canClose := false
else
try DisConnectAll(); except end;
end
else
begin
if (Application.MessageBox('您确定需要关闭中间层系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDNO) then
canClose := False;
end;
end;
procedure TfrmMain.DisConnect;
var
I: Integer;
begin
i := TStringGrid(ClientGrid).Row;
try
sskServer.Socket.Connections[i - 1].SendText(c_Disconnect);
sskServer.Socket.Connections[i - 1].Close;
frmDMServer.qryClientStatus.Delete;
except
end;
with frmDMServer.qryClientStatus do
if Active then Requery Else Open;
end;
procedure TfrmMain.DisConnectAll;
var
h: Integer;
begin
if frmDMServer.qryClientStatus.RecordCount > 0 then
begin
for h := 0 to frmDMServer.qryClientStatus.RecordCount - 1 do
begin
try
sskServer.Socket.Connections[h].SendText(c_Disconnect);
sskServer.Socket.Connections[h].Close;
frmDMServer.qryClientStatus.Delete;
except
end;
end;
with frmDMServer.qryClientStatus do
if Active then Requery else Open;
end;
end;
procedure TfrmMain.acDisSelectExecute(Sender: TObject);
begin
inherited;
if (Application.MessageBox('你确定要断开当前客户连接?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
DisConnect();
if frmDMServer.qryClientStatus.Fields[1].AsString = '' then
begin
acDisSelect.Enabled := false;
acDisall.Enabled := false;
acSendMessage.Enabled := false;
acReceiptMessage.Enabled := false;
end;
end;
procedure TfrmMain.acDisAllExecute(Sender: TObject);
begin
inherited;
if (Application.MessageBox('你确定要断开所有客户连接?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
DisConnectAll();
if frmDMServer.qryClientStatus.Fields[1].AsString = '' then
begin
acDisSelect.Enabled := false;
acDisall.Enabled := false;
acSendMessage.Enabled := false;
acReceiptMessage.Enabled := false;
end;
end;
procedure TfrmMain.sskServerClientError(Sender: TObject; Socket: TCustomWinSocket; ErrorEvent: TErrorEvent; var ErrorCode: Integer);
begin
inherited;
case ErrorEvent of
eeConnect:
Application.MessageBox('连接错误!', '信息', MB_OK + MB_ICONINFORMATION);
eeSend:
if bSendError then
Application.MessageBox('信息发送错误!', '信息', MB_OK + MB_ICONINFORMATION);
eeReceive:
Application.MessageBox('信息接收错误!', '信息', MB_OK + MB_ICONINFORMATION);
eeLookup:
Application.MessageBox('查找错误!', '信息', MB_OK + MB_ICONINFORMATION);
end;
ErrorCode := 0;
end;
/*==============================================================*/
/* Object name: 客户端程序 */
/* DBMS name: Delphi 7 */
/* Created on: 2006-09-13 21:00:00 */
/*==============================================================*/
procedure TfrmDMClient.cstLinkError(Sender: TObject; Socket: TCustomWinSocket; ErrorEvent: TErrorEvent; var ErrorCode: Integer);
begin
case ErrorEvent of
eeConnect:
Application.MessageBox(PChar('远程连接错误'+#13#10+'请尝试重新启动中间层和SCKTSRVR!'), '警告', MB_ICONSTOP);
eeSend:
Application.MessageBox(PChar('发送错误...'), '警告', MB_ICONSTOP);
eeReceive:
Application.MessageBox(PChar('接收错误...'), '警告', MB_ICONSTOP);
eeDisconnect:
Application.MessageBox(PChar('断开错误...'), '警告', MB_ICONSTOP);
eeLookup:
Application.MessageBox(PChar('查找错误...'), '警告', MB_ICONSTOP);
end;
ErrorCode:=0;
end;
//关闭所有窗体
procedure TfrmMain.muiWindowsCloseAllFormClick(Sender: TObject);
begin
CloseAllForm(Self);
end;
//退出系统
procedure TfrmMain.muiExitClick(Sender: TObject);
begin
Close;
end;
//注销
procedure TfrmMain.muiReLoginClick(Sender: TObject);
begin
if (Application.MessageBox('你确定要注销此系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
begin
if Assigned(frmDMClient) then
begin
if frmDMClient.cstLink.Socket.Connected then
begin
frmDMClient.cstLink.Socket.SendText(c_Close);
end;
end;
muiWindowsCloseAllFormClick(Sender);//关闭所有窗体
if Assigned(frmGuide) then frmGuide.Close; //关闭导航
proLogin(1);//注销
end;
end;
//窗体关闭
procedure TfrmMain.FormClose(Sender: TObject; var Action: TCloseAction);
begin
if not bMainClose then
if (Application.MessageBox('你确定要退出此系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
begin
CloseAllForm(Self);
frmDMClient.cstLink.Active:=false;
if Assigned(frmDMClient) then
begin
if frmDMClient.cstLink.Socket.Connected then
begin
frmDMClient.cstLink.Socket.SendText(c_Close);
end;
frmDMClient.Free;
end;
Action:=caFree;
end
else
Action:=caNone;
end;
这是我的三层结构的客户端和中间层的部份退出代码
现在的问题是:无论是客户端的非正常退出还是中间层的非正常关闭,都会导致所有的客户端再次登录时显示“断开错误”,其实主要的原因是客户端和中间层的退出机制有问题,没有对异常的正常处理,当中间层或是客户端当机或是直接关机而并未正常注销退出程序时用户信息未正常清除。请高手帮忙改一下,并且最好在中间层能给加一个心跳机制~~~~
高人现身吧
/* Object name: 服务器端程序 */
/* DBMS name: Delphi 7 */
/* Created on: 2006-09-13 21:00:00 */
/*==============================================================*/
procedure TfrmMain.FormCloseQuery(Sender: TObject;
var CanClose: Boolean);
begin
inherited;
ComServer.UIInteractive:=False;
if Not frmDMServer.adoConMain.Connected then
exit;
if frmDMServer.qryClientStatus.Active then
if frmDMServer.qryClientStatus.RecordCount > 0 then
begin
if (Application.MessageBox('关闭中间层系统将导致所有客户端无法连接,你确定需要关闭中间层系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDNO) then
canClose := false
else
try DisConnectAll(); except end;
end
else
begin
if (Application.MessageBox('您确定需要关闭中间层系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDNO) then
canClose := False;
end;
end;
procedure TfrmMain.DisConnect;
var
I: Integer;
begin
i := TStringGrid(ClientGrid).Row;
try
sskServer.Socket.Connections[i - 1].SendText(c_Disconnect);
sskServer.Socket.Connections[i - 1].Close;
frmDMServer.qryClientStatus.Delete;
except
end;
with frmDMServer.qryClientStatus do
if Active then Requery Else Open;
end;
procedure TfrmMain.DisConnectAll;
var
h: Integer;
begin
if frmDMServer.qryClientStatus.RecordCount > 0 then
begin
for h := 0 to frmDMServer.qryClientStatus.RecordCount - 1 do
begin
try
sskServer.Socket.Connections[h].SendText(c_Disconnect);
sskServer.Socket.Connections[h].Close;
frmDMServer.qryClientStatus.Delete;
except
end;
end;
with frmDMServer.qryClientStatus do
if Active then Requery else Open;
end;
end;
procedure TfrmMain.acDisSelectExecute(Sender: TObject);
begin
inherited;
if (Application.MessageBox('你确定要断开当前客户连接?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
DisConnect();
if frmDMServer.qryClientStatus.Fields[1].AsString = '' then
begin
acDisSelect.Enabled := false;
acDisall.Enabled := false;
acSendMessage.Enabled := false;
acReceiptMessage.Enabled := false;
end;
end;
procedure TfrmMain.acDisAllExecute(Sender: TObject);
begin
inherited;
if (Application.MessageBox('你确定要断开所有客户连接?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
DisConnectAll();
if frmDMServer.qryClientStatus.Fields[1].AsString = '' then
begin
acDisSelect.Enabled := false;
acDisall.Enabled := false;
acSendMessage.Enabled := false;
acReceiptMessage.Enabled := false;
end;
end;
procedure TfrmMain.sskServerClientError(Sender: TObject; Socket: TCustomWinSocket; ErrorEvent: TErrorEvent; var ErrorCode: Integer);
begin
inherited;
case ErrorEvent of
eeConnect:
Application.MessageBox('连接错误!', '信息', MB_OK + MB_ICONINFORMATION);
eeSend:
if bSendError then
Application.MessageBox('信息发送错误!', '信息', MB_OK + MB_ICONINFORMATION);
eeReceive:
Application.MessageBox('信息接收错误!', '信息', MB_OK + MB_ICONINFORMATION);
eeLookup:
Application.MessageBox('查找错误!', '信息', MB_OK + MB_ICONINFORMATION);
end;
ErrorCode := 0;
end;
/*==============================================================*/
/* Object name: 客户端程序 */
/* DBMS name: Delphi 7 */
/* Created on: 2006-09-13 21:00:00 */
/*==============================================================*/
procedure TfrmDMClient.cstLinkError(Sender: TObject; Socket: TCustomWinSocket; ErrorEvent: TErrorEvent; var ErrorCode: Integer);
begin
case ErrorEvent of
eeConnect:
Application.MessageBox(PChar('远程连接错误'+#13#10+'请尝试重新启动中间层和SCKTSRVR!'), '警告', MB_ICONSTOP);
eeSend:
Application.MessageBox(PChar('发送错误...'), '警告', MB_ICONSTOP);
eeReceive:
Application.MessageBox(PChar('接收错误...'), '警告', MB_ICONSTOP);
eeDisconnect:
Application.MessageBox(PChar('断开错误...'), '警告', MB_ICONSTOP);
eeLookup:
Application.MessageBox(PChar('查找错误...'), '警告', MB_ICONSTOP);
end;
ErrorCode:=0;
end;
//关闭所有窗体
procedure TfrmMain.muiWindowsCloseAllFormClick(Sender: TObject);
begin
CloseAllForm(Self);
end;
//退出系统
procedure TfrmMain.muiExitClick(Sender: TObject);
begin
Close;
end;
//注销
procedure TfrmMain.muiReLoginClick(Sender: TObject);
begin
if (Application.MessageBox('你确定要注销此系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
begin
if Assigned(frmDMClient) then
begin
if frmDMClient.cstLink.Socket.Connected then
begin
frmDMClient.cstLink.Socket.SendText(c_Close);
end;
end;
muiWindowsCloseAllFormClick(Sender);//关闭所有窗体
if Assigned(frmGuide) then frmGuide.Close; //关闭导航
proLogin(1);//注销
end;
end;
//窗体关闭
procedure TfrmMain.FormClose(Sender: TObject; var Action: TCloseAction);
begin
if not bMainClose then
if (Application.MessageBox('你确定要退出此系统吗?', '确认', MB_YESNO + MB_ICONQUESTION) = IDYES) then
begin
CloseAllForm(Self);
frmDMClient.cstLink.Active:=false;
if Assigned(frmDMClient) then
begin
if frmDMClient.cstLink.Socket.Connected then
begin
frmDMClient.cstLink.Socket.SendText(c_Close);
end;
frmDMClient.Free;
end;
Action:=caFree;
end
else
Action:=caNone;
end;
这是我的三层结构的客户端和中间层的部份退出代码
现在的问题是:无论是客户端的非正常退出还是中间层的非正常关闭,都会导致所有的客户端再次登录时显示“断开错误”,其实主要的原因是客户端和中间层的退出机制有问题,没有对异常的正常处理,当中间层或是客户端当机或是直接关机而并未正常注销退出程序时用户信息未正常清除。请高手帮忙改一下,并且最好在中间层能给加一个心跳机制~~~~
高人现身吧
解决方案 »
免费领取超大流量手机卡,每月29元包185G流量+100分钟通话, 中国电信官方发货