| Autor |
Mensagem |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 20/07/2009 21:12:07
|
laudenpower
JavaEvangelist
![[Avatar]](/images/avatar/090d1f9732c52fc3770cba691cff7d11.jpg)
Membro desde: 28/12/2008 21:00:08
Mensagens: 349
Offline
|
Olá pessoal, bem estou implementando um sistema clienteXservidor onde eu quero abrir um socket no cliente e mante-lo aberto durante todo o ciclo de vida do aplicativo cliente apenas mandando mensagens para o servidor. Acontece que eu até consigo manter ele aberto porém tudo que eu mando para o servidor só é enviado de fato mesmo quando eu fecho o socket no cliente, mas ai nesse caso eu perco a conexão. Já tentei mandar um '\n' no fim da mensagem mas nesse caso é a mesma coisa que se eu fechasse o socket, tipo o que eu quero mesmo é que ele fique aberto o tempo todo sendo que eu apenas chamaria um método para mandar a mensagem para o servidor.
Eu fiz uns testes com um servidor feito em delphi e nesse caso quando eu dava um in.write(algum byte) seguido de um in.flush(); o servidor mostrava na tela normalmente a mensagem vinda do cliente, mas quando eu fiz isso em um servidor feito em java a coisa não deu certo.
Enfim era essa a minha pergunta, é possível manter esse socket aberto enviando mensagens?
Desde já grato pela atenção.
|
Enquanto cultivares teu saber, nada tens a temer!
"Any fool can write code that a computer can understand. Good programmers write code that humans can understand."
-Martin Fowler et al, Refactoring: Improving the Design of Existing Code, 1999 |
|
|
 |
|
|
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 07:43:16
|
ViniGodoy
Moderador
![[Avatar]](/images/avatar/1921493b5362e63fbe8983f4bd54157d.png)
Membro desde: 11/12/2006 08:22:01
Mensagens: 20576
Localização: Curitiba/PR
Offline
|
Sim, é possível.
Como você está fazendo a leitura do socket?
|
@ViniGodoy - Lattes
Tem dúvidas de Java? Poste no fórum! Não respondo dúvidas de java via MP!
Ponto V! - Desenvolvimento de Jogos Profissional - @Pontov - Facebook
Projeto Towel - Swing de uma forma inteligente (Novo lar do ObjectTableModel e do Auto-Filtro).
Ei... você está usando DefaultTableModel no seu projeto??
Não faça isso! Veja: http://www.guj.com.br/posts/list/15/199067.java#1001295 |
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 07:43:47
|
filipenf
JavaBaby
Membro desde: 27/05/2009 12:47:07
Mensagens: 98
Offline
|
é possível sim, e não há a necessidade de ficar enviando \n nem fechar a conexão. O que deve estar acontecendo é que o SO ou a VM devem estar 'bufferizando' a saída do seu socket. Você está dando flush a cada vez que escreve ?
|
Você está bêbado quando começa a sentir solidariedade e não consegue pronunciar essa palavra.
Filipe N. Felisbino
SCJP - SCWCD - LPIC 1
fnf01.blogspot.com - twitter.com/filipenf
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 07:52:39
|
laudenpower
JavaEvangelist
![[Avatar]](/images/avatar/090d1f9732c52fc3770cba691cff7d11.jpg)
Membro desde: 28/12/2008 21:00:08
Mensagens: 349
Offline
|
Segue o código:
Servidor
Cliente
Desde já agradeço a atenção de todos.
|
Enquanto cultivares teu saber, nada tens a temer!
"Any fool can write code that a computer can understand. Good programmers write code that humans can understand."
-Martin Fowler et al, Refactoring: Improving the Design of Existing Code, 1999 |
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 08:42:36
|
thingol
Moderador
Membro desde: 29/07/2004 16:10:13
Mensagens: 17543
Offline
|
Você pode mudar um pouco seu protocolo? Pela minha experiência, é muito difícil fazer protocolos baseados em texto funcionar.
Normalmente é aconselhável:
- Modificar uma opção DO SOCKET ( dê uma olhada em setTcpNoDelay - você deve chamar esse método imediatamente após abrir o socket , e não depois, com o parâmetro "true" ) para que ele não bufferize a saída :
- Criar um protocolo binário que mande pacotes com cabeçalho e dados.
O cabeçalho pode ser bem simples e ter apenas o tamanho dos dados (em 2 bytes).
Por exemplo, para mandar a mensagem "abacaxi" (que tem 7 bytes), você:
a) Converte a mensagem para um array de bytes;
b) Mede o tamanho desse array;
c) Usa DataOutputStream, método writeShort, para gravar o tamanho desse array;
d) Usa DataOutputStream, método write, para mandar os outros bytes.
Para receber a mensagem, você
a) Usa DataInputStream, método readShort, para ler o tamanho do array;
b) Vai chamando repetidamente DataInputStream, método read, até receber todos os dados (de acordo com o tamanho) e acumulando os dados em um ByteArrayOutputStream. Quando receber todos os dados (ou quando read retornar -1, indicando que o socket foi fechado), a mensagem foi lida.
This message was edited 1 time. Last update was at 21/07/2009 08:44:34
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 08:46:09
|
thingol
Moderador
Membro desde: 29/07/2004 16:10:13
Mensagens: 17543
Offline
|
thingol wrote:Você pode mudar um pouco seu protocolo? Pela minha experiência, é muito difícil fazer protocolos baseados em texto funcionar.
Mesmo o HTTP, que é um protocolo baseado em texto, também trabalha com tamanhos de mensagens (o tal do Content-Length).
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 09:04:38
|
laudenpower
JavaEvangelist
![[Avatar]](/images/avatar/090d1f9732c52fc3770cba691cff7d11.jpg)
Membro desde: 28/12/2008 21:00:08
Mensagens: 349
Offline
|
thingol wrote:Você pode mudar um pouco seu protocolo? Pela minha experiência, é muito difícil fazer protocolos baseados em texto funcionar.
Tipo nesse caso minha inexperiencia me deixa na mão a principio eu tenho que mandar uma mensagem para o servidor e nada mais (tipo não preciso receber nada do mesmo), mas sendo assim você poderia me mandar um link exemplificando a criação de tal protocolo?
Desde já agradeço muito a todos que dedicaram a sua atenção.
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 11:58:05
|
Tchello
GUJ Master
![[Avatar]](/images/avatar/901db33c84e81b1a30e59949bbcb112b.png)
Membro desde: 07/06/2008 14:41:04
Mensagens: 1693
Online
|
thingol, um protocolo em xml não seria interessante?
Mesmo que o projeto seja para fins didáticos seria algo que eu mesmo gostaria muito de implementar.
Sim, já fiz um projeto onde havia um protocolo de texto, foi um horror.
Pelo menos o componente responsável em administrar as conexões dos sockets ficou muito satisfatório =D, taí um projeto que eu gostaria de fazer novamente com meus conhecimentos atuais, ficaria muito mais interessante ^^
Desculpem-me pela divagação, é apenas a nostalgia em atacando =(
Abraços!
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 11:59:17
|
Tchello
GUJ Master
![[Avatar]](/images/avatar/901db33c84e81b1a30e59949bbcb112b.png)
Membro desde: 07/06/2008 14:41:04
Mensagens: 1693
Online
|
lol, ao postar aqui o GUJ lançou um SocketException hehehehehe
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 13:03:40
|
laudenpower
JavaEvangelist
![[Avatar]](/images/avatar/090d1f9732c52fc3770cba691cff7d11.jpg)
Membro desde: 28/12/2008 21:00:08
Mensagens: 349
Offline
|
Tchello wrote: thingol, um protocolo em xml não seria interessante? Mesmo que o projeto seja para fins didáticos seria algo que eu mesmo gostaria muito de implementar. Sim, já fiz um projeto onde havia um protocolo de texto, foi um horror. Pelo menos o componente responsável em administrar as conexões dos sockets ficou muito satisfatório =D, taí um projeto que eu gostaria de fazer novamente com meus conhecimentos atuais, ficaria muito mais interessante ^^ Desculpem-me pela divagação, é apenas a nostalgia em atacando =( Abraços!
É que na verdade eu apenas preciso enviar uma string de tamanho 10, nada mais tipo eu estou usando o DataInputStream e o DataOutputStream para enviar as informações do cliente e ler elas no servidor, o que acontece é que não tem jeito do servidor ficar lendo a medida que vou enviando, o servidor processa o que o cliente manda apenas quando o mesmo fecha a conexão. Você teria algum exemplo de como fazer essa comunicação, mantendo o socket do cliente aberto. Desde já agradeço a atenção
This message was edited 1 time. Last update was at 21/07/2009 13:04:21
|
Enquanto cultivares teu saber, nada tens a temer!
"Any fool can write code that a computer can understand. Good programmers write code that humans can understand."
-Martin Fowler et al, Refactoring: Improving the Design of Existing Code, 1999 |
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 13:36:51
|
thingol
Moderador
Membro desde: 29/07/2004 16:10:13
Mensagens: 17543
Offline
|
Thingol wrote:
- Modificar uma opção DO SOCKET ( dê uma olhada em setTcpNoDelay - você deve chamar esse método imediatamente após abrir o socket , e não depois, com o parâmetro "true" ) para que ele não bufferize a saída :
Você leu o que escrevi? Vou repetir.
Em caso de dúvida:
http://articles.techrepublic.com.com/5100-10878_11-1050878.html
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 13:54:37
|
laudenpower
JavaEvangelist
![[Avatar]](/images/avatar/090d1f9732c52fc3770cba691cff7d11.jpg)
Membro desde: 28/12/2008 21:00:08
Mensagens: 349
Offline
|
thingol wrote:
Thingol wrote:
- Modificar uma opção DO SOCKET ( dê uma olhada em setTcpNoDelay - você deve chamar esse método imediatamente após abrir o socket , e não depois, com o parâmetro "true" ) para que ele não bufferize a saída :
Você leu o que escrevi? Vou repetir.
Em caso de dúvida:
http://articles.techrepublic.com.com/5100-10878_11-1050878.html
Nesse caso é após a criação do socket no cliente? Eu li o que foi escrito porém quando eu chamo o método setTcpNoDelay(true); não acontece nada. Li o conceito sobre os método TCP_NODELAY e TCP_CORK, até onde eu pude entender quando eu configuro o meu socket para um desses o mesmo não espera que o cabeçalho do pacote seja enviado antes. Mas nesse caso não estou entendendo como eu tenho que chamar o método imediatamente após abrir o socket, vou postar o código que comecei do zero para os colegas avaliarem melhor.
Servidor
Cliente
Desculpa se não entendi direito algumas coisas, mas estou acompanhando esse tópico com o máximo de atenção para não disperdiçar o tempo de ninguém.
Desde já agrdeço pela atenção.
|
|
|
 |
![[Post New]](/templates/default/images/icon_minipost_new.gif) 21/07/2009 14:41:20
|
filipenf
JavaBaby
Membro desde: 27/05/2009 12:47:07
Mensagens: 98
Offline
|
não vejo problema nenhum quanto à usar o protocolo texto. Temos uma aplicação aqui que conecta à um servidor feito em C++ e transfere dados em modo texto sem problema. Existe uma opção para utilizar texto-plano ou criptografado, e nunca tive nenhum problema com isso. Pelo que entendi o problema é buffer, só não sei se no client ou no servidor.
Se você tiver acesso à uma máquina com linux, sugiro você usar o netcat pra emular o seu servidor, desta forma você consegue verificar se o problema é realmente o client. Basta você digitar
netcat -l -p 20000
e depois apontar o seu client para essa máquina. Com o uso do netcat, tudo que entrar por essa porta será impresso na stdout. Se não aparecer nada, o problema está no seu client. Se aparecer, o problema está no seu server.
|
Você está bêbado quando começa a sentir solidariedade e não consegue pronunciar essa palavra.
Filipe N. Felisbino
SCJP - SCWCD - LPIC 1
fnf01.blogspot.com - twitter.com/filipenf
|
|
|
 |
|
|