Solved

Console App Help...

Posted on 2004-04-01
19
1,096 Views
Last Modified: 2008-02-01
Hello,
 I have this code but I need some help with it

Program Project2;

{$APPTYPE CONSOLE}

Uses
  SysUtils, ScktComp;

Type
  TMyApp = Class(TObject)
    Public
      Procedure Connect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Disconnect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Receive(Sender: TObject; Socket: TCustomWinSocket);
  End;

Var
  MyApp: TMyApp; Server: TServerSocket;

Procedure TMyApp.Connect(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn('Connected.') End;
Procedure TMyApp.Disconnect(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn('Disconnected.') End;
Procedure TMyApp.Receive(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn(Socket.ReceiveText) End;

Begin
  MyApp := TMyApp.Create;
  Server := TServerSocket.Create(nil);
  Server.OnClientConnect := MyApp.Connect;
  Server.OnClientDisconnect := MyApp.Disconnect;
  Server.OnClientRead := MyApp.Receive;
  Server.Port := 6000;
  Server.Active := True;
  While True Do ReadLn;
End.

But I think the
   While True Do ReadLn;

Is blocking the ServerSocket, how can I fix this?
I will give more points but this is all I have at the mo.

Thx Karamja
0
Comment
Question by:-Karamja-
[X]
Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people just like you are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
  • 11
  • 7
19 Comments
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10734709
you might want to try adding a timer

set it interval property for say 3000 //every 3 seconds

Begin
 timer1:= TTimer.Create;
 timer1.enabled:= false;
 timer1.OnTImer:= MyTImer;
  MyApp := TMyApp.Create;
  Server := TServerSocket.Create(nil);
  Server.OnClientConnect := MyApp.Connect;
  Server.OnClientDisconnect := MyApp.Disconnect;
  Server.OnClientRead := MyApp.Receive;
  Server.Port := 6000;
  Server.Active := True;
  Timer1.Enabled:= True;
End.


procedure MyTimer(Sender: TObject);
var
 tmp: String;
begin
tmp:=  Server.Readln;
if tmp <> '' then
// DoSomething with tmp
end;


don't forget to free your timer & server on forms close


Shane
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10734732
procedure MyTimer(Sender: TObject);
var
 tmp: String;
begin
tmp:=  Readln;
if tmp <> '' then
// DoSomething with tmp
end;


this will continue until you call timer1.enabled:= false;

Shane
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10734737
sorry

timer1:= TTimer.Create(nil);

Shane
0
Industry Leaders: We Want Your Opinion!

We value your feedback.

Take our survey and automatically be enter to win anyone of the following:
Yeti Cooler, Amazon eGift Card, and Movie eGift Card!

 
LVL 11

Expert Comment

by:shaneholmes
ID: 10734962
Program Project2;

{$APPTYPE CONSOLE}

Uses
  SysUtils, ScktComp, ExtCtrls;

Type
  TMyApp = Class(TObject)
    Public
      Procedure Connect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Disconnect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Receive(Sender: TObject; Socket: TCustomWinSocket);
      Procedure MyTimer(Sender: TObject);
  End;

Var
  MyApp: TMyApp; Server: TServerSocket;
  Timer1: TTimer;

Procedure TMyApp.Connect(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn('Connected.') End;
Procedure TMyApp.Disconnect(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn('Disconnected.') End;
Procedure TMyApp.Receive(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn(Socket.ReceiveText) End;

procedure MyTimer(Sender: TObject);
var
 tmp: String;
begin
tmp:=  Readln;
if tmp <> '' then
begin
 //do something here
end;
end;
 

Begin
 Timer1:= TTimer.Create(nil);
 Timer1.Enabled:= false;
 Timer1.OnTimer:= MyTimer
  MyApp := TMyApp.Create;
  Server := TServerSocket.Create(nil);
  Server.OnClientConnect := MyApp.Connect;
  Server.OnClientDisconnect := MyApp.Disconnect;
  Server.OnClientRead := MyApp.Receive;
  Server.Port := 6000;
  Server.Active := True;
  Timer1.Enabled:= True
End.


you also need to figure out how you are going to free up your objects when program terminates

Timer1.Free
 Server.Free;


You might want to do it in the MyTimer event.

You check for some logic then free them

Shane
0
 
LVL 2

Author Comment

by:-Karamja-
ID: 10735106
[Error] Project1.dpr(29): Incompatible types: 'String' and 'procedure, untyped pointer or untyped parameter'
[Error] Project1.dpr(41): Incompatible types: 'method pointer and regular procedure'
[Error] Project1.dpr(14): Unsatisfied forward or external declaration: 'TMyApp.MyTimer'

??????????
0
 
LVL 2

Author Comment

by:-Karamja-
ID: 10735119
At this line btw
tmp:= Readln;
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10735196
Building you an example right now


Shane
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10735229
program Project1;

uses
  Forms,
  Unit2 in 'Unit2.pas';

{$R *.res}

begin
 Server.Active := True;
 Timer.Enabled:= True;
end.





unit Unit2;

interface

uses
 SysUtils, ScktComp, ExtCtrls, Dialogs;

Type
  TMyApp = Class(TObject)
    Public
      Procedure Connect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Disconnect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Receive(Sender: TObject; Socket: TCustomWinSocket);
      Procedure MyTimer(Sender: TObject);
  End;

var
 MyApp: TMyApp;
 Server: TServerSocket;
 Timer: TTimer;
 ReceivedText: String;

implementation

Procedure TMyApp.Connect(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn('Connected.') End;
Procedure TMyApp.Disconnect(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn('Disconnected.') End;
Procedure TMyApp.Receive(Sender: TObject; Socket: TCustomWinSocket); Begin WriteLn(Socket.ReceiveText) End;

procedure TMyApp.MyTimer(Sender: TObject);
begin
 //
end;


initialization
begin
 Timer:= TTimer.Create(nil);
 Timer.Enabled:= false;
 Timer.OnTimer:= MyApp.MyTimer;
 MyApp := TMyApp.Create;
 Server := TServerSocket.Create(nil);
 Server.OnClientConnect := MyApp.Connect;
 Server.OnClientDisconnect := MyApp.Disconnect;
 Server.OnClientRead := MyApp.Receive;
 Server.Port := 6000;
end;

finalization
begin
 Timer.Free;
 Server.Free;
end;
end.
0
 
LVL 2

Author Comment

by:-Karamja-
ID: 10735329
Ok, thx for your quick reply but I think you messed up a bit.

I am making a console app but you have done this a a normal project with units

{$APPTYPE CONSOLE}
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10735359
program Project1;
No, i no your doing a Console app. I just figured out the timer wont work.

Although, I added the second unit, so you could free the Objects

Try This,

Shane



{$APPTYPE CONSOLE}
uses
  Forms,
  Unit2 in 'Unit2.pas';


{$R *.res}

begin
 Server.Active := True;
 System.Readln;
end.


unit Unit2;

interface

uses
 SysUtils, ScktComp, ExtCtrls;

Type
  TMyApp = Class(TObject)
    Public
      Procedure Connect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Disconnect(Sender: TObject; Socket: TCustomWinSocket);
      Procedure Receive(Sender: TObject; Socket: TCustomWinSocket);
  End;

var
 MyApp: TMyApp;
 Server: TServerSocket;

implementation

Procedure TMyApp.Connect(Sender: TObject; Socket: TCustomWinSocket);
Begin
 WriteLn('Connected.')
End;

Procedure TMyApp.Disconnect(Sender: TObject; Socket: TCustomWinSocket);
Begin
 WriteLn('Disconnected.')
End;

Procedure TMyApp.Receive(Sender: TObject; Socket: TCustomWinSocket);
Begin
 WriteLn(Socket.ReceiveText)
End;


initialization
begin
 MyApp := TMyApp.Create;
 Server := TServerSocket.Create(nil);
 Server.OnClientConnect := MyApp.Connect;
 Server.OnClientDisconnect := MyApp.Disconnect;
 Server.OnClientRead := MyApp.Receive;
 Server.Port := 6000;
end;

finalization
begin
 MyApp.Free;
 Server.Free;
end;
end.
0
 
LVL 2

Author Comment

by:-Karamja-
ID: 10735561
Right even tho this code works we are back to step one,
Somethink is blocking it again
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10735666
Something is blocking what?

The socket from receiving data?

SHane
0
 
LVL 2

Author Comment

by:-Karamja-
ID: 10735819
That or showing it
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10735846
did you try doing any type of break points, or write statements at certain points to test ...


example, the OnReceive event

Shane
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10735849
I can't test it, cause i don't have anything coming across that port

Shane
0
 
LVL 2

Author Comment

by:-Karamja-
ID: 10736098
1) You could change port to test
2) http://127.0.0.1:6000 Should call the on connect event
0
 
LVL 11

Expert Comment

by:shaneholmes
ID: 10736195
What i believe you want to do is in fact hard to accommplish in a console app
rather than in a GUI app.
A GUI app typically sits idly waiting in the message loop for messages to come it to
process. Sockets create background threads that need to Synchronize to the
main threads for the socket events, and the synchronization is done using
messages. So, no message loop, no synchronization. And a console app typically
does not have a message loop, it sits waiting for console input events if it
is not a linear processing code flow anyway.

So i would make a little VCl app, using a main form with a memo as output
window instead of a console.

It is surely possible to get this to work with a console as well, but it
requires a whole lot more work.

Would you consider a invisible form?

A Borderless form?

SOmething other than a Console app?

Shane
0
 
LVL 19

Accepted Solution

by:
Melih SARICA earned 55 total points
ID: 10739220
Here is a running example

How to test:
 open internet explorer and type this address

   http://127.0.0.1:5555


 

program Project1;

{$APPTYPE CONSOLE}

uses
  sockets,windows;

type
  TmySocket = class(TObject)
    mServer : TTcpServer;
    public
      procedure Create;
      Procedure Destroy;
      property TCPServer : TTcpServer read mserver write mserver;
    protected
      Procedure mOnAccept (Sender: TObject; ClientSocket: TCustomIpClient);
  end;
var
  mysock : TmySocket;
  msg : tagMSG;
{ TmySocket }

procedure TmySocket.Create;
begin
  mServer:=TTcpServer.Create(nil);
end;

procedure TmySocket.Destroy;
begin
 mServer.Free;
end;

procedure TmySocket.mOnAccept(Sender: TObject;ClientSocket: TCustomIpClient);
var
   mbuf : pchar;
   dlen : integer;
   mstr : string ;
begin
   writeln(clientSocket.remotehost);
   mstr :=clientSocket.remotehost+ ' ->Just To see if that is send';
   ClientSocket.Sendln(mstr);
   ClientSocket.ReceiveBuf(mbuf,dlen,0);
end;

begin
  mysock.Create;
  mysock.TCPServer.LocalPort:='5555';
  mysock.TCPServer.OnAccept:=mysock.mOnAccept;
  mysock.TCPServer.Active:=true;
  while GetMessage(Msg, 0, 0, 0) <> BOOL(FALSE) do begin
   TranslateMessage(Msg);
   DispatchMessage(Msg);
  end;
  mysock.TCPServer.Active:=false;
  mysock.Destroy;

end.
0
 
LVL 2

Author Comment

by:-Karamja-
ID: 10739470
Thx, your code worked fine.
Also thx for your quick replys
0

Featured Post

On Demand Webinar: Networking for the Cloud Era

Ready to improve network connectivity? Watch this webinar to learn how SD-WANs and a one-click instant connect tool can boost provisions, deployment, and management of your cloud connection.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Have you ever had your Delphi form/application just hanging while waiting for data to load? This is the article to read if you want to learn some things about adding threads for data loading in the background. First, I'll setup a general applica…
Introduction I have seen many questions in this Delphi topic area where queries in threads are needed or suggested. I know bumped into a similar need. This article will address some of the concepts when dealing with a multithreaded delphi database…
NetCrunch network monitor is a highly extensive platform for network monitoring and alert generation. In this video you'll see a live demo of NetCrunch with most notable features explained in a walk-through manner. You'll also get to know the philos…
If you’ve ever visited a web page and noticed a cool font that you really liked the look of, but couldn’t figure out which font it was so that you could use it for your own work, then this video is for you! In this Micro Tutorial, you'll learn yo…

726 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question