Подскажите пожалуйста пример работы с lNet

Модератор: Модераторы

Подскажите пожалуйста пример работы с lNet

Сообщение Freezz » 13.03.2015 14:07:38

Добрый день, в примерах к lNet есть проект testnet, в котором показано как работать с компанентами TCP и UDP.
Но там сообщения от сервера получают все клиенты, а как сделать что бы сообщение получал определенный клиент?
Первы раз взялся за клиент серверное приложение, застрял на этом, не пинайте сильно :roll:
Freezz
новенький
 
Сообщения: 10
Зарегистрирован: 13.03.2015 13:23:22

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Vadim » 13.03.2015 19:04:24

Почему все? Только тот клиент, который связался с сервером. Вот смотрите:
Код: Выделить всё
Address := ParamStr(1);

Это как раз тот адрес, который Вы задали клиенту для связи с сервером. Соответственно и ответ получит тот же самый клиент, а вовсе не Билл Гейтс. ;-)
На всякий случай - смотрите в каталоге examples/ltcp/. А то вдруг Вы куда-то не в тот пример залезли... :-)
Vadim
долгожитель
 
Сообщения: 4112
Зарегистрирован: 05.10.2006 08:52:59
Откуда: Красноярск

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Freezz » 16.03.2015 10:23:16

Vadim, спасибо что ответили.
В данном примере со стороны сервера нет возможности отправлять сообщения на клиенты.
А если отправляешь сообщение с одного клиента, то второй клиент тоже получает это сообщение.
Мне же надо организовать отправку сообщения только на одного из подключившихся клиентов, зная, например, его ip-адрес.
Я смотрел пример examples/visual/tcpudp, там можно отправлять сообщения как с клиентов, так и с сервера, но все рано сообщения получают все...
Freezz
новенький
 
Сообщения: 10
Зарегистрирован: 13.03.2015 13:23:22

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Vadim » 16.03.2015 11:31:29

Freezz
Вот смотрите. Сервер просто слушает сеть и ждёт, кто чего ему скажет. Поэтому отправить сообщение можно только на конкретный адрес.
UDP предназначен для быстрого обмена сообщениями, без гарантии их доставки. Поэтому применение udp чревато... Лучше, если нет необходимости обмениваться агромадными объёмами данных, использовать протокол TCP.
Конкретно, в том примере, который Вы указали, применяется функция SendToAll() - название говорит само за себя ;-) сами понимаете, ничего другого, как посылка сообщений всей округе ждать от этой функции нечего. Данная функция как раз и заведует тем, чтобы никто не ушёл несообщённым. ;-) Для этого используется специальный широковещательной маской сети, которая в примере представлена константой LADDR_BR и является на самом деле вот этим: 255.255.255.255.
Именно по этой причине и на основании Вашего вопроса, я предложил Вам другой пример, который отвечает поставленной Вами задаче. Не смотрите, что это пример для консоли. Связь и обмен сообщениями сервера с клиентом не имеют никакого отношения ни к окнам ни к консоли. Хотите окошки - вставляете код классов в свои окошки и вперёд... ;-)
Vadim
долгожитель
 
Сообщения: 4112
Зарегистрирован: 05.10.2006 08:52:59
Откуда: Красноярск

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Freezz » 16.03.2015 12:35:02

Vadim, у меня в голове полная каша образовалась пока я эти примеры рассматривал :shock:
Я наверное, просто непонятно вопрос задаю...
Давайте так, вот этот кусочек программы, перебирая всех подключенных клиентов, отправляет им сообщение. Всем.
Код: Выделить всё
FNet.IterReset; // start at server socket
while FNet.IterNext do begin // skip server socket, go to clients only
  n := FNet.SendMessage(aMsg, FNet.Iterator);
  if n < Length(aMsg) then
    MemoText.Append('Error on send [' + IntToStr(n) + ']');
end;

Мне же надо выбрать одного из клиентов и передать ему сообщение.
Я так понимаю надо в строке n := FNet.SendMessage(aMsg, FNet.Iterator); вместо FNet.Iterator подставить указание на конкретного клиента, соответственно убрав цикл while do.
Так вот ЧТО именно надо написать, зная ip-адрес клиента?
Спасибо за терпение, первый раз пытаюсь написать подобное приложение. Про lNet в интернете что-то ничего внятного не нашел, поэтому и решил на форуме вопрос задать.
Freezz
новенький
 
Сообщения: 10
Зарегистрирован: 13.03.2015 13:23:22

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Vadim » 16.03.2015 12:58:35

У lnet примеры довольно понятные, наверно поэтому и документации подробной нет.
В методе SendMessage(aMsg, FNet.Iterator), параметр FNet.Iterator - это сокет, который содержит в себе адрес того, кому направляется сообщение. Следовательно нужно этот адрес узнавать во время пробежки по списку сокетов-клиентов и если нашёлся подходящий - слать ему сообщение. В общем случае должно быть что-то вроде:
Код: Выделить всё
while FNet.IterNext do
  If FNet.Iterator.LocalAddress='192.168.0.12' Then //адрес взят с потолка ;-)
  Begin
    FNet.SendMessage(aMsg, FNet.Iterator);
    Exit;  //Выходим из цикла, он нам больше не нужен
  End;
 

Или так, если Вы знаете, под каким номером в списке сидит клиент:
Код: Выделить всё
Var
  mySock: TLSocket;
Begin
  mySock:=FNet.Socks[Номер_клиента_по_списку_начиная_с_нуля];
  mySock.SendMessage(aMsg);
End;
Vadim
долгожитель
 
Сообщения: 4112
Зарегистрирован: 05.10.2006 08:52:59
Откуда: Красноярск

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Freezz » 16.03.2015 13:21:18

Vadim, огромное спасибо! То что нужно было! Первый вариант отлично подойдет.
Freezz
новенький
 
Сообщения: 10
Зарегистрирован: 13.03.2015 13:23:22

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Freezz » 18.03.2015 10:00:35

Уважаемый Vadim, а можно ли в lNet открыть для прослушивания два порта?
Попробовал сделать так:
Код: Выделить всё
procedure TLTCPrmtserver.Run;
var
  quit: Boolean;
  s: String;
  c: Char;
begin
  quit := false;
  s := '';                       
  FNet.Listen(1305);
  FNet.Listen(1501);
  Writeln('Сервер запущен');
  Writeln('''Escape'' - выход');
  repeat
    FNet.CallAction;
    if KeyPressed then begin
      c := ReadKey;
      case c of
        #27: quit := true;
        #8: begin
          if Length(s) > 1 then Delete(s, Length(s) - 1, 1)
          else s := '';
          GotoXY(WhereX - 1, WhereY);
          Write(' ');
          GotoXY(WhereX - 1, WhereY);
        end;
        #10,
        #13: begin
          FNet.SendMessage(s);
          s := '';
          Writeln;
        end;
        else begin
          s := s + c;
          Write(c);
        end;
      end;
    end;
  until quit;
end;           

открывается только один порт, и почему-то второй из списка (в данном случае 1501).
И, кстати, FNet.aSocket.PeerPort всегда выдает ноль почему-то :(
хотя FNet.aSocket.PeerAddress правильно выдает адрес подсоединившегося клиента.
Freezz
новенький
 
Сообщения: 10
Зарегистрирован: 13.03.2015 13:23:22

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Снег Север » 18.03.2015 12:42:55

Не скажу конкретно про lNet, но как правило, для двух портов надо иметь два разных экземпляра компонента. У вас же в коде всё логично - вы переопределяете вторым вызовом порт для прослушивания и прослушивается только он.
Аватара пользователя
Снег Север
долгожитель
 
Сообщения: 3039
Зарегистрирован: 27.11.2007 16:14:47

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Vadim » 18.03.2015 13:33:45

Freezz
Действительно, Снег Север совершенно прав - каждый созданный экземпляр объекта может прослушивать только один порт.
Vadim
долгожитель
 
Сообщения: 4112
Зарегистрирован: 05.10.2006 08:52:59
Откуда: Красноярск

Re: Подскажите пожалуйста пример работы с lNet

Сообщение Freezz » 18.03.2015 13:40:57

Снег Север, Vadim спасибо вам, ведь действительно ответ лежал на поверхности. Надо сделать перерыв, скушать твикс :D
Freezz
новенький
 
Сообщения: 10
Зарегистрирован: 13.03.2015 13:23:22


Вернуться в Сети

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 7

Рейтинг@Mail.ru