Ein kleines Chat-Programm

Chat (v. engl. to chat plaudern) ist die Bezeichnung für die innerhalb des Internet weit verbreitete Art der direkten Unterhaltung zwischen zwei oder mehreren Personen in Echtzeit. Es ist eine Art Computerkonferenz, die meist allerdings ohne Bilder auskommt. Stattdessen gebrauchen Teilnehmer, die zusammen "chatten", daher neben dem geschriebenen Wort auch Ersatzbilder (Avatare, Emoticons). Man trifft sich meist in Chatrooms zu verschiedenen Themen. Eine besondere Form sind die Webcam-Chats, bei denen man sich über Webcams sieht.
(aus WIKIPEDIA - die freie Enzyklopädie)


Programm Chat1

Im Programm steht die Verwaltung von Clientsockets in einem Serversocket im Vordergrund. Am Chat-Server können sich mehrere Chat-Clients anmelden, die dann untereinander Nachrichten austauschen können. Jede Verbindung erfordert einen eigenen Socket. Daher besteht der Unterschied zwischen einer Serversocket-Komponente und einer Clientsocket-Komponente im Wesentlichen darin, dass eine aktive  Serversocket-Komponente

Im Gegensatz zu echten Chat-Protokollen (z. B. das IRC Protoll, IRC = Internet Relay Chat), die in der Regel Zeichenketten mit einem festen Aufbau verwenden, wird hier eine Datenstruktur (Record TChatNachricht) verwendet, um die Funktionen SendBuf und ReceiveBuf vorzustellen.

Einige Merkmale des Programms Chat1:

Das Programm dient der Darstellung der benötigten Techniken. Es ist nicht praxistauglich, da es keinerlei Schutzmechanismen für Fehler beinhaltet, z. B.

Es gibt also noch genügend Möglichkeiten, dieses Programm zu verbessern.


Ein Datensatz für die Kommunikation

Die hier verwendeten Datenpakete enthalten neben der eigentlichen textuellen Nachricht noch den Anmeldenamen (Nickname) des Senders. Im Gegensatz zum weit verbreiteten IRC Protokoll, bei dem sämtliche übertragenen Informationen mit in dem Nachrichten-String codiert werden, wird hier ein Datenpaket als Datenstruktur übertragen..

TChatNachricht = Record
  Nickname: string[255];
  Text:     string[255]
end;


Übertragen von Datenpaketen des Typs TChatNachricht

Die Übertragung eines solchen Datensatzes mithilfe der Methoden SendBuf und ReceiveBuf geschieht byteweise und unstrukturiert.

function SendBuf (var Buf; Count: Integer): Integer;
Schreibt einen beliebigen, unstrukturierten, nicht typisierten Datenbereich Buf (= 'Buffer') in die Socketverbindung. Bei der Datenübertragung ist immer die Länge Count der Daten (= Anzahl Bytes) anzugeben, damit der Empfänger weiß wie groß die Datenmenge ist.
  
function ReceiveBuf (var Buf; Count: Integer): Integer;
Liest einen beliebigen, unstrukturierten, nicht typisierten Datenbereich Buf (= 'Buffer') der Länge Count (Bytes) aus der Socketverbindung.
  

Einige Hinweise zur Verwendung dieser Methoden:


Beispiel:  Senden einer Chat-Nachricht

Beim Drücken der Schaltfläche BtSenden wird der Anmeldename aus dem Edit-Feld EdNickname und die Nachricht im Editfeld EdSenden an den Chat-Server gesendet.

procedure TFrmClient.BtSendenClick(Sender: TObject);
var Nachricht: TChatNachricht;
begin
  Nachricht.Nickname := EdNickname.Text;
  Nachricht.Text := EdSenden.Text;
  ClientSocket.Socket.SendBuf (Nachricht, SizeOf(Nachricht));
end; 
Datenpaket
 
initialisieren, dann

senden



Beispiel:  Anmelden und Abmelden beim Chat-Server

Meldet sich ein neuer Teilnehmer beim Chat-Server an, wird für ihn ein neuer Socket angelegt und das Ereignis OnConnect ausgelöst. Der Chat-Server reagiert auf dieses Ereignis, indem er


procedure TFrmServer.ServerSocketClientConnect (Sender: TObject; Socket: TCustomWinSocket);
var Nachricht: TChatNachricht;
    var I: Integer;
begin
  MemStatus.Lines.Add ('Status: Neuer Client verbunden');

  Nachricht.NickName := 'Server';
  Nachricht.Text := 'Willkommen am Chat-Server';
  Socket.SendBuf (Nachricht, SizeOf(Nachricht));

  with ServerSocket.Socket do begin
    Nachricht.Nickname := 'Server';
    Nachricht.Text := 'Jetzt ' + IntToStr(ActiveConnections) + ' Teilnehmer';
    for I := 0 to ActiveConnections-2 do
      Connections[I].SendBuf (Nachricht, SizeOf(Nachricht))
  end; {with}

end;





Willkommensgruß



Info



Verwalten der Client-Sockets im Server-Socket

Der Programmausschnitt oben zeigt auch zugleich die Verwaltung der einzelnen Sockets in der Serversocket-Komponente:

Typische Zugriffmechanismen auf die Socket-Verwaltung

Anzahl der verwalteten Sockets:

if (ServerSocket.Socket.ActiveConnections > 0)
  then begin

      {Client-Sockets sind mit dem Server verbunden}

  end;

Indizierter Zugriff:

Die Nummerierung der Sockets beginnt immer bei 0. Der 4. Socket hat also den Index 3. Voraussetzung: ActiveConnections >= 4.

ServerSocket.Socket.Connections[3].SendText ('Nachricht an 4. Socket');

Iteration über alle Sockets:

Eine Nachricht an alle verbundenen Clients (wie z. B. im Programm Chat1) wird damit in der Regel mithilfe einer Schleife über diese Feldstruktur realisiert:

For I := 0 to ServerSocket.Socket.ActiveConnections-1 do begin
  ServerSocket.Socket.Connections[I].SendText (' ... ');
    ...
end;

Detailliertere Informationen zu den an der Verwaltung der Sockets beteiligten Klassen finden Sie z. B. in der Beschreibung der Klasse TServerSocket.

  Download Programm Chat1 (Delphi 7): Chat1.zip

Mögliche Erweiterungen von Programm Chat1

Hier endet nun die Beschreibung der Möglichkeiten und Techniken, die das Programmiersystem Delphi in Form der Komponenten TServerSocket und TClientSocket zur Verfügung stellt. "Algorithmisch" wird das Thema an dieser Stelle jetzt erst richtig interessant.

Als Beispiel betrachten wir die folgende mögliche Erweiterung:

Programm Chat2: Der Benutzer eines solchen Chat-Programms kann einem der aktiven Chat-Teilnehmer eine private Nachricht schicken.





Für dieser Erweiterung ergibt sich im Gegensatz zur "Sammelnachricht an alle" des Programms Chat1 die Notwendigkeit, Teilnehmer (Sender wie Empfänger) gezielt zu identifizieren und über "Ihren" Socket anzusprechen. Der Server muss also z. B. die Anmeldenamen aller verbundenen Clients verwalten, die Eindeutigkeit des Nicknamens garantieren, diesen Teilnehmer über "seinen" Socket" ansprechen können usw.

Vielleicht wird man hierzu die hier vorgestellten Record-Struktur TChatNachricht um weitere Bestandteile erweiteren müssen, oder man verabschiedet sich von dieser Datenstruktur und verwendet statt dessen das im Internet weit verbreitete IRC Protokoll.

In jedem Fall treten jetzt die Techniken der Socket-Kommunikation in den Hintergrund, und die für komplexere Client-Server-Anwendungen notwendigen Kommunikationsprotokolle stehen im den Mittelpunkt der Betrachtungen.

        


(FvSG 30.1.2006)