Como é que um servidor WCF informar um cliente WCF sobre as mudanças? (Melhor solução, em seguida, simples de sondagem, por exemplo cometa ou sondagem longa)

StackOverflow https://stackoverflow.com/questions/1700917

Pergunta

ver também " impulso WCF ao cliente através firewall "

Eu preciso ter um cliente WCF que se conectam a um servidor WCF, então, quando alguns dos dados altera no servidor os clientes precisam update a sua exibição.

Como não é provável que seja um firewall entre os clientes eo servidor.

  • Todas as comunicações devem ser maiores de HTTP
  • O servidor não pode fazer uma (física) chamada de saída para o cliente.

Como estou escrevendo tanto o cliente eo servidor não precisa limitar a solução para usar apenas sabonetes etc.


Eu estou procurando construído em surport para " longo polling" / " Comet " etc


Obrigado pela resposta mais informativa de Drew Marsh sobre como implementar longo de votação em WCF. No entanto, eu pensei que o principal “ponto de venda” do WCF foi que você poderia fazer esse tipo de coisa simplesmente configurando os canais a serem utilizados no arquivo de configuração. por exemplo eu quero um canal que, logicamente, nos dois sentidos, mas fisicamente recebidas apenas.

Foi útil?

Solução

Parece-me que você já sabe a resposta: o uso a longo polling. :) Então, eu acho que a única coisa que resta a explicar é como você pode ser capaz de fazer isso com o WCF e da maneira mais eficiente possível.


O básico:

  1. Em primeiro lugar, decidir quanto tempo você deseja que cada "longa poll" para ser. Por causa do argumento que vou escolher o tempo limite 5min.
  2. Na ligação do lado do cliente, altere o sendTimeout="00:05:00".
  3. Assim como usando XMLHttpRequest (XHR) por muito tempo de votação, quando o tempo limite ocorre realmente, você vai precisar para detectá-lo e re-edição do próximo pedido de poll. Isto é bastante fácil no WCF porque há uma exceção específica, TimeoutException , que você pode pegar para detectar facilmente esta foi a questão vs. alguma outra exceção.
  4. Dependendo de como você está hospedando seu serviço WCF, você vai precisar para se certificar de configurar-se para permitir o processamento de até 5 minutos. De uma perspectiva WCF puro você vai querer certificar-se de que você definir o receiveTimeout="00:05:00". No entanto, se você está hospedando dentro de ASP.NET você também precisará configurar o tempo de execução ASP.NET para ter um tempo limite superior que é feito usando o <httpRuntime executionTimeout="300" /> ( Nota: as medidas são em segundos para este atributo).

Ser eficiente no cliente

Se você acabou de configurar o seu cliente para chamar sincronicamente o serviço e os blocos de cliente para 5 minutos enquanto espera por uma resposta, isso não é um uso muito eficiente de recursos do sistema. Você poderia colocar essas chamadas em threads de fundo, mas isso ainda vai mastigar um recurso thread enquanto a chamada é excelente. A maneira mais eficiente de lidar com isso é usar assíncrono operações.

Se você estiver criando seus contratos de serviços à mão, gostaria de sugerir verificar Nesta seção no MSDN em OperationContractAttribute.AsyncPattern para obter detalhes sobre como adicionar um BeginXXX / EndXXX par método assíncrono para cada uma das suas chamadas. No entanto, se você estiver usando svcutil para gerar seus contratos de operação para você, tudo que você precisa fazer para ter assíncrona métodos gerados é passar a opção /async na linha de comando. Para mais detalhes sobre este tópico, confira o tópico síncronas e assíncronas no MSDN .

Agora que você já ir suas operações assíncronas definir, o padrão é muito parecido com trabalhar com XHR. Você chamar o método BeginXXX a que você passar um AsyncCallback delegado. O método BeginXXX irá retornar uma IAsyncResult , que você pode hold para se você queria ser capaz de esperar sobre o funcionamento (em cenários mais avançados) ou ignorar, e, em seguida, a infra-estrutura WCF irá de forma assíncrona enviar o pedido para o servidor e espera por uma resposta nos bastidores. Quando for recebida uma resposta ou uma exceção ocorre, o retorno de chamada que você passado para o método BeginXXX será invocado. Dentro deste método de retorno você precisa chamar o método EndXXX correspondente passando o IAsyncResult que é entregue a você. Durante a chamada para o método EndXXX você precisará empregar manipulação de exceção para lidar com qualquer tipo de falha lógica que possa ter ocorrido ao chamar o método, mas isso também é onde você iria agora ser capaz de pegar o TimeoutException que falamos anteriormente. Supondo que você tem uma boa resposta, os dados serão o retornado do EndXXXligar e você pode reagir a esses dados de qualquer maneira que faz sentido.

NOTA: Uma coisa a ter em mente sobre este padrão é a natureza do threading. Os retornos de chamada assíncronos de WCF será recebido em um segmento de da piscina segmento gerenciado . Se você está pensando em atualizar a interface do usuário em uma tecnologia como WPF ou WinForms, você precisa ter certeza de que você empacotar os chama de volta para o segmento de interface do usuário usando o Invoke ou métodos BeginInvoke .

Ser eficiente no servidor

Se nós estamos indo para estar preocupado com a eficiência no cliente, devemos estar duplamente assim quando se trata de servidor. Obviamente, este tipo de puts abordagem mais demanda no lado do servidor porque uma conexão deve permanecer aberto e pendente até que haja uma razão para enviar de volta a notificação para o cliente. O desafio aqui é que você só quer amarrar o tempo de execução do WCF com o processamento desses clientes que realmente estão sendo enviados de um evento. Tudo o resto deve ser apenas adormecida, esperando que o evento ocorra. Felizmente o mesmo padrão assíncrono, a apenas utilizado no lado do cliente também trabalha no lado do servidor. No entanto, há agora uma grande diferença: agora você deve devolver o IAsyncResult (e, portanto, a WaitHandle ) a partir do método BeginXXX que o tempo de execução do WCF, então, esperar para ser sinalizada no antes de chamar seu método EndXXX.

Você não encontrar muito na forma de documentação dentro da MSDN além dos links que eu já fornecidas anteriormente e, infelizmente, as suas amostras em escrever um serviço assíncrono são menos do que útil. Dito isto, Wenlong Dong escreveu um artigo sobre o dimensionamento serviços WCF com o modelo assíncrono há algum tempo que eu recomendo que você check-out.

Além disso, eu sinceramente não posso dar muita conselhos sobre a melhor forma de implementar o modelo assíncrono no lado do servidor para você bcause depende inteiramente de que tipo de fonte de dados os seus eventos serão provenientes, em primeiro lugar . Arquivo I / O? A fila de mensagens? Um banco de dados? Algum outro software proprietário com seu próprio serviço de mensagens que você está tentando fornecer uma fachada mais? Eu não sei, mas todos eles deverão oferecer uma modelos assíncronos de sua própria onde pode cavalitas seu próprio serviço para torná-lo o mais eficiente possível.

Prescription Atualizado

Uma vez que esta parece ser uma resposta popular, eu percebi que eu deveria voltar aqui e fornecer uma atualização dadas as recentes mudanças na paisagem. Neste ponto, há agora uma biblioteca .NET chamado SignalR que fornece essa funcionalidade exata e é definitivamente como eu recomendaria implementação de qualquer comunicação com o servidor.

Outras dicas

Se o servidor poderia fazer uma conexão de saída a um barramento de serviço que você poderia implament um tipo de chamada de volta. Desta forma, o cliente / servidor não precisa saber sobre o outro em tudo, apenas a confiar barramento de serviço. Consulte .NET Service Bus

Você vai querer olhar para WSDualHttpBinding

O WSDualHttpBinding fornece a mesmo suporte para protocolos de Serviços Web como o WSHttpBinding, mas para uso com contratos duplex. WSDualHttpBinding só suporta a segurança SOAP e requer mensagens confiável. Esta vinculativo requer que o cliente tem uma pública URI que fornece um callback endpoint para o serviço. Isto é fornecida pelo ClientBaseAddress. UMA expõe ligação dupla o endereço IP do do cliente para o serviço. O cliente deve usar a segurança para garantir que ele só se conecta a serviços que confia.

Enquanto não WCF você pode tentar usar XMPP para obter essa funcionalidade vai. Há um artigo sobre InfoQ sobre ele e outros sistemas. Enquanto o artigo afirma que XMPP não pode ser usado através de HTTP, é possível ao usar BOSH .

Existem .NET bibliotecas disponíveis agsXMPP para citar um.

A empresa onde eu trabalho está começando a usá-lo para empurrar notificações de atualização para uma aplicação para ele para atualizar partes da interface do usuário.

O Google para " WCF duplex ". Eu usei isso usando com sucesso netTcpBinding (em todos os continentes), mas não tenho certeza sobre basicHttpBinding.

No entanto, ele exige que o servidor para chamar de volta para o cliente. Se o servidor não está autorizado a fazer isso, a votação pode ser sua única opção ...

Se o servidor não pode chamar o cliente (e não deve normalmente) você deve ter a votação cliente o servidor conforme especificou. desde que você tem fundamento WCF já em vigor, basta adicionar uma operação para isso.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top