usuário(s) online!

LER ARTIGO
  Artigos Recentes
Todos os Artigos
Mais Votados
Artigos com Arquivos
Por Categoria

  Dicas Recentes
Todas as Dicas
Mais Votadas
Dicas com Arquivos
Por Categoria

  Downloads
Fórum Delphi
E-Zines Anteriores
Notícias
Manifesto Tecnocolor
Nossa Lojinha
Como usar o Site?


  Cadastre-se
Alterar Cadastro
Login/Logout
Escrever Artigos
Escrever Dicas
Meus Artigos
Minhas Dicas


  Contate-nos
Você tem Site?
Indique para Amigos

Comunicação entre micros via TCP/IP
Comunicação entre micros via TCP/IP
Delphi 3.x Delphi 4.x Delphi 5.x
Categoria:
Outros
Nível de Habilidade:
Classificação:
Inserção:
18/03/2003
Palavras Principais:
TCP/IP IP comunicação
Número de Votos :
45
Usuário: Ramos de Souza Janones
Referência: Ramos da Informática

Questão/Problema:

Como realizar comunicação TCP/IP

Resposta:

O TCP/IP é o protocolo de comunicação usado na Internet. Ele pode ser usado para permitir que dois programas troquem informações ente si. E o melhor: os programas podem estar tanto na mesma máquina como conectados via Internet.
Em várias situações precisamos trocar informações entre programas. Existem muitas maneiras de fazer isto, provavelmente a mais comum é via tabelas de bancos de dados. No entanto, uma das técnicas se destaca: troca de informações via TCP/IP. Esta técnica tem as seguintes vantagens:

É relativamente fácil de usar;

Funciona para programas rodando no mesmo micro, em rede local ou até mesmo via Internet;

É rápida e eficiente.

A única desvantagem é que o protocolo TCP/IP deve estar instalado na máquina. Como este protocolo é necessário para o acesso à Internet e a Internet é muito usada, este problema é muito pequeno.

O protocolo TCP/IP

Para transmitir informações de um lado para outro da rede, a Internet se baseia em diversos protocolos. Os principais protocolos, sob os quais todos os demais são construídos são:

TCP ou Transmission Control Protocol;

IP ou Internet Protocol.

Estes dois protocolos são usados em conjunto e conhecidos coletivamente como TCP/IP.

O IP tem a responsabilidade de enviar dados de um computador a outro. Cada transmissão IP traz inclui os campos mostrados na figura1.


Cabeçalho
(checksum, contador de expiração etc)
Endereço IP de origem
Endereço IP de destino
Dados
Figura 1


O campo de dados contém a informação que deve ser enviada. Caso o campo de dados seja muito grande para uma rede em particular, o IP pode quebra-lo em vários pacotes e remonta-los no destino. O endereço IP é um número de 32 bits, necessário para qualquer troca de informações pela Internet. Cada equipamento conectado à Internet deve ter um endereço IP único. Este endereço pode ser atribuído basicamente de duas formas:

Fixamente: Neste caso, cada equipamento tem sempre o mesmo número IP, atribuído durante a configuração. É normalmente o caso de universidades e grandes empresas americanas que se conectaram cedo à Internet e pegaram uma grande quantidade de endereços IP.

Dinamicamente: Neste caso, o computador recebe um endereço IP "emprestado" enquanto estiver conectado. Assim que ele se desconectar, um outro computador pode usar o endereço. É o método normalmente usado em acesso via linha discada a um provedor.

É costume especificar o endereço IP como quatro números decimais de 0 a 255, por exemplo:

207.68.156.73 (www.microsoft.com).

O algarismo final tem dois valores reservados: no início e no fim da faixa, normalmente 0 e 255, que jamais correspondem a nenhum equipamento.

Os endereços IP são difíceis para os seres humanos decorarem. Por esta razão, foi criada uma espécie de "lista telefônica" que atribui sinônimos em forma de caracteres a endereços IP. Por exemplo, www.ramosdainformatica.com.br é um "sinônimo" de IP. Esta "lista telefônica" usa um protocolo chamado "DNS". A base de dados do DNS é mantida pelos órgãos gestores da Internet (no Brasil é a FAPESP). A "publicação na lista" custa uma taxa anual que hoje está em R$70,00.

O TCP usa o protocolo IP, mas garante que os dados chegaram ao seu destino e também que chegam na ordem correta. Se houver um erro na transmissão, o pacote é enviado novamente. O TCP é capaz de manter uma conexão entre as duas pontas da comunicação.

Toda a comunicação via TCP/IP é feita através de "portas". Uma porta é um numero de 16 bits que identifica um destino dentro do servidor. Ou seja, para estabelecer comunicação entre dois computadores precisamos a porta, além do endereço IP. Algumas portas tem protocolos normalmente associados a elas, por exemplo:

FTP: 21
Telnet: 23
SMTP (Envio de correio): 25
POP3 (Recepção de correio): 125
HTTP (Web) 80
NNTP (News): 119

Quando formos criar um programa para troca de informações via TCP/IP, devemos escolher uma porta que não não esteja sendo usada. É uma boa idéia permitir que o usuário troque a porta de alguma forma, para o caso de conflitos. Outra coisa: para usar na Internet, devemos configurar os roteadores e "firewalls" no caminho para aceitarem conexões na porta escolhida.

TCP/IP no Delphi

As versões 3 e 4 do Delphi vem com dois componentes destinados a implementar conexões TCP/IP: TClientSocket e TServerSocket. Estes componentes podem ser usados de duas maneiras: "blocking" e "non-blocking". A primeira maneira dispara uma nova "thread" para cada comunicação, a segunda roda toda a comunicação na mesma thread. É muito mais fácil programar como "non-blocking" e os exemplos mostrados a seguir usam este modelo. Caso você decida por "blocking", leia atentamente a documentação do Delphi sobre o assunto.

TServerSocket implementa o lado "servidor" de uma conexão TCP/IP. Para usa-lo, devemos ajustar a porta de comunicação e chamar o método Open. O componente então fica "escutando" a porta por uma conexão. Depois de efetuada uma conexão, o evento OnClientRead é disparado quando existirem dados a serem lidos. Veja o exemplo ESCUTA.DPR:

Veja o código do programa acima:

procedure TForm1.BtEscutaClick(Sender: TObject);
begin
// Abre porta para escutar
ServerSocket1.Port := StrToInt(EdPorta.Text);
ServerSocket1.Open;
BtEscuta.Enabled := false;
BtDesconecta.Enabled := true;
end;

procedure TForm1.ServerSocket1ClientRead(Sender: TObject;
Socket: TCustomWinSocket);
var
S1, S2: string;
begin
// Lê bytes da conexão, mexe um pouco e devolve
S1 := Socket.ReceiveText;
S2 := 'Você enviou >' + S1 + '<'#13#10;
Socket.SendText(S2);
Memo1.Lines.Add('Recebido:' + S1 + ' Devolvido:'+ S2);
end;

procedure TForm1.BtDesconectaClick(Sender: TObject);
begin
// Fecha conexão
ServerSocket1.Close;
BtEscuta.Enabled := true;
BtDesconecta.Enabled := false;
end;

procedure TForm1.ServerSocket1ClientConnect(Sender: TObject;
Socket: TCustomWinSocket);
begin
Memo1.Lines.Add('Conectado com:' + Socket.RemoteAddress);
end;

procedure TForm1.ServerSocket1ClientDisconnect(Sender: TObject;
Socket: TCustomWinSocket);
begin
Memo1.Lines.Add('Desconectado de :' + Socket.RemoteAddress);
End;

Podemos testar o programa acima com o programa TELNET, que vem com o Windows. Rode programa ESCUTA e clique no botão "Escuta". A seguir, rode o Telnet na mesma máquina, peça para conectar e selecione as seguintes opções:


"localhost" é um sinônimo TCP/IP para a própria máquina. Poderíamos também ter usado o endereço IP 127.0.0.1 que tem o mesmo significado. Se você tiver dois micros conectados em rede, poderá rodar cada programa em uma máquina, ajustando no cliente o nome ou endereço IP da máquina na qual o programa servidor está rodando. Uma vez estabelecida a conexão, o que você digitar no Telnet irá até o servidor, que enviará uma resposta.

Podemos também escrever um programa para fazer o papel de cliente, com o componente TClientSocket. Para usar este componente, você deve ajustar as propriedades Port com o número da porta TCP/IP e também Address ou Host para identificar o computador remoto. Address aceita uma string no format X.X.X.X como um endereço IP. Já Host aceita um nome como string. O exemplo FALA.DPR se conecta com o exemplo anterior, ESCUTA.

Acesso a banco de dados

O exemplo a seguir (EMPINFO.DPR) faz algo mais útil: consulta uma tabela de banco de dados e retorna uma resposta. Ele usa a tabela EMPLOYEE.DB do alias DBDEMOS. Ele recebe "EmpNo", a chave primária da tabela e retorna o nome e sobrenome da pessoa. Neste exemplo, temos algumas complicações:

Devemos esperar receber um "enter" para efetuar a pesquisa.

O programa pode estar servindo várias conexões simultaneamente. Por causa disto, temos que armazenar uma string com o comando para cada conexão existente. Felizmente, existe a propriedade Data na conexão TCP/IP exatamente para isto.

Veja o código do programa:

type
PString = ^string;

procedure TForm1.ExecutaCmd(S: string; Socket: TCustomWinSocket);
var
Resposta: string;
begin
try
// Procura o registro
if Table1.Locate('EmpNo', S, []) then
Resposta := Table1FirstName.Value + ' ' + Table1LastName.Value
else
Resposta := 'Não Achado';
except
// Retorna mensagem de erro, caso tenha ocorrido
on E:Exception do
Resposta := E.Message;
end;
Socket.SendText(Resposta + #13#10);
end;

procedure TForm1.BtEscutaClick(Sender: TObject);
begin
// Abre porta para escutar
ServerSocket1.Port := StrToInt(EdPorta.Text);
ServerSocket1.Open;
BtEscuta.Enabled := false;
BtDesconecta.Enabled := true;
end;

procedure TForm1.ServerSocket1ClientRead(Sender: TObject;
Socket: TCustomWinSocket);
var
S: PString;
P: integer;
Cmd: string;
begin
// Pega e concatena dados novo
S := PString(Socket.Data);
S^ := S^ + Socket.ReceiveText;
// Procuta fim de linha
P := pos(#13, S^);
if P <> 0 then
begin
// Separa comando e executa
Cmd := copy(S^, 1, P - 1);
S^ := copy(S^, P + 1, length(S^) - P);
ExecutaCmd(Cmd, Socket);
end;
end;

procedure TForm1.BtDesconectaClick(Sender: TObject);
begin
// Fecha conexão
ServerSocket1.Close;
BtEscuta.Enabled := true;
BtDesconecta.Enabled := false;
end;

procedure TForm1.ServerSocket1ClientConnect(Sender: TObject;
Socket: TCustomWinSocket);
var
S: PString;
begin
AcrescentaMemo(Memo1, 'Conectado com:' + Socket.RemoteAddress);
// Aloca string que guardará o comando
S := new(PString);
S^ := '';
Socket.Data := new(PString);
end;

procedure TForm1.ServerSocket1ClientDisconnect(Sender: TObject;
Socket: TCustomWinSocket);
begin
// Libera memória
dispose(Socket.Data);
AcrescentaMemo(Memo1, 'Desconectado de :' + Socket.RemoteAddress);
end;

Podemos testar o programa acima tanto com o TELNET como com o projeto CONSULTAEMP, feito especialmente para isto.

Como pudemos ver, é relativamente fácil escrever programas que se conectam, diretamente via TCP/IP.


AVALIE ESTE ARTIGO !
Sua Avaliação:
Ruim
Excelente

 9 COMENTÁRIO(S) PARA ESTE ARTIGO
Muito Bom.!...
marcosabadi
30/04/2003
Excelente artigo...!...
sergiobarros
15/05/2003
Este artigo é muito interessante....
lourencon
04/07/2003
Este artigo é muito interessante....
lourencon
04/07/2003
Muito legal!!! Bom mesmo!!!...
ivantgm
11/08/2003
Interessante e útil. A Borland, porém, está ...
telmo
28/08/2003
seu artigo é muito bom, poderia falar também...
dennerbb
01/11/2003
um exemplo simples, mas muito muito util me...
NACIONAL
21/11/2003
Parabens p/Objetividade, Clareza e Eficacia...
jairconde
15/04/2005