Habilitar a comunicação para instâncias de função nos Serviços de Nuvem do Azure (clássico)
Importante
Os Serviços na Nuvem (clássicos) foram preteridos para todos os clientes a partir de 1º de setembro de 2024. Todas as implantações em execução existentes serão interrompidas e encerradas pela Microsoft e os dados serão perdidos permanentemente a partir de outubro de 2024. Novas implantações devem usar o novo modelo de implantação baseado no Azure Resource Manager Serviços de Nuvem do Azure (suporte estendido).
As funções de serviço de nuvem se comunicam por meio de conexões internas e externas. As conexões externas são chamadas de pontos de extremidade de entrada, enquanto as conexões internas são chamadas de pontos de extremidade internos. Este artigo descreve como modificar a definição de serviço para criar pontos de extremidade.
Ponto final de entrada
O ponto de extremidade de entrada é usado quando você deseja expor uma porta para o exterior. Você especifica o tipo de protocolo e a porta do ponto de extremidade, que se aplica às portas externa e interna do ponto de extremidade. Se desejar, você pode especificar uma porta interna diferente para o ponto de extremidade com o atributo localPort .
O ponto de extremidade de entrada pode usar os seguintes protocolos: http, https, tcp, udp.
Para criar um ponto de extremidade de entrada, adicione o elemento filho InputEndpoint ao elemento Endpoints de uma função Web ou de trabalho.
<Endpoints>
<InputEndpoint name="StandardWeb" protocol="http" port="80" localPort="80" />
</Endpoints>
Ponto de extremidade de entrada da instância
Os pontos de extremidade de entrada de instância são semelhantes aos pontos de extremidade de entrada, mas permitem mapear portas específicas voltadas para o público para cada instância de função individual usando o encaminhamento de porta no balanceador de carga. Você pode especificar uma única porta voltada para o público ou um intervalo de portas.
O ponto de extremidade de entrada da instância só pode usar tcp ou udp como protocolo.
Para criar um ponto de extremidade de entrada de instância, adicione o elemento filho InstanceInputEndpoint ao elemento Endpoints de uma função Web ou de trabalho.
<Endpoints>
<InstanceInputEndpoint name="Endpoint2" protocol="tcp" localPort="10100">
<AllocatePublicPortFrom>
<FixedPortRange max="10109" min="10105" />
</AllocatePublicPortFrom>
</InstanceInputEndpoint>
</Endpoints>
Parâmetro de avaliação interno
Os pontos de extremidade internos estão disponíveis para comunicação instância a instância. A porta é opcional e, se omitida, uma porta dinâmica é atribuída ao ponto de extremidade. Um intervalo de portas pode ser usado. Há um limite de cinco pontos de extremidade internos por função.
O endpoint interno pode usar os seguintes protocolos: http, tcp, udp, any.
Para criar um ponto de extremidade de entrada interno, adicione o elemento filho InternalEndpoint ao elemento Endpoints de uma função Web ou de trabalho.
<Endpoints>
<InternalEndpoint name="Endpoint3" protocol="any" port="8999" />
</Endpoints>
Você também pode usar um intervalo de portas.
<Endpoints>
<InternalEndpoint name="Endpoint3" protocol="any">
<FixedPortRange max="8999" min="8995" />
</InternalEndpoint>
</Endpoints>
Funções de trabalho vs. funções Web
Há uma pequena diferença com os pontos de extremidade ao trabalhar com funções de trabalho e da Web. A função Web deve ter, no mínimo, um único ponto de extremidade de entrada usando o protocolo HTTP .
<Endpoints>
<InputEndpoint name="StandardWeb" protocol="http" port="80" localPort="80" />
<!-- more endpoints may be declared after the first InputEndPoint -->
</Endpoints>
Usando o SDK do .NET para acessar um ponto de extremidade
A Biblioteca Gerenciada do Azure fornece métodos para instâncias de função se comunicarem em tempo de execução. A partir do código em execução em uma instância de função, você pode recuperar informações sobre a existência de outras instâncias de função e seus pontos de extremidade. Você também pode obter informações sobre a instância de função atual.
Nota
Você só pode recuperar informações sobre instâncias de função que estão sendo executadas em seu serviço de nuvem e que definem pelo menos um ponto de extremidade interno. Não é possível obter dados sobre instâncias de função em execução em um serviço diferente.
Você pode usar a propriedade Instances para recuperar instâncias de uma função. Primeiro, use CurrentRoleInstance para retornar uma referência à instância de função atual e, em seguida, use a propriedade Role para retornar uma referência à própria função.
Quando você se conecta a uma instância de função programaticamente por meio do SDK do .NET, é relativamente fácil acessar as informações do ponto de extremidade. Por exemplo, depois de se conectar a um ambiente de função específico, você pode obter a porta de um ponto de extremidade específico com este código:
int port = RoleEnvironment.CurrentRoleInstance.InstanceEndpoints["StandardWeb"].IPEndpoint.Port;
A propriedade Instances retorna uma coleção de objetos RoleInstance . Essa coleção sempre contém a instância atual. Se a função não definir um ponto de extremidade interno, a coleção incluirá a instância atual, mas nenhuma outra instância. O número de instâncias de função na coleção é sempre um no caso em que nenhum ponto de extremidade interno é definido para a função. Se a função definir um ponto de extremidade interno, suas instâncias poderão ser detetadas em tempo de execução e o número de instâncias na coleção corresponderá ao número de instâncias especificadas para a função no arquivo de configuração de serviço.
Nota
A Biblioteca Gerenciada do Azure não fornece um meio de determinar a integridade de outras instâncias de função, mas você mesmo pode implementar essas avaliações de integridade se o seu serviço precisar dessa funcionalidade. Você pode usar o Diagnóstico do Azure para obter informações sobre a execução de instâncias de função.
Para determinar o número da porta de um ponto de extremidade interno em uma instância de função, você pode usar a InstanceEndpoints
propriedade para retornar um objeto Dictionary que contém nomes de ponto de extremidade e seus endereços IP e portas correspondentes. A IPEndpoint
propriedade retorna o endereço IP e a porta para um ponto de extremidade especificado. A PublicIPEndpoint
propriedade retorna a porta para um ponto de extremidade com balanceamento de carga. A parte do endereço IP da PublicIPEndpoint
propriedade não é usada.
Aqui está um exemplo que itera instâncias de função.
foreach (RoleInstance roleInst in RoleEnvironment.CurrentRoleInstance.Role.Instances)
{
Trace.WriteLine("Instance ID: " + roleInst.Id);
foreach (RoleInstanceEndpoint roleInstEndpoint in roleInst.InstanceEndpoints.Values)
{
Trace.WriteLine("Instance endpoint IP address and port: " + roleInstEndpoint.IPEndpoint);
}
}
Aqui está um exemplo de uma função de trabalho que expõe o ponto de extremidade por meio da definição de serviço e começa a escutar conexões.
Aviso
Esse código só funcionará para um serviço implantado. Ao executar no Emulador de Computação do Azure, os elementos de configuração de serviço que criam pontos de extremidade de porta direta (elementos InstanceInputEndpoint ) são ignorados.
using System;
using System.Diagnostics;
using System.Linq;
using System.Net;
using System.Net.Sockets;
using System.Threading;
using Microsoft.WindowsAzure;
using Microsoft.WindowsAzure.Diagnostics;
using Microsoft.WindowsAzure.ServiceRuntime;
using Microsoft.WindowsAzure.StorageClient;
namespace WorkerRole1
{
public class WorkerRole : RoleEntryPoint
{
public override void Run()
{
try
{
// Initialize method-wide variables
var epName = "Endpoint1";
var roleInstance = RoleEnvironment.CurrentRoleInstance;
// Identify direct communication port
var myPublicEp = roleInstance.InstanceEndpoints[epName].PublicIPEndpoint;
Trace.TraceInformation("IP:{0}, Port:{1}", myPublicEp.Address, myPublicEp.Port);
// Identify public endpoint
var myInternalEp = roleInstance.InstanceEndpoints[epName].IPEndpoint;
// Create socket listener
var listener = new Socket(
myInternalEp.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
// Bind socket listener to internal endpoint and listen
listener.Bind(myInternalEp);
listener.Listen(10);
Trace.TraceInformation("Listening on IP:{0},Port: {1}",
myInternalEp.Address, myInternalEp.Port);
while (true)
{
// Block the thread and wait for a client request
Socket handler = listener.Accept();
Trace.TraceInformation("Client request received.");
// Define body of socket handler
var handlerThread = new Thread(
new ParameterizedThreadStart(h =>
{
var socket = h as Socket;
Trace.TraceInformation("Local:{0} Remote{1}",
socket.LocalEndPoint, socket.RemoteEndPoint);
// Shut down and close socket
socket.Shutdown(SocketShutdown.Both);
socket.Close();
}
));
// Start socket handler on new thread
handlerThread.Start(handler);
}
}
catch (Exception e)
{
Trace.TraceError("Caught exception in run. Details: {0}", e);
}
}
public override bool OnStart()
{
// Set the maximum number of concurrent connections
ServicePointManager.DefaultConnectionLimit = 12;
// For information on handling configuration changes
// see the MSDN topic at https://go.microsoft.com/fwlink/?LinkId=166357.
return base.OnStart();
}
}
}
Regras de tráfego de rede para controlar a comunicação de função
Depois de definir pontos de extremidade internos, você pode adicionar regras de tráfego de rede (com base nos pontos de extremidade criados) para controlar como as instâncias de função podem se comunicar entre si. O diagrama a seguir mostra alguns cenários comuns para controlar a comunicação de função:
O exemplo de código a seguir mostra definições de função para as funções mostradas no diagrama anterior. Cada definição de função inclui pelo menos um ponto de extremidade interno definido:
<ServiceDefinition name="MyService" xmlns="http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceDefinition">
<WebRole name="WebRole1" vmsize="Medium">
<Sites>
<Site name="Web">
<Bindings>
<Binding name="HttpIn" endpointName="HttpIn" />
</Bindings>
</Site>
</Sites>
<Endpoints>
<InputEndpoint name="HttpIn" protocol="http" port="80" />
<InternalEndpoint name="InternalTCP1" protocol="tcp" />
</Endpoints>
</WebRole>
<WorkerRole name="WorkerRole1">
<Endpoints>
<InternalEndpoint name="InternalTCP2" protocol="tcp" />
</Endpoints>
</WorkerRole>
<WorkerRole name="WorkerRole2">
<Endpoints>
<InternalEndpoint name="InternalTCP3" protocol="tcp" />
<InternalEndpoint name="InternalTCP4" protocol="tcp" />
</Endpoints>
</WorkerRole>
</ServiceDefinition>
Nota
A restrição de comunicação entre funções pode ocorrer com pontos de extremidade internos de portas fixas e atribuídas automaticamente.
Por padrão, depois que um ponto de extremidade interno é definido, a comunicação pode fluir de qualquer função para o ponto de extremidade interno de uma função sem quaisquer restrições. Para restringir a comunicação, você deve adicionar um elemento NetworkTrafficRules ao elemento ServiceDefinition no arquivo de definição de serviço.
Cenário 1
Permita apenas o tráfego de rede de WebRole1 para WorkerRole1.
<ServiceDefinition name="MyService" xmlns="http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceDefinition">
<NetworkTrafficRules>
<OnlyAllowTrafficTo>
<Destinations>
<RoleEndpoint endpointName="InternalTCP2" roleName="WorkerRole1"/>
</Destinations>
<AllowAllTraffic/>
<WhenSource matches="AnyRule">
<FromRole roleName="WebRole1"/>
</WhenSource>
</OnlyAllowTrafficTo>
</NetworkTrafficRules>
</ServiceDefinition>
Cenário 2
Só permite tráfego de rede de WebRole1 para WorkerRole1 e WorkerRole2.
<ServiceDefinition name="MyService" xmlns="http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceDefinition">
<NetworkTrafficRules>
<OnlyAllowTrafficTo>
<Destinations>
<RoleEndpoint endpointName="InternalTCP2" roleName="WorkerRole1"/>
<RoleEndpoint endpointName="InternalTCP3" roleName="WorkerRole2"/>
</Destinations>
<WhenSource matches="AnyRule">
<FromRole roleName="WebRole1"/>
</WhenSource>
</OnlyAllowTrafficTo>
</NetworkTrafficRules>
</ServiceDefinition>
Cenário 3
Permite apenas tráfego de rede de WebRole1 para WorkerRole1 e WorkerRole1 para WorkerRole2.
<ServiceDefinition name="MyService" xmlns="http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceDefinition">
<NetworkTrafficRules>
<OnlyAllowTrafficTo>
<Destinations>
<RoleEndpoint endpointName="InternalTCP2" roleName="WorkerRole1"/>
</Destinations>
<AllowAllTraffic/>
<WhenSource matches="AnyRule">
<FromRole roleName="WebRole1"/>
</WhenSource>
</OnlyAllowTrafficTo>
</NetworkTrafficRules>
<NetworkTrafficRules>
<OnlyAllowTrafficTo>
<Destinations>
<RoleEndpoint endpointName="InternalTCP3" roleName="WorkerRole2"/>
</Destinations>
<WhenSource matches="AnyRule">
<FromRole roleName="WorkerRole1"/>
</WhenSource>
</OnlyAllowTrafficTo>
</NetworkTrafficRules>
</ServiceDefinition>
Cenário 4
Só permite tráfego de rede de WebRole1 para WorkerRole1, WebRole1 para WorkerRole2 e WorkerRole1 para WorkerRole2.
<ServiceDefinition name="MyService" xmlns="http://schemas.microsoft.com/ServiceHosting/2008/10/ServiceDefinition">
<NetworkTrafficRules>
<OnlyAllowTrafficTo>
<Destinations>
<RoleEndpoint endpointName="InternalTCP2" roleName="WorkerRole1"/>
</Destinations>
<AllowAllTraffic/>
<WhenSource matches="AnyRule">
<FromRole roleName="WebRole1"/>
</WhenSource>
</OnlyAllowTrafficTo>
</NetworkTrafficRules>
<NetworkTrafficRules>
<OnlyAllowTrafficTo >
<Destinations>
<RoleEndpoint endpointName="InternalTCP3" roleName="WorkerRole2"/>
</Destinations>
<AllowAllTraffic/>
<WhenSource matches="AnyRule">
<FromRole roleName="WorkerRole1"/>
</WhenSource>
</OnlyAllowTrafficTo>
</NetworkTrafficRules>
<NetworkTrafficRules>
<OnlyAllowTrafficTo >
<Destinations>
<RoleEndpoint endpointName="InternalTCP4" roleName="WorkerRole2"/>
</Destinations>
<AllowAllTraffic/>
<WhenSource matches="AnyRule">
<FromRole roleName="WebRole1"/>
</WhenSource>
</OnlyAllowTrafficTo>
</NetworkTrafficRules>
</ServiceDefinition>
Uma referência de esquema XML para os elementos usados pode ser encontrada aqui.
Próximos passos
Leia mais sobre o modelo de serviço de nuvem.