Gerir ligações em Funções AzureManage connections in Azure Functions

As funções numa aplicação de função partilham recursos.Functions in a function app share resources. Entre esses recursos partilhados estão ligações: conexões HTTP, ligações de base de dados e ligações a serviços como o Armazenamento Azure.Among those shared resources are connections: HTTP connections, database connections, and connections to services such as Azure Storage. Quando muitas funções estão a funcionar simultaneamente, é possível ficar sem ligações disponíveis.When many functions are running concurrently, it's possible to run out of available connections. Este artigo explica como codificar as suas funções para evitar usar mais ligações do que as necessárias.This article explains how to code your functions to avoid using more connections than they need.

Limite de ligaçãoConnection limit

O número de ligações disponíveis é limitado em parte porque uma aplicação de função funciona num ambiente de caixa de areia.The number of available connections is limited partly because a function app runs in a sandbox environment. Uma das restrições que a caixa de areia impõe ao seu código é um limite para o número de ligações de saída, que atualmente são 600 ligações ativas (1.200 no total) por exemplo.One of the restrictions that the sandbox imposes on your code is a limit on the number of outbound connections, which is currently 600 active (1,200 total) connections per instance. Quando se chega a este limite, as funções de tempo Host thresholds exceeded: Connectionsde funcionamento escrevem a seguinte mensagem aos registos: .When you reach this limit, the functions runtime writes the following message to the logs: Host thresholds exceeded: Connections. Para mais informações, consulte os limites de serviço functions.For more information, see the Functions service limits.

Este limite é por exemplo.This limit is per instance. Quando o controlador de escala adiciona instâncias de aplicações de função para lidar com mais pedidos, cada instância tem um limite de ligação independente.When the scale controller adds function app instances to handle more requests, each instance has an independent connection limit. Isso significa que não há limite de ligação global, e você pode ter muito mais de 600 conexões ativas em todos os casos ativos.That means there's no global connection limit, and you can have much more than 600 active connections across all active instances.

Ao resolver problemas, certifique-se de que ativou os Insights de Aplicação para a sua aplicação de função.When troubleshooting, make sure that you have enabled Application Insights for your function app. Os Insights de Aplicação permitem-lhe visualizar métricas para as suas aplicações de função, como execuções.Application Insights lets you view metrics for your function apps like executions. Para mais informações, consulte a telemetria ver em Insights de Aplicação.For more information, see View telemetry in Application Insights.

Clientes estáticosStatic clients

Para evitar a detenção de mais ligações do que o necessário, reutilize as instâncias dos clientes em vez de criar novas com cada invocação de função.To avoid holding more connections than necessary, reuse client instances rather than creating new ones with each function invocation. Recomendamos que reutilize as ligações do cliente para qualquer idioma em que possa escrever a sua função.We recommend reusing client connections for any language that you might write your function in. Por exemplo, clientes .NET como os clientes HttpClient, DocumentCliente Azure Storage podem gerir ligações se utilizar um único cliente estático.For example, .NET clients like the HttpClient, DocumentClient, and Azure Storage clients can manage connections if you use a single, static client.

Aqui ficam algumas diretrizes a seguir quando está a usar um cliente específico do serviço numa aplicação de Funções Azure:Here are some guidelines to follow when you're using a service-specific client in an Azure Functions application:

  • Não crie um novo cliente com todas as funções de invocação.Do not create a new client with every function invocation.
  • Crie um único cliente estático que cada invocação de função possa usar.Do create a single, static client that every function invocation can use.
  • Considere criar um único cliente estático numa classe de ajudante compartilhado se diferentes funções usarem o mesmo serviço.Consider creating a single, static client in a shared helper class if different functions use the same service.

Exemplos de código de clienteClient code examples

Esta secção demonstra as melhores práticas para criar e utilizar clientes a partir do seu código de funcionamento.This section demonstrates best practices for creating and using clients from your function code.

Exemplo httpClient (C#)HttpClient example (C#)

Aqui está um exemplo de código de função C# que cria uma instância estática httpClient:Here's an example of C# function code that creates a static HttpClient instance:

// Create a single, static HttpClient
private static HttpClient httpClient = new HttpClient();

public static async Task Run(string input)
{
    var response = await httpClient.GetAsync("https://example.com");
    // Rest of function
}

Uma pergunta comum sobre httpClient em .NET é "Devo dispor do meu cliente?"A common question about HttpClient in .NET is "Should I dispose of my client?" Em geral, elimina-se IDisposable os objetos que implementam quando acabam os utilizar.In general, you dispose of objects that implement IDisposable when you're done using them. Mas não se livra de um cliente estático porque ainda não acaba de usá-lo quando a função termina.But you don't dispose of a static client because you aren't done using it when the function ends. Quer que o cliente estático viva durante a duração da sua candidatura.You want the static client to live for the duration of your application.

Exemplos de agente HTTP (JavaScript)HTTP agent examples (JavaScript)

Como fornece melhores opções de gestão http.agent de ligação, você deve node-fetch usar a classe nativa em vez de métodos não nativos, como o módulo.Because it provides better connection management options, you should use the native http.agent class instead of non-native methods, such as the node-fetch module. Os parâmetros de ligação http.agent são configurados através de opções na classe.Connection parameters are configured through options on the http.agent class. Para obter opções detalhadas disponíveis com o agente HTTP, consulte o novo Agente([opções).]For detailed options available with the HTTP agent, see new Agent([options]).

A http.globalAgent classe global http.request() utilizada por tem todos estes valores definidos para os respetivos incumprimentos.The global http.globalAgent class used by http.request() has all of these values set to their respective defaults. A forma recomendada de configurar os limites de ligação nas Funções é definir um número máximo a nível global.The recommended way to configure connection limits in Functions is to set a maximum number globally. O exemplo que se segue define o número máximo de tomadas para a aplicação de funções:The following example sets the maximum number of sockets for the function app:

http.globalAgent.maxSockets = 200;

O exemplo seguinte cria um novo pedido http com um agente HTTP personalizado apenas para esse pedido:The following example creates a new HTTP request with a custom HTTP agent only for that request:

var http = require('http');
var httpAgent = new http.Agent();
httpAgent.maxSockets = 200;
options.agent = httpAgent;
http.request(options, onResponseCallback);

Exemplo de código Do Cliente Document (C#)DocumentClient code example (C#)

O DocumentClient liga-se a uma instância de Azure Cosmos DB.DocumentClient connects to an Azure Cosmos DB instance. A documentação Azure Cosmos DB recomenda que utilize um cliente Singleton Azure Cosmos DB durante toda a sua aplicação.The Azure Cosmos DB documentation recommends that you use a singleton Azure Cosmos DB client for the lifetime of your application. O exemplo que se segue mostra um padrão para fazer isso numa função:The following example shows one pattern for doing that in a function:

#r "Microsoft.Azure.Documents.Client"
using Microsoft.Azure.Documents.Client;

private static Lazy<DocumentClient> lazyClient = new Lazy<DocumentClient>(InitializeDocumentClient);
private static DocumentClient documentClient => lazyClient.Value;

private static DocumentClient InitializeDocumentClient()
{
    // Perform any initialization here
    var uri = new Uri("example");
    var authKey = "authKey";
    
    return new DocumentClient(uri, authKey);
}

public static async Task Run(string input)
{
    Uri collectionUri = UriFactory.CreateDocumentCollectionUri("database", "collection");
    object document = new { Data = "example" };
    await documentClient.UpsertDocumentAsync(collectionUri, document);
    
    // Rest of function
}

Exemplo de código CosmosClient (JavaScript)CosmosClient code example (JavaScript)

CosmosClient conecta-se a uma instância De Db Azure Cosmos.CosmosClient connects to an Azure Cosmos DB instance. A documentação Azure Cosmos DB recomenda que utilize um cliente Singleton Azure Cosmos DB durante toda a sua aplicação.The Azure Cosmos DB documentation recommends that you use a singleton Azure Cosmos DB client for the lifetime of your application. O exemplo que se segue mostra um padrão para fazer isso numa função:The following example shows one pattern for doing that in a function:

const cosmos = require('@azure/cosmos');
const endpoint = process.env.COSMOS_API_URL;
const key = process.env.COSMOS_API_KEY;
const { CosmosClient } = cosmos;

const client = new CosmosClient({ endpoint, key });
// All function invocations also reference the same database and container.
const container = client.database("MyDatabaseName").container("MyContainerName");

module.exports = async function (context) {
    const { resources: itemArray } = await container.items.readAll().fetchAll();
    context.log(itemArray);
}

Conexões SqlClientSqlClient connections

O seu código de funcionamento pode utilizar o Fornecedor de Dados de Enquadramento .NET para o Servidor SQL(SqlClient)para efetuar ligações a uma base de dados relacional SQL.Your function code can use the .NET Framework Data Provider for SQL Server (SqlClient) to make connections to a SQL relational database. Este é também o fornecedor subjacente a quadros de dados que dependem de ADO.NET, como o Quadro de Entidades.This is also the underlying provider for data frameworks that rely on ADO.NET, such as Entity Framework. Ao contrário das ligações HttpClient e DocumentClient, ADO.NET implementa o agrupamento de ligação por padrão.Unlike HttpClient and DocumentClient connections, ADO.NET implements connection pooling by default. Mas como ainda pode ficar sem ligações, deve otimizar as ligações à base de dados.But because you can still run out of connections, you should optimize connections to the database. Para mais informações, consulte o Pooling de Ligação ao Servidor SQL (ADO.NET).For more information, see SQL Server Connection Pooling (ADO.NET).

Dica

Algumas estruturas de dados, como o Quadro de Entidades, normalmente obtêm cordas de ligação da secção ConnectionStrings de um ficheiro de configuração.Some data frameworks, such as Entity Framework, typically get connection strings from the ConnectionStrings section of a configuration file. Neste caso, deve adicionar explicitamente as cadeias de ligação à base de dados SQL à recolha de cordas de Ligação das definições da sua aplicação de função e no ficheiro local.settings.json no seu projeto local.In this case, you must explicitly add SQL database connection strings to the Connection strings collection of your function app settings and in the local.settings.json file in your local project. Se estiver a criar uma instância de SqlConnection no seu código de funcionamento, deverá armazenar o valor de cadeia de ligação nas definições da Aplicação com as suas outras ligações.If you're creating an instance of SqlConnection in your function code, you should store the connection string value in Application settings with your other connections.

Passos seguintesNext steps

Para mais informações sobre o porquê de recomendarmos clientes estáticos, consulte antipadrãode instantânea impróprio .For more information about why we recommend static clients, see Improper instantiation antipattern.

Para obter mais dicas de desempenho das Funções Azure, consulte Otimizar o desempenho e a fiabilidade das Funções Azure.For more Azure Functions performance tips, see Optimize the performance and reliability of Azure Functions.