Nota
O acesso a esta página requer autorização. Pode tentar iniciar sessão ou alterar os diretórios.
O acesso a esta página requer autorização. Pode tentar alterar os diretórios.
Por Ashley Stanton-Enfermeira, Brady Gaster e Tom Dykstra
Este artigo explica as considerações de hospedagem e dimensionamento para aplicativos de alto tráfego que usam o ASP.NET Core SignalR.
Sessões persistentes
SignalR requer que o mesmo processo do servidor trate de todos os pedidos HTTP para uma ligação específica. Quando SignalR é executado numa fazenda de servidores (múltiplos servidores), devem ser usadas "sessões fixas". As "sessões persistentes" também são conhecidas como afinidade de sessão. Serviço de Aplicações do Azure utiliza Microsoft Application Request Routing (ARR) para encaminhar pedidos. Ativar a definição "Afinidade da sessão" (Afinidade ARR) na sua aplicação do App Service ativa sessões persistentes.
Existem três cenários em que as sessões fixas não são obrigatórias para uma aplicação:
- Hospedagem num único servidor num único processo
- Usar o serviço Azure SignalR (as sessões fixas estão ativadas para o serviço, não para a aplicação)
- Todos os clientes estão configurados para utilizar WebSockets apenas e a configuração do cliente ativa SkipNegotiation
Em todos os outros cenários (incluindo quando o backplane do Redis é usado), o ambiente do servidor tem de ser configurado para sessões persistentes.
Para obter orientação sobre como configurar o Serviço de Aplicativo do Azure para SignalR, consulte Publicar um aplicativo ASP.NET Core SignalR no Serviço de Aplicativo do Azure. Para obter orientação sobre como configurar sessões rígidas para Blazor aplicativos que usam o Serviço do AzureSignalR, consulte Hospedar e implantar aplicativos do lado Blazor do servidor ASP.NET Core.
Recursos de conexão TCP
O número de conexões TCP simultâneas que um servidor Web pode suportar é limitado. Clientes HTTP padrão usam conexões efêmeras . Essas conexões podem ser fechadas quando o cliente fica ocioso e reabertas mais tarde. Por outro lado, uma SignalR conexão é persistente. SignalR As conexões permanecem abertas mesmo quando o cliente fica ocioso. Em um aplicativo de alto tráfego que atende muitos clientes, essas conexões persistentes podem fazer com que os servidores atinjam seu número máximo de conexões.
As ligações persistentes também consomem memória extra para acompanhar cada ligação.
O uso intenso de recursos relacionados à conexão por SignalR pode afetar outras aplicações web alojadas no mesmo servidor. Quando SignalR abre e mantém as últimas conexões TCP disponíveis, outros aplicativos Web no mesmo servidor também não têm mais conexões disponíveis para eles.
Se um servidor ficar sem ligações, vês erros aleatórios de socket e erros de reinício de ligação. Por exemplo:
An attempt was made to access a socket in a way forbidden by its access permissions...
Para evitar que o uso de recursos cause erros noutras aplicações web, execute SignalR em servidores diferentes dos seus outros apps web.
Para evitar que SignalR o uso de recursos cause erros em um SignalR aplicativo, dimensione para limitar o número de conexões que um servidor precisa manipular.
Expansão horizontal
Uma aplicação que usa SignalR precisa fazer o acompanhamento de todas as suas conexões, o que cria problemas para um grupo de servidores. Adicione um servidor e ele obtém novas conexões que os outros servidores não conhecem. Por exemplo, SignalR em cada servidor no diagrama a seguir não está ciente das conexões nos outros servidores. Quando SignalR em um dos servidores deseja enviar uma mensagem para todos os clientes, a mensagem só vai para os clientes conectados a esse servidor.
As opções para resolver este problema são o Serviço Azure SignalR e o Redis backplane.
Azure SignalR Serviço
O Serviço do Azure SignalR funciona como um proxy para tráfego em tempo real e funciona como um backplane quando o aplicativo é expandido em vários servidores. Cada vez que um cliente inicia uma conexão com o servidor, o cliente é redirecionado para se conectar ao serviço. O diagrama seguinte ilustra este processo:
O resultado é que o serviço gerencia todas as conexões do cliente, enquanto cada servidor precisa apenas de um pequeno número constante de conexões com o serviço, conforme mostrado no diagrama a seguir:
Esta abordagem de expansão horizontal tem várias vantagens em relação à alternativa de backplane do Redis:
- As sessões persistentes, também conhecidas como afinidade do cliente, não são necessárias porque os clientes são imediatamente redirecionados para o serviço Azure SignalR quando estabelecem ligação.
- Um SignalR aplicativo pode ser dimensionado com base no número de mensagens enviadas, enquanto o Serviço do Azure SignalR é dimensionado para lidar com qualquer número de conexões. Por exemplo, pode haver milhares de clientes, mas se forem enviadas apenas algumas mensagens por segundo, a SignalR aplicação não precisa de escalar para vários servidores só para gerir as ligações em si.
- Uma SignalR aplicação não usa muitos mais recursos de ligação do que uma aplicação web sem SignalR.
Por estas razões, a recomendação é usar o Serviço Azure SignalR para todas as aplicações ASP.NET Core SignalR alojadas em Azure, incluindo Serviço de Aplicações, máquinas virtuais e containers.
Para mais informações, consulte a documentação de serviço Azure SignalR Service.
Backplane do Redis
O Redis é um armazenamento de chave-valor na memória que suporta um sistema de mensagens com um modelo de publicação/assinatura. O SignalR backplane do Redis utiliza a funcionalidade de publicação/subscrição para reencaminhar mensagens para outros servidores. Quando um cliente faz uma conexão, as informações de conexão são passadas para o backplane. Quando um servidor quer enviar uma mensagem a todos os clientes, envia-a para o backplane. O backplane conhece todos os clientes conectados e em quais servidores eles estão. Ele envia a mensagem para todos os clientes através de seus respetivos servidores. Este processo é ilustrado no diagrama seguinte:
O backplane Redis é a abordagem de dimensionamento recomendada para aplicativos hospedados na sua própria infraestrutura. Se existir uma latência significativa de ligação entre o seu centro de dados e um centro de dados Azure, o serviço Azure SignalR pode não ser uma opção prática para aplicações locais com requisitos de baixa latência ou alto rendimento.
As vantagens do Serviço Azure SignalR descritas anteriormente são desvantagens para o backplane Redis:
- As sessões permanentes, também conhecidas como afinidade do cliente, são necessárias, exceto quando ambos os casos a seguir forem verdadeiros:
- Todos os clientes são configurados para usar apenas WebSockets.
- A configuração SkipNegotiation está ativada na configuração cliente. Depois de uma ligação ser iniciada num servidor, a ligação tem de permanecer nesse servidor.
- Uma SignalR aplicação tem de escalar consoante o número de clientes, mesmo quando envia poucas mensagens.
- Uma SignalR aplicação usa muito mais recursos de ligação do que uma aplicação web sem SignalR.
Limitações do IIS no sistema operativo cliente Windows
O Windows 10 e o Windows 8.x são sistemas operativos cliente. O Serviços de Informação Internet (IIS) em sistemas operativos clientes tem um limite de 10 ligações concorrentes. As SignalR ligações têm as seguintes características:
- São transitórias e frequentemente restabelecidas.
- Não são descartados imediatamente quando deixam de ser usados.
Estas características tornam provável que atinja o limite de 10 ligações num sistema operativo cliente. Quando utiliza um sistema operativo cliente para desenvolvimento, considere as seguintes recomendações:
- Evite o IIS
- Utilize Kestrel ou o IIS Express como destinos de implementação
Linux com Nginx
O seguinte código contém as definições mínimas necessárias para ativar WebSockets, ServerSentEvents e LongPolling para SignalR:
http {
map $http_connection $connection_upgrade {
"~*Upgrade" $http_connection;
default keep-alive;
}
server {
listen 80;
server_name example.com *.example.com;
# Configure the SignalR Endpoint
location /hubroute {
# App server url
proxy_pass http://localhost:5000;
# Configuration for WebSockets
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_cache off;
# WebSockets were implemented after http/1.0
proxy_http_version 1.1;
# Configuration for ServerSentEvents
proxy_buffering off;
# Configuration for LongPolling or if your KeepAliveInterval is longer than 60 seconds
proxy_read_timeout 100s;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
}
}
Quando são utilizados vários servidores back-end, devem ser adicionadas sessões persistentes para impedir que as ligações SignalR mudem de servidor ao estabelecer ligação. Existem várias maneiras de adicionar sessões adesivas no Nginx. Os exemplos seguintes mostram duas abordagens baseadas no que tem disponível.
O código seguinte complementa a configuração de exemplo anterior. Nos excertos, backend está o nome do grupo de servidores.
Com o Nginx Open Source, utiliza-se
ip_hashpara encaminhar ligações para um servidor com base no endereço IP do cliente:http { upstream backend { # App server 1 server localhost:5000; # App server 2 server localhost:5002; ip_hash; } }Com Nginx Plus, utilize
stickypara adicionar cookie aos pedidos e associar os pedidos do utilizador a um servidor:http { upstream backend { # App server 1 server localhost:5000; # App server 2 server localhost:5002; sticky cookie srv_id expires=max domain=.example.com path=/ httponly; } }Para ambas as configurações, muda
proxy_pass http://localhost:5000naserversecção paraproxy_pass http://backend.
Pode encontrar mais informações em Host ASP.NET Core no Linux com Nginx.
- Para usar WebSockets em vez de Nginx, veja Proxy WebSocket com Nginx.
- Para usar balanceamento de carga e sessões fixas, veja HTTP load balancing com Nginx.
Outros fornecedores de SignalR backplane
Os seguintes fornecedores que não são da Microsoft também oferecem SignalR backplane: