我正在尝试将用 Delphi 编写的客户端应用程序连接到使用 TCP/IP 的服务器上运行的服务。该服务也是用 Delphi 编写的,并使用 TIdTCPServer 来监听连接。当客户端应用程序尝试连接到服务时,我收到错误“连接被拒绝”。该服务似乎工作正常,所有侦听和进一步步骤(通过 ADO 连接到数据库)都在线程中进行。
这是我已经检查过的:
class function OperationThread.DefaultHost: string;
begin
Result := '127.0.0.1';
end;
class function OperationThread.DefaultPort: Integer;
begin
Result := 5000;
end;
procedure ServiceController(CtrlCode: DWord); stdcall;
begin
MyService.Controller(CtrlCode);
end;
function TTestService2.GetServiceController: TServiceController;
begin
Result := ServiceController;
end;
procedure TTestService2.ServiceExecute(Sender: TService);
begin
while not Terminated do
begin
ServiceThread.ProcessRequests(False);
TThread.Sleep(1000);
end;
end;
procedure TTestService2.ServiceStart(Sender: TService; var Started: Boolean);
begin
try
FBackgroundThread := TBackgroundThread.Create(
ADOConnection1, DBemployesConnection, ADOQuery1, ADOQuery2, ADOQuery3, IdTCPServer1);
FBackgroundThread.Start;
Started := True;
except
on E: Exception do
begin
Started := False;
end;
end;
end;
procedure TTestService2.ServiceStop(Sender: TService; var Stopped: Boolean);
begin
try
if Assigned(FBackgroundThread) then
begin
FBackgroundThread.Terminate;
FBackgroundThread.WaitFor;
FreeAndNil(FBackgroundThread);
end;
Stopped := True;
except
on E: Exception do
begin
Stopped := False;
end;
end;
end;
procedure TTestService2.ServicePause(Sender: TService; var Paused: Boolean);
begin
FBackgroundThread.Pause;
Paused := True;
end;
procedure TTestService2.ServiceContinue(Sender: TService; var Continued: Boolean);
begin
FBackgroundThread.Continue;
Continued := True;
end;
以及我在服务中使用的线程代码:
constructor TBackgroundThread.Create(ADOConnection, DBEmployesConnection: TADOConnection;
ADOQuery1, ADOQuery2, ADOQuery3: TADOQuery; IdTCPServer: TIdTCPServer);
begin
inherited Create(True);
FADOConnection := ADOConnection;
FDBEmployesConnection := DBEmployesConnection;
FADOQuery1 := ADOQuery1;
FADOQuery2 := ADOQuery2;
FADOQuery3 := ADOQuery3;
FIdTCPServer := IdTCPServer;
FreeOnTerminate := True;
FADOConnection.Connected := True;
FDBEmployesConnection.Connected := True;
FIdTCPServer.Active := True;
end;
destructor TBackgroundThread.Destroy;
begin
if Assigned(FADOConnection) then
FADOConnection.Free;
if Assigned(FDBEmployesConnection) then
FDBEmployesConnection.Free;
if Assigned(FADOQuery1) then
FADOQuery1.Free;
if Assigned(FADOQuery2) then
FADOQuery2.Free;
if Assigned(FADOQuery3) then
FADOQuery3.Free;
FIdTCPServer.Active := False;
inherited;
end;
procedure TBackgroundThread.Continue;
begin
FPaused := False;
end;
procedure TBackgroundThread.Execute;
begin
CoInitialize(nil);
try
FIdTCPServer.OnExecute := IdTCPServer1Execute;
while not Terminated do
begin
if not FPaused then
begin
// Główne zadania wątku
// Na przykład przetwarzanie zapytań, jeśli istnieją
end
else
begin
Sleep(100);
end;
Sleep(10);
end;
FIdTCPServer.Active := False;
finally
CoUninitialize;
end;
end;
procedure TBackgroundThread.IdTCPServer1Execute(AContext: TIdContext);
var
Request: string;
Response: string;
begin
try
Request := AContext.Connection.IOHandler.ReadLn;
ProcessRequest(Request, Response);
AContext.Connection.IOHandler.WriteLn(Response);
except
on E: Exception do
begin
Response := '{"status":"error", "message":"Błąd podczas przetwarzania zadania: ' + E.Message + '"}';
AContext.Connection.IOHandler.WriteLn(Response);
end;
end;
end;
procedure TBackgroundThread.Pause;
begin
FPaused := True;
end;
其余代码并不重要,并且运行良好。
尝试为应用程序的每个步骤和 IdTcpServer 事件添加日志记录,写入日志侦听状态和其他服务器参数。最简单的方法 - 编写简单的控制台应用程序。 另外,您的服务的权限可能存在问题。检查哪个用户正在运行该服务。