![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Сокеты [D7, WinXP]
Ivolg © (2006-08-04 19:51:00)Всем привет ! У меня возникла такая проблема с TServerSocket и TClientSocket... Вообщем при передаче какого-нибудь текста, принимается у меня он иногда с каракулями... Например посылаю: Client.Socket.SendText('90'), сервер принемает не число 90, а їРї9Р0ї... Помогите пожайлуста, в чем может быть проблема ? Спасибо...
Ivolg (2006-08-07 13:08:00) [1]Кто-нибдуь работал с этим компонентом ?
Ivolg (2006-08-05 22:17:00) [2]>Ketmar © (05.08.06 19:52) [12]
А этот компонент, только на локальном хосте работает ?
Ivolg (2006-08-05 20:45:00) [3]>Ketmar © (05.08.06 19:52) [12]
Спасибо ОГРОМНОЕ... Буду юзать )
Ketmar (2006-08-05 19:52:00) [4]TVyChat (было у Кабана -- http://cobans.net/). в Indy есть IRC. может, и ещё есть, с ходу вспоминать лень.
Ivolg (2006-08-05 17:22:00) [5]>Ketmar © (05.08.06 16:53) [10]
б, в - варианты мне походят, вопрос: где взять уже готовые компоненты для чата ?
Ketmar (2006-08-05 16:53:00) [6]> [9] Ivolg © (05.08.06 16:03)
а) не использовать сеть вообще;
б) сделать нормальный протокол и разбирать его;
в) использовать уже готовые компоненты для чата.
Ivolg (2006-08-05 16:03:00) [7]Можете посоветовать\подсказать как исправить эту проблему ?
Ketmar (2006-08-05 09:44:00) [8]> [7] Ivolg © (05.08.06 00:43)
тебе же пояснили. если ты отправил 100 байт, то совсем не обязательно клиент получит именно эти 100 и именно сразу. он может получить их любыми кусками. порядок сохранится, но не более.
Ivolg (2006-08-05 00:43:00) [9]>kami ©
Собственно эта статья мне ничем не помогла :\
kami (2006-08-04 23:29:00) [10]Ага, а вот тут уже нужно учитывать разбиение и склейку пакетов.
Пример - подключается клиент (при уже подключенных нескольких). Тогда начинается отправка всем известным полного списка ников (причем - с каждым новым ответом "Status\" данных в каждое гнездо посылается все больше и больше). Вот и получается, что при сравнительно большой занятости сети может быть следующее :
Сервер отправил"Ul\1;2;3...6;"и (после еще одного ответа клиента)"Ul\1;2;3;...6;7;".
При передаче эти два сообщения склеились, и на клиент пришло :"Ul\1;2;3...6;Ul\1;2;3;...6;7;", а могло и так (тоже к примеру) :"Ul\1;2;3...6;Ul\1;2"+";3;...6;7;".
А теперь посмотри, как это обрабатывают твои сервер с клиентами :) Никак.А нужно.
Почитай, например, http://www.delphimaster.ru/articles/sockets/index.html
Ivolg (2006-08-04 23:00:00) [11]Вот это кусок куда из моего чата, который передается с искажениями:
Серверная часть:
procedure TForm1.ServerClientRead(Sender: TObject;
Socket: TCustomWinSocket);
var
S: string;
i: Integer;
begin
S:=Socket.ReceiveText;
if Copy(s,1,7)='Status\' then begin
Delete(s,1,7);
ListBox1.Items.Add(s); // Добавляем юзера в список
S:='Ul\';
for i:=0 to ListBox1.Items.Count-1 do
S:=S+ListBox1.Items[i]+';'; // Разделяем каждый ник знаком ;
for i:=0 to Server.Socket.ActiveConnections-1 do
Server.Socket.Connections[i].SendText(S);
end;
end;
procedure TForm1.ServerClientConnect(Sender: TObject;
Socket: TCustomWinSocket);
var
i: Integer;
begin
listbox1.Clear;
for i:=0 to Server.Socket.ActiveConnections-1 do
Server.Socket.Connections[i].SendText('Status\'); // Посылаем клиенту запрос на получение его ника
end;
end.
Клиентская часть:
procedure TForm1.ClientRead(Sender: TObject;
Socket: TCustomWinSocket);
var
S: String;
it: TListItem;
begin
S:=Socket.ReceiveText;
if Copy(s,1,3)='Ul\' then begin
Delete(s,1,3);
lv.Clear;
while Pos(';',s) > 0 do begin
it:=lv.Items.Add;
it.Caption:=Copy(s,1,Pos(';',s)-1);
Delete(s,1,Pos(';',s));
end;
end;
if copy(s,1,7)='Status\' then begin
delete(s,1,7);
client.Socket.SendText('Status\'+edit1.Text); // Посылаем серверу свой ник
end;
end;
Когда когда заходят больше 3-4 клиентов в чат, то у одних показывается что юзеров 6-8, у других получается такая вещь:
User
User
User
Ul/User
User
Ul/User
User
User
Иного даже вместо Ников, добовляются всякие каракули...
kami (2006-08-04 20:56:00) [12]Забыл архи-сложный код :)
procedure TForm1.FormCreate(Sender: TObject);
begin
ss:=TServerSocket.Create(Self);
ss.Port:=1256;
ss.OnClientRead:=ssClientRead;
ss.Active:=True;
cs:=TClientSocket.Create(Self);
cs.Address:='127.0.0.1';
cs.Port:=1256;
cs.Active:=True;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
cs.Socket.SendText(Edit1.Text);
end;
procedure TForm1.ssClientRead(Sender: TObject;
Socket: TCustomWinSocket);
begin
Edit2.Text:=Socket.ReceiveText;
end;
Пытался как только мог - отправлял и много текста, и циклом, так и не смог добиться того, чтобы принялось что-то не то, что отправлял :)) (да и невозможно это, если не брать в расчет склейку и разбиение по пакетам)
kami (2006-08-04 20:28:00) [13]Только что (в пределах одного приложения) посмотрел - все передается без искажений.
Ivolg (2006-08-04 20:13:00) [14]>kami © (04.08.06 20:05) [1]
Как принимаешь, код давай.
Как обычно...
procedure TForm1.ServerSocket1ClientRead(Sender: TObject;
Socket: TCustomWinSocket);
var
Msg: String;
I: Integer;
begin
Msg:=Socket.ReceiveText;
I:=StrToInt(Msg);
end;
end.
kami (2006-08-04 20:05:00) [15]Как принимаешь, код давай.