Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2002.12.02;
Скачать: CL | DM;

Вниз

Обсуждение статьи   Найти похожие ветки 

 
megatrend ©   (2002-09-25 18:22) [0]

http://delphi.mastak.ru/articles/sockadv/index.html

Есть такой вопрос. Ниже приводится код сервера, в который вставлена моя отладочная печать. В коде есть некоторая ошибка, приводящая к тому, что когда на сервере есть N пользователей и к ним присоединяется N+1, то контактный лист посылается ВСЕМ N+1 раз.

Как бы это побороть? Ведь это расходы на трафик и процессорное
время.

procedure TForm1.ServerSocket1ClientRead(Sender: TObject;
Socket: TCustomWinSocket);
var s: string;
i: Integer;
begin
{сохраняем в s присланную нам строку}
s := Socket.ReceiveText;
{Если кто-то прислал нам свое имя}
if Copy(s,1,2) = "#N" then begin
Delete(s,1,2);
{Добавляем его в юзер лист}
ListBox1.Items.Add(s);
say2log("Новый пользователь "+s);
{Записываем в s команду для посылки нового списка юзеров}
s := "#U";
for i := 0 to ListBox1.Items.Count-1 do
s := s+ListBox1.Items[i]+";";
{...и рассылаем этот список всем клиентам}
say2log("Всего соединений
"+inttostr(ServerSocket1.Socket.ActiveConnections));
for i := 0 to ServerSocket1.Socket.ActiveConnections-1 do
ServerSocket1.Socket.Connections[i].SendText(s);
Exit;
end;

...

Пример : В чат вошли друг за другом
Дима Белянцев, Олег Белянцев, Женя Белянцев.
Затем вышел Женя, Олег, Дима.

Вот итоговый лог на сервере.

25.09.2002 17:57:51 Сервер запущен
25.09.2002 17:59:21 Новый пользователь Дима Белянцев
25.09.2002 17:59:21 Всего соединений 1

25.09.2002 17:59:27 Новый пользователь Дима Белянцев
25.09.2002 17:59:27 Всего соединений 2
25.09.2002 17:59:27 Новый пользователь Олег Белянцев
25.09.2002 17:59:27 Всего соединений 2

25.09.2002 17:59:28 Новый пользователь Дима Белянцев
25.09.2002 17:59:28 Всего соединений 3
25.09.2002 17:59:28 Новый пользователь Олег Белянцев
25.09.2002 17:59:28 Всего соединений 3
25.09.2002 17:59:28 Новый пользователь Женя Белянцев
25.09.2002 17:59:28 Всего соединений 3

25.09.2002 17:59:36 Новый пользователь Дима Белянцев
25.09.2002 17:59:36 Всего соединений 2
25.09.2002 17:59:36 Новый пользователь Олег Белянцев
25.09.2002 17:59:36 Всего соединений 2

25.09.2002 17:59:38 Новый пользователь Дима Белянцев
25.09.2002 17:59:38 Всего соединений 1


 
megatrend ©   (2002-09-26 10:04) [1]

Еще один глюк такой технологии написании чата : клиенту при дисконнекте одного из других клиентов (сервер начинает построение списка контактов с нуля) несколько раз передается все возрастающий список контактов (начиная с первого приславшего имя серверу), из-за чего некоторые списки контактов от сервера сливаются в один.


 
megatrend ©   (2002-09-27 09:25) [2]

?


 
Anatoly Podgoretsky ©   (2002-09-27 09:33) [3]

Так надо технологию менять, новому клиенту посылать весь список, а другим только дельту


 
VID ©   (2002-09-27 10:01) [4]

>некоторые списки контактов от сервера сливаются в один

Нормальное явление. на приёмнике пакета, надо просто реализовать "расклеивание" таких пакетов. Вообще эта тема обсуждалась на этой конфе, посмотри на 2,3,4 страницах

А вообще, тебе надо понять, что принятая в этом чате методика получения списка пользователей не очень хорошая (даже можно сказать - очень нехорошая :)

Там для получения списка контактов, всем клиентам рассылается команда "Отправь на сервер свой логин". А должно быть иначе:
при входе клиента в чат, его логин и пароль добавляются в список LOGPASList:TStringList; (LogPasList.Add(Login+"="+Password);)
при отключении/выходе этот логин удаляется из LogPasList"а

а в нужный момент, когда необходимо клиенту отправить список пользователей, ему просто будет необходимо отправить левую часть (до знака "=") каждой строки LogPasList"а.

А насчёт того, что при каждом коннекте или дисконнекте клиента, всем остальным будет рассылаться полный список... Стоит ли беспокоиться из-за этого ? Особо много траффа это не сожрёт.
Хотя конечно можно не полный список всем рассылать, а только ЛОГИН НОВОГО/ОТКЛЮЧИВШЕГОСЯ КЛИЕНТА (со спец командой), а самому этом клиенту - "виновнику торжества" полный лист... в-общем, как уже сказал Подгоретский.


 
Anatoly Podgoretsky ©   (2002-09-27 10:07) [5]

Естественно надо иметь возможность "Обновить весь список"


 
megatrend ©   (2002-09-30 13:19) [6]

Спасибо за ответы. Я вот переползаю на этот чат с чата-NMMsg. При использовании NMMsg открытие сокетов происходит при отправке каждого сообщения, а здесь сокеты открываются при начале работы 1 раз.

Хотелось бы знать, как будут влиять "падения" сети на работу чата? Как открытый на клиенте сокет отнесется к тому, что в период его бездействия свяхь с сервером временно прерывалась?


 
VID ©   (2002-09-30 19:31) [7]

Прервалась связь - возникнет событие onDisconnect или onError.
В onError пиши
Client.Socket.Disconnect(Socket.SocketHandle);

Поэтому необходимо реализовать механизм реконнекта.
Он был уже описан мною в этой конфе, поищи на страницах...


 
megatrend ©   (2002-10-01 10:46) [8]

2 VID : Поиском не нашел этот механизм реконнекта. Видимо, форум индексируется не сразу.


 
VID ©   (2002-10-01 10:54) [9]

Var CanConnect:Boolean = False;

timer1.interval = 10000;//10 sec

procedure ConnectBtnClick;
begin
CanConnect:=True;
Client.open;
end;

Procedure DisconnectBtnClick;
begin
CanConnect := False;
Client.Close;
end;

procedure ClientonDisconnect;
begin
IF CanConnect then Timer1.Enabled := True;
end;

Procedure ClientonError;
begin
Client.Socket.Disconnect(Socket.socketHandle);
IF CanConnect then Timer1.Enabled := True;
end;

Procedure Timer1Timer;
begin
Timer1.Enabled := False;
Client.open;
end;


 
megatrend ©   (2002-10-02 18:22) [10]

Спасибо. А чем отличаются значения свойства "режим" компонента Tsocketserver - ThreadBlocking от NonBlocking?


 
megatrend ©   (2002-10-07 10:50) [11]

?


 
VID ©   (2002-10-07 12:28) [12]

Тем что в режиме stThreadBlocking для каждого нового клиента создаётся отдельный поток, в котором и происходит получение пакетов от клиента, и вообще большая часть работы с клиентом может происходить в этом доп.потоке. А в режиме stNonBlocking вся работа с клиентами осуществляется в основном потоке приложение, что в конечном счетё может приводить к "торможению" сервера.


 
megatrend ©   (2002-10-07 12:45) [13]

А надо как-либо переписывать код, чтобы в один прекрасный день перейти с одного режима на другой (например, с NonBlocking на stThreadBlocking)? Или Дельфи все сделает сама?


 
VID ©   (2002-10-07 13:55) [14]

ещё как надо. Поэтому лучше начинать с stThreadBlocking



Страницы: 1 вся ветка

Текущий архив: 2002.12.02;
Скачать: CL | DM;

Наверх




Память: 0.51 MB
Время: 0.017 c
6-4547
aga
2002-10-04 12:33
2002.12.02
можно ли чтобы кто-то подключился ко мне как к провайдеру и...


3-4181
bigbill
2002-11-13 04:41
2002.12.02
номер записи ПОСЛЕ фильтрации


3-4211
Геннадий
2002-11-12 21:42
2002.12.02
При удалении дублир-щих записей удал-ся ВСЕ. А как оставить одну?


3-4206
Yazilimci
2002-11-13 15:26
2002.12.02
Vapros:


1-4440
alcat
2002-11-20 01:56
2002.12.02
Проблема с ReadLn